Web動態(tài)加載JS外部文件(script標(biāo)簽)

( 摘自高性能Javascript )
文檔對象模型(DOM)允許你使用JavaScript 動態(tài)創(chuàng)建HTML的幾乎全部文檔內(nèi)容。其根本在于,<script>元素與頁面其他元素沒有什么不同:引用變量可以通過DOM進(jìn)行檢索,可以從文檔中移動、刪除,也可以被創(chuàng)建.

var script = document.createElement("script");
script.type = "text/javascript";
script.src = "file1.js";
document.getElementsByTagName_r("head")[0].appendChild(script);

新的<script>元素加載file1.js源文件。此文件當(dāng)元素添加到頁面之后立刻開始下載。此技術(shù)的重點在于:無論在何處啟動下載,文件的下載和運(yùn)行都不會阻塞其他頁面處理過程。你甚至可以將這些代碼放在<head>部分而不會對其余部分的頁面代碼造成影響(除了用于下載文件的HTTP 連接)。

當(dāng)文件使用動態(tài)腳本節(jié)點下載時,返回的代碼通常立即執(zhí)行(除了Firefox和Opera,他們將等待此前的所有動態(tài)腳本節(jié)點執(zhí)行完畢)。當(dāng)腳本是“自運(yùn)行”類型時這一機(jī)制運(yùn)行正常,但是如果腳本只包含供頁面其他腳本調(diào)用調(diào)用的接口,則會帶來問題。這種情況下,你需要跟蹤腳本下載完成并準(zhǔn)備妥善的情況??梢允褂脛討B(tài)<script>節(jié)點發(fā)出事件得到相關(guān)信息。

Firefox, Opera, Chorme, IE11+ 和Safari3+會在<script>節(jié)點接收完成之后發(fā)出一個load 事件。你可以監(jiān)聽這一事件,以得到腳本準(zhǔn)備好的通知:

var script = document.createElement("script")
script.type = "text/javascript";
//Firefox, Opera, Chrome, Safari 3+
script.onload = function(){
    alert("Script loaded!");
};
script.src = "file1.js";
document.getElementsByTagName_r("head")[0].appendChild(script);

Internet Explorer(IE10及以下版本)支持另一種實現(xiàn)方式,它發(fā)出一個readystatechange事件。<script>元素有一個readyState屬性,它的值隨著下載外部文件的過程而改變。readyState 有五種取值:

  • uninitialized: 默認(rèn)狀態(tài)
  • loading: 下載開始
  • loaded: 下載完成
  • interactive: 下載完成但尚不可用
  • complete: 所有數(shù)據(jù)已經(jīng)準(zhǔn)備好

微軟文檔上說,在<script>元素的生命周期中,readyState 的這些取值不一定全部出現(xiàn),但并沒有指出哪些取值總會被用到。實踐中,我們最感興趣的是“l(fā)oaded”和“complete”狀態(tài)。Internet Explorer 對這兩個readyState值所表示的最終狀態(tài)并不一致,有時<script>元素會得到“l(fā)oader”卻從不出現(xiàn)“complete”,但另外一些情況下出現(xiàn)“complete”而用不到“l(fā)oaded”。最安全的辦法就是在readystatechange 事件中檢查這兩種狀態(tài),并且當(dāng)其中一種狀態(tài)出現(xiàn)時,刪除readystatechange事件句柄(保證事件不會被處理兩次):

var script = document.createElement("script")
script.type = "text/javascript";
//Internet Explorer
script.onreadystatechange = function(){
    if (script.readyState == "loaded" || script.readyState == "complete"){
        script.onreadystatechange = null;
        alert("Script loaded.");
    }
};
script.src = "file1.js";
document.getElementsByTagName_r("head")[0].appendChild(script);

大多數(shù)情況下,你希望調(diào)用一個函數(shù)就可以實現(xiàn)JavaScript 文件的動態(tài)加載。下面的函數(shù)封裝了標(biāo)準(zhǔn)實現(xiàn)和IE 實現(xiàn)所需的功能:

function loadScript(url, callback){
    var script = document.createElement ("script")
    script.type = "text/javascript";
    if (script.readyState){ //IE
        script.onreadystatechange = function(){
            if (script.readyState == "loaded" || script.readyState == "complete"){
                script.onreadystatechange = null;
                callback();
            }
        };
    } else { //Others
        script.onload = function(){
            callback();
        };
    }
    script.src = url;
    document.getElementsByTagName_r("head")[0].appendChild(script);
}
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容