2017-09-29 22 views
1

我想懶加載一個css文件,然後讓所有css加載後javascript修改頁面。爲此,我使用this方法,如圖所示這裏:回調和延遲加載香草的css javascript

lazyLoadCSS = function (pathToStyleSheet, options, callback) { 
    var stylesheet = document.createElement('link'); 
    stylesheet.href = pathToStyleSheet; 
    stylesheet.rel = 'stylesheet'; 
    stylesheet.type = 'text/css'; 
    // temporarily set media to something inapplicable to ensure 
    // it'll fetch without blocking render 
    stylesheet.media = 'only x'; 
    // set the media back when the stylesheet loads 
    stylesheet.onload = function() { 
     stylesheet.media = 'all'; 

     // here be callbacks... 
     callback(); 
    }; 
    document.getElementsByTagName('head')[0].appendChild(stylesheet); 
}; 

所以,這個想法是,javascript中獲取的CSS,但走私它作爲「唯一的X」這樣的瀏覽器不認爲這在呈現頁面的其餘部分之前需要等待文件,這是整個觀點。這approach似乎是非常標準的,上面的代碼工作...主要。

唯一的問題是回調。它發生在CSS加載後,但在樣式應用到文檔之前。

如果我把一個計時器上的回調,像這樣:

window.setTimeout(function(){ 
    callback(); 
}, 2000); 

然後一切工作完全應該的方式(僅慢)。

問題是,我該如何等待不僅要加載CSS,還要在運行callback()之前應用?

+0

渲染後運行代碼的一種常見方式是調用沒有延遲值的setTimeout:setTimeout(()=> callback())。嘗試一下。如果它適合你的情況,那應該就足夠了。 – ideaboxer

+0

我正在傾向於這樣的東西,但它似乎有點......簡單的?太明顯了?很高興有人同意它會起作用。 – crowhill

+0

你可以把它想象成'onIdle'。即使AngularJS採用它(他們稱之爲'$ timeout'),它被用來模擬一個空閒的回調。例如在這裏:https://stackoverflow.com/questions/20610450/angularjs-timeout-without-delay-parameters-reason – ideaboxer

回答

0

按照上面的一些意見,這是我想出和它的工作很大(雖然它不是徹底的測試):

function waitForStylesToApply(cycleNumber, canary, callback){ 
    if(cycleNumber < 100){ 
     window.setTimeout(function(){ 
      var computedValue = window 
       .getComputedStyle(window.document.body, null) 
       .getPropertyValue('max-width'); 
      if(computedValue !== canary){ 
       if(typeof callback === 'function'){ 
        console.log('done in ' + cycleNumber + ' cycles'); 
        callback();            
       } 
      } 
      else { 
       waitForStylesToApply(cycleNumber++, canary, callback);       
      } 
     }, 10);  
    } 
} 

檢查在計算樣式<body>一遍又一遍,直到它變化。然後它進行回調。到目前爲止,代碼無需循環多次,因此等待時間無限小。

即使延遲10也太多了。代碼將延遲0,並且只能循環一次。

編輯:使用此功能代替上述示例中的簡單使用callback()