Javascript文件加載:LABjs和RequireJS

作者: 阮一峰  發布時間: 2011-10-03 20:30  閱讀: 2264 次  推薦: 0   原文鏈接   [收藏]  

  傳統上,加載 Javascript 文件都是使用<script>標簽。

  就像下面這樣:

<script type="text/javascript" src="example.js"></script>

  <script>標簽很方便,只要加入網頁,瀏覽器就會讀取并運行。但是,它存在一些嚴重的缺陷。

  (1)嚴格的讀取順序。由于瀏覽器按照<script>在網頁中出現的順序,讀取 Javascript 文件,然后立即運行,導致在多個文件互相依賴的情況下,依賴性最小的文件必須放在最前面,依賴性最大的文件必須放在最后面,否則代碼會報錯。

  (2)性能問題。瀏覽器采用"同步模式"加載<script>標簽,也就是說,頁面會"堵塞"(blocking),等待 javascript 文件加載完成,然后再運行后面的 HTML 代碼。當存在多個<script>標簽時,瀏覽器無法同時讀取,必須讀取完一個再去讀取另一個,造成讀取時間大大延長,頁面響應緩慢。

  為了解決這些問題,可以使用 DOM 方法,動態加載 Javascript 文件。

function loadScript (url){
    var script = document.createElement ("script");
    script.type = "text/javascript";
    script.src = url;
    document.body.appendChild (script);
}

  這樣做的原理是,瀏覽器即時創造出一個<script>標簽,然后"異步"讀取 Javascript 文件。這樣不會造成頁面堵塞,但會造成另外一個問題:這樣加載的 Javascript 文件,不在原始的 DOM 結構之中,因此在 DOM-ready(DOMContentLoaded)事件和 window.onload 事件中指定的回調函數對它無效。

  外部函數庫 LABjsRequireJS,可以幫助我們更有效地管理 Javascript 加載。

  下面根據 ScriptJunkie的文章,舉一個最簡單的例子,來說明這兩個函數庫的基本用法。更高級的用法,請參閱它們的文檔。

<script src="script1.js"></script>
<script src="script2-a.js"></script>
<script src="script2-b.js"></script>
<script type="text/javascript">
    initScript1 ();
    initScript2 ();
</script>
<script src="script3.js"></script>
<script type="text/javascript">
    initScript3 ();
</script>

  上面這段代碼,將依次加載 4 個 javascript 文件:script1.js、script2-a.js、script2-b.js 和 script3.js。在加載完前三個文件后,運行兩個函數 initScript1 ()和 initScript2 ();加載完第四個文件后,再運行函數 initScript3 ()。

  下面,用 LABjs 對其進行改寫:

<script src="LAB.js"></script>
<script type="text/javascript">
    $LAB
    .script ("script1.js") .wait ()
    .script ("script2-a.js")
    .script ("script2-b.js")
    .wait (function (){
    initScript1 ();
    initScript2 ();
    })
    .script ("script3.js")
    .wait (function (){
    initScript3 ();
    });
</script>

  首先,$LAB 對象替代了<script>標簽,然后 .script ()方法表示加載 Javascript 文件,不帶參數的 .wait () 方法表示立即運行剛才加載的 Javascript 文件,帶參數的 .wait ()方法也是立即運行剛才加載的 Javascript 文件,但是還運行參數中指定的函數。

  這里需要注意的是,可以同時運行多條 $LAB 鏈,但是它們之間是完全獨立的,不存在次序關系。如果你要確保一個 Javascript 文件在另一個文件之后運行,你只能把它們寫在同一個鏈操作之中。只有當某些腳本是完全無關的時候,你才應該考慮把它們分成不同的 $LAB 鏈,表示它們之間不存在相關關系。

  接下來是 requireJS 的改寫:

<script src="require.js"></script>
<script type="text/javascript">
    require ([
    "script1.js",
    "script2-a.js",
    "script2-b.js",
    "script3.js"
    ],
    function (){
        initScript1 ();
        initScript2 ();
        initScript3 ();
        }
    );
</script>

  require ()接受兩個參數,第一個數組表示所要加載的 Javascript 文件,第二個是加載完成后所要運行的回調函數。原生的 require () 不支持按次序加載,所以四個 Javascript 文件到底先加載哪個,無法事前知道,require ()只保證這四個文件全部加載完成之后,才會運行所指定的回調函數。

  如果按次序加載對你很重要,你可以使用官方提供的 order 插件

0
0
 
標簽:Javascript
 
 

文章列表

arrow
arrow
    全站熱搜
    創作者介紹
    創作者 大師兄 的頭像
    大師兄

    IT工程師數位筆記本

    大師兄 發表在 痞客邦 留言(0) 人氣()