3

I have cobbled together a script from different sources, that helps me to put some fallbacks in place when a stylesheet fails to load (specifically for me, Pictos server is not always reliable).

This works great, but fails on Firefox for some reason, it doesn't process anything within the if statement. I've tried running it through JSHint and nothing serious is coming up.

Any ideas?

$(document).ready(function(){
    $.each(document.styleSheets, function(i,sheet){
      if(sheet.href==='http://get.pictos.cc/fonts/357/9') {
        var rules = sheet.rules ? sheet.rules : sheet.cssRules; // Assign the stylesheet rules to a variable for testing

        $('body').addClass('pictos-working');
        $('.pictos-fallback').hide(); // Hide fallbacks

        // If the stylesheet fails to load...
        if (rules.length === 0) {
            $('.pictos').hide(); // Hide Pictos tags so we don't get random letters
            $('body').removeClass('pictos-working'); // Remove 'working' class
            $('.pictos-fallback').show(); // Show fallbacks
        }
     }
    });
});​
SparrwHawk
  • 13,581
  • 22
  • 61
  • 91

2 Answers2

5

Your style sheet detection method is not reliable. cssRules is null when the style sheet originates from a different domain, because of the Same origin policy.

Instead of detecting the existence of a css rule through the cssRules object, check if a rule from the style sheet is being applied:

if ($('selector').css('property') === 'expectedvalue') {
    // Loaded
} else {
    // Not loaded.
}
Rob W
  • 341,306
  • 83
  • 791
  • 678
  • Hmm the problem is that I don't really have any control over that - here is what Pictos generates - http://pastebin.com/zJsC47qt – SparrwHawk Jul 01 '12 at 15:08
  • I tried $(document).ready(function(){ if ($('@font-face').css('font-family') === 'Pictos Custom') { alert("loaded") } else { alert("not loaded") } }); but that didn't seem to work, any suggestions? – SparrwHawk Jul 01 '12 at 15:08
  • @SparrwHawk @font-face is not a valid jQuery **selector**. Since your style sheet only contains a `@font-face` rule, your only remaining detection method is to measure the size of a rendered font. Have a look at the source code of font-face feature detection methods, such as the ones from [this answer](http://stackoverflow.com/questions/10339268/is-there-a-way-to-detect-whether-a-users-browser-is-supporting-font-face). The idea is: 1. Get the current dimensions. 2. Set the new font family. 3. Check if the dimensions have changed. – Rob W Jul 01 '12 at 15:18
0

Just some suggestions for improvement that might help:

why a nested if? since you only have two scenarios, use if then else.. are you sure that cssRules is zero when the file doesn't load? maybe there are some headers or metadata that load.. Where did you find this property?

something I just found: http://www.quirksmode.org/dom/w3c_css.html

George Katsanos
  • 13,524
  • 16
  • 62
  • 98
  • 1
    I can't see any possible way to refactor the nested `if` statement into an `if else` statement, considering the second `if` is dependent on the first condition having evaluated to true. – Anthony Grist Jul 01 '12 at 14:51
  • Yes, Anthony is right, I can't see a way around it. Still can't see a way to solve this issue :-/ – SparrwHawk Jul 01 '12 at 15:50