$.getScript, but for stylesheets in jQuery?

26,486

Solution 1

CSS is not a script, so you dont have to "execute" it in the sense of script execution.

Basically a <link> tag created on the fly and appended to the header should suffice, like

$('<link/>', {
   rel: 'stylesheet',
   type: 'text/css',
   href: 'path_to_the.css'
}).appendTo('head');

or

var linkElem = document.createElement('link');
document.getElementsByTagName('head')[0].appendChild(linkElem);
linkElem.rel = 'stylesheet';
linkElem.type = 'text/css';
linkElem.href = 'path_to_the.css';

if you want to do it without jQuery.

The browser will respond to the change in the DOM and update your page layout accordingly.


EDIT:

I have read that old Internet Explorer has trouble with this, and you might need to do it like in answer to make it work:

https://stackoverflow.com/a/2685639/618206


EDIT2:

Reading the file content and putting it inline (between <style> tags) is also a valid solution, but that way the CSS will not be cached by the browser.

Solution 2

I have created an alternative to $.getScript that handles stylesheets. I called it $.getStylesheet for obvious reasons.

It implements the $.Deferred object, which means you can chain things like so:

$.when($.getStylesheet('css/main.css'), $.getScript('js/main.js'))
.then(function () {
  console.log('the css and js loaded successfully and are both ready');
}, function () {
  console.log('an error occurred somewhere');
});

Here is the little function for $.getStylesheet. It is just hosted on Github gist, so I can update it if I need to.

Solution 3

you can use same method $.getScript to "download" style sheet, since $.getScript actually is just another HTTP request. but it will be a bit wired since css is not executable.

Solution 4

Here is a function that will load CSS files with a success or failure callback. I think this approach is better than the accepted answer because inserting a element into the DOM with an HREF causes an additional browser request (albeit, the request will likely come from cache, depending on response headers).

function loadCssFiles(urls, successCallback, failureCallback) {

    $.when.apply($,
        $.map(urls, function(url) {
            return $.get(url, function(css) {
                $("<style>" + css + "</style>").appendTo("head");
            });
        })
    ).then(function() {
        if (typeof successCallback === 'function') successCallback();
    }).fail(function() {
        if (typeof failureCallback === 'function') failureCallback();
    });

}

Usage as so:

loadCssFiles(["https://test.com/style1.css", "https://test.com/style2.css",],
    function() {
    alert("All resources loaded");
}, function() {
    alert("One or more resources failed to load");
});

Here is another function that will load both CSS and javascript files:

function loadJavascriptAndCssFiles(urls, successCallback, failureCallback) {

    $.when.apply($,
        $.map(urls, function(url) {
            if(url.endsWith(".css")) {
                return $.get(url, function(css) {
                    $("<style>" + css + "</style>").appendTo("head");
                });
            } else {
                return $.getScript(url);
            }
        })
    ).then(function() {
        if (typeof successCallback === 'function') successCallback();
    }).fail(function() {
        if (typeof failureCallback === 'function') failureCallback();
    });

}
Share:
26,486
Lucas
Author by

Lucas

Updated on December 01, 2021

Comments

  • Lucas
    Lucas over 2 years

    Is there a $.getScript equivalent in jQuery, but for loading stylesheets?

  • David Hellsing
    David Hellsing over 11 years
    This is not really an equivalent, since there is no callback for when the CSS is "ready".
  • vinczemarton
    vinczemarton over 11 years
    That is true. If you want to get a callback, you can use getScript, and insert the contents inline.
  • David Hellsing
    David Hellsing over 11 years
    that is an option, but it’s still not reliable (depending on usage). Even if you know that the CSS file has loaded it doesn’t mean that it’s styles has been applied to the DOM.
  • vinczemarton
    vinczemarton over 11 years
    Keep in mind, that even getScript does not guarantee that the callback will be called after the script execution. For reference: api.jquery.com/jQuery.getScript I'm not sure if you have any way to tell if a style has been applied yet.
  • vinczemarton
    vinczemarton over 7 years
    Adding a <link> to the DOM is near instantaneous. Why wrap it in a deferred?
  • james2doyle
    james2doyle over 7 years
    @SoonDead it's to emulate the same API. Without the $.Deferred You could not use $.when at all.
  • vinczemarton
    vinczemarton over 7 years
    I still don't get why would you want to wrap it in a when. You are actually better off moving the $.getStylesheet line before the when and get the exact same result. After that you can take an other step to unwrap it from the deferred and still get the exact same result.
  • james2doyle
    james2doyle over 7 years
    @SoonDead Firstly, you don't have to use when, it is just an example of why you would want to use this technique. Say you want to make a request to 2 scripts and 2 stylesheets and you want to wait till all that is done, then do something else. This is an approach to do that in a clean and succinct way.
  • vinczemarton
    vinczemarton over 7 years
    Do note, that you don't complete your deferred when "all that is done". You complete your deferred when the link tag is added to the dom. This does not guarantee anything to be done.
  • AStopher
    AStopher about 2 years
    Relying on the browser to correct your code rather than doing it properly in the first place doesn't seem like good practice to me...