|
13 | 13 | // define on the loadCSS obj
|
14 | 14 | var rp = loadCSS.relpreload = {};
|
15 | 15 | // rel=preload feature support test
|
16 |
| - rp.support = function(){ |
| 16 | + // runs once and returns a function for compat purposes |
| 17 | + rp.support = (function(){ |
| 18 | + var ret; |
17 | 19 | try {
|
18 |
| - return w.document.createElement( "link" ).relList.supports( "preload" ); |
| 20 | + ret = w.document.createElement( "link" ).relList.supports( "preload" ); |
19 | 21 | } catch (e) {
|
20 |
| - return false; |
| 22 | + ret = false; |
21 | 23 | }
|
22 |
| - }; |
| 24 | + return function(){ |
| 25 | + return ret; |
| 26 | + }; |
| 27 | + })(); |
23 | 28 |
|
24 | 29 | // if preload isn't supported, get an asynchronous load by using a non-matching media attribute
|
25 | 30 | // then change that media back to its intended value on load
|
26 |
| - rp.bindMediaToggle = function( link, media ){ |
| 31 | + rp.bindMediaToggle = function( link ){ |
| 32 | + // remember existing media attr for ultimate state, or default to 'all' |
| 33 | + var finalMedia = link.media || "all"; |
| 34 | + |
27 | 35 | function enableStylesheet(){
|
28 |
| - link.media = media; |
| 36 | + link.media = finalMedia; |
29 | 37 | }
|
| 38 | + |
| 39 | + // bind load handlers to enable media |
30 | 40 | if( link.addEventListener ){
|
31 | 41 | link.addEventListener( "load", enableStylesheet );
|
32 | 42 | } else if( link.attachEvent ){
|
33 | 43 | link.attachEvent( "onload", enableStylesheet );
|
34 | 44 | }
|
| 45 | + |
| 46 | + // Set rel and non-applicable media type to start an async request |
| 47 | + // note: timeout allows this to happen async to let rendering continue in IE |
| 48 | + setTimeout(function(){ |
| 49 | + link.rel = "stylesheet"; |
| 50 | + link.media = "only x"; |
| 51 | + }); |
35 | 52 | // also enable media after 3 seconds,
|
36 | 53 | // which will catch very old browsers (android 2.x, old firefox) that don't support onload on link
|
37 | 54 | setTimeout( enableStylesheet, 3000 );
|
38 | 55 | };
|
39 | 56 |
|
40 | 57 | // loop through link elements in DOM
|
41 | 58 | rp.poly = function(){
|
| 59 | + // double check this to prevent external calls from running |
42 | 60 | if( rp.support() ){
|
43 | 61 | return;
|
44 | 62 | }
|
|
47 | 65 | var link = links[ i ];
|
48 | 66 | // qualify links to those with rel=preload and as=style attrs
|
49 | 67 | if( link.rel === "preload" && link.getAttribute( "as" ) === "style" && !link.getAttribute( "data-loadcss" ) ){
|
50 |
| - // remember existing media attr for ultimate state, or default to 'all' |
51 |
| - var finalMedia = link.media || "all"; |
52 |
| - // bind listeners to toggle media back |
53 |
| - rp.bindMediaToggle( link, finalMedia ); |
54 |
| - // if preload is not supported, kick off an asynchronous request by using a non-matching media query and rel=stylesheet |
55 |
| - link.media = "x"; |
56 |
| - link.rel = "stylesheet"; |
57 |
| - |
58 | 68 | // prevent rerunning on link
|
59 | 69 | link.setAttribute( "data-loadcss", true );
|
| 70 | + // bind listeners to toggle media back |
| 71 | + rp.bindMediaToggle( link ); |
60 | 72 | }
|
61 | 73 | }
|
| 74 | + }; |
| 75 | + |
| 76 | + // if unsupported, run the polyfill |
| 77 | + if( !rp.support() ){ |
| 78 | + // run once at least |
| 79 | + rp.poly(); |
| 80 | + |
62 | 81 | // rerun poly on an interval until onload
|
63 |
| - var run = w.setInterval( rp.poly, 300 ); |
| 82 | + var run = w.setInterval( rp.poly, 500 ); |
64 | 83 | if( w.addEventListener ){
|
65 | 84 | w.addEventListener( "load", function(){
|
66 | 85 | rp.poly();
|
|
72 | 91 | w.clearInterval( run );
|
73 | 92 | } );
|
74 | 93 | }
|
75 |
| - }; |
76 |
| - // run once at least |
77 |
| - rp.poly(); |
| 94 | + } |
| 95 | + |
| 96 | + |
78 | 97 | // commonjs
|
79 | 98 | if( typeof exports !== "undefined" ){
|
80 | 99 | exports.loadCSS = loadCSS;
|
|
0 commit comments