72

正直に言って、jQuery/jQuery-ui は重いダウンロードです。

Google では、最初のレンダリングを高速化するために、JavaScript の遅延読み込みを推奨しています。私のページでは、jQuery を使用して、ページの下部に配置されている (ほとんどが最初のビューの外にある) いくつかのタブを設定しており、ページがレンダリングされるまで jQuery を延期したいと考えています。

Google の遅延コードは、本文の onLoad イベントにフックすることで、ページの読み込み後に DOM にタグを追加します。

<script type="text/javascript">

 // Add a script element as a child of the body
 function downloadJSAtOnload() {
 var element = document.createElement("script");
 element.src = "deferredfunctions.js";
 document.body.appendChild(element);
 }

 // Check for browser support of event handling capability
 if (window.addEventListener)
 window.addEventListener("load", downloadJSAtOnload, false);
 else if (window.attachEvent)
 window.attachEvent("onload", downloadJSAtOnload);
 else window.onload = downloadJSAtOnload;

</script>

この方法で jQuery の読み込みを延期したいのですが、試してみると、jQuery コードが jQuery を見つけることができませんでした (私の側ではまったく予想外ではありませんでした)。

$(document).ready(function() {
    $("#tabs").tabs();
});

したがって、jQuery が読み込まれるまで jQuery コードの実行を延期する方法を見つける必要があるようです。追加されたタグの読み込みと解析が完了したことを検出するにはどうすればよいですか?

当然の結果として、非同期ロードにも答えが含まれている可能性があるようです。

何かご意見は?

4

17 に答える 17

54

これは、jQuerify ブックマークレットから少し前に編集したものです。jQueryをロードし、ロード後に実行するために頻繁に使用します。もちろん、そこにある URL を、カスタマイズした jquery への独自の URL に置き換えることができます。

(function() {
      function getScript(url,success){
        var script=document.createElement('script');
        script.src=url;
        var head=document.getElementsByTagName('head')[0],
            done=false;
        script.onload=script.onreadystatechange = function(){
          if ( !done && (!this.readyState || this.readyState == 'loaded' || this.readyState == 'complete') ) {
            done=true;
            success();
            script.onload = script.onreadystatechange = null;
            head.removeChild(script);
          }
        };
        head.appendChild(script);
      }
        getScript('http://ajax.googleapis.com/ajax/libs/jquery/1.5.2/jquery.min.js',function(){
            // YOUR CODE GOES HERE AND IS EXECUTED AFTER JQUERY LOADS
        });
    })();

jQuery と jQuery-UI を 1 つのファイルに実際に結合し、そのファイルへの URL を使用します。本当に別々にロードしたい場合は、getScripts を連鎖させてください:

getScript('http://myurltojquery.js',function(){
        getScript('http://myurltojqueryUI.js',function(){
              //your tab code here
        })
});
于 2011-05-02T04:03:17.163 に答える
14

これは重要な主題に関する最上位の質問であるため、@valmarv と @amparsand からの以前の回答に基づいて、これについて私自身の見解を提供することを大胆にさせてください.

多次元配列を使用してスクリプトをロードしています。それらの間に依存関係がないものをグループ化します。

var dfLoadStatus = 0;
var dfLoadFiles = [
      ["http://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js"],
      ["http://ajax.googleapis.com/ajax/libs/jqueryui/1.8.11/jquery-ui.min.js",
       "/js/somespecial.js",
       "/js/feedback-widget.js#2312195",
       "/js/nohover.js"]
     ];

function downloadJSAtOnload() {
    if (!dfLoadFiles.length) return;

    var dfGroup = dfLoadFiles.shift();
    dfLoadStatus = 0;

    for(var i = 0; i<dfGroup.length; i++) {
        dfLoadStatus++;
        var element = document.createElement('script');
        element.src = dfGroup[i];
        element.onload = element.onreadystatechange = function() {
        if ( ! this.readyState || 
               this.readyState == 'complete') {
            dfLoadStatus--;
            if (dfLoadStatus==0) downloadJSAtOnload();
        }
    };
    document.body.appendChild(element);
  }

}

if (window.addEventListener)
    window.addEventListener("load", downloadJSAtOnload, false);
else if (window.attachEvent)
    window.attachEvent("onload", downloadJSAtOnload);
else window.onload = downloadJSAtOnload;

ロードされた後、最初のjqueryをロードし、他のスクリプトを一度にロードし続けます。ページの任意の場所に配列を追加することで、スクリプトを簡単に追加できます。

dfLoadFiles.push(["/js/loadbeforeA.js"]);
dfLoadFiles.push(["/js/javascriptA.js", "/js/javascriptB.js"]);
dfLoadFiles.push(["/js/loadafterB.js"]);
于 2013-08-23T14:34:17.070 に答える
3
element.addEventListener("load", function () {
    $('#tabs').tabs()
}, false);

それを試してみてください。

于 2011-05-02T03:21:24.890 に答える
3

async/defered jquery スクリプト タグの後にこのコードを追加します。これは、すべての読み込みが完了したときに実行する必要があるものをすべて蓄積する一時関数 $ を定義します。関数を実行するために上書きされます。このコードでは、ドキュメントのさらに下にある jQuery onload 構文を変更する必要はありません。

<script defer async src="https://code.jquery.com/jquery-2.2.0.min.js">
<script>
    var executeLater = [];
    function $(func) {
        executeLater.push(func);
    }
    window.addEventListener('load', function () {
        $(function () {
            for (var c = 0; c < executeLater.length; c++) {
                executeLater[c]();
            }
        });
    })
</script>

....その後...

<script>
    $(function() {
        alert("loaded");
    });
</script>
于 2016-01-14T12:49:34.500 に答える
2

特定の状況では、jquery がロードされたときにイベントを発生させることができます。

<script type="text/javascript">
    (function (window) {

        window.jQueryHasLoaded = false;

        document.body.addEventListener('jqueryloaded', function (e) {
            console.log('jqueryloaded ' + new Date() );
        }, false);

        function appendScript(script) {
            var tagS = document.createElement("script"), 
                s = document.getElementsByTagName("script")[0];
            tagS.src = script.src;
            s.parentNode.insertBefore(tagS, s);

            if ( script.id == 'jquery' ) {
                tagS.addEventListener('load', function (e) {
                    window.jQueryHasLoaded = true;
                    var jQueryLoaded = new Event('jqueryloaded');
                    document.body.dispatchEvent(jQueryLoaded);
                }, false);
            }
        }

        var scripts = [
            {
                'id': 'jquery',
                'src': 'js/libs/jquery/jquery-2.0.3.min.js'
            },
            {
                'src': 'js/myscript1.js'
            },
            {
                'src': 'js/myscript2.js'
            }
        ];

        for (var i=0; i < scripts.length; i++) {
            appendScript(scripts[i]);
        }

    }(window));
</script>

次に、依存関係を関数でラップします。

// myscript1.js 
(function(){ 

    function initMyjQueryDependency() {
        console.log('my code is executed after jquery is loaded!');
        // here my code that depends on jquery
    }

    if ( jQueryHasLoaded === true )
        initMyjQueryDependency();
    else
        document.body.addEventListener('jqueryloaded', initMyjQueryDependency, false);

}());

jquery が他のスクリプトの後にロードを完了すると、jqueryloaded イベントが発生したときに依存関係が実行されます。

jquery がすでにロードされている場合jQueryHasLoaded === true、依存関係が実行されinitMyjQueryDependency()ます。

于 2013-11-19T11:43:13.680 に答える
2

jQuery と jQuery に依存するコードを HTML ファイルの最後に配置します。

編集:もう少し明確に

<html>
<head></head>
<body>
    <!-- Your normal content here -->
    <script type="text/javascript" src="http://path/to/jquery/jquery.min.js"></script>
    <script>//Put your jQuery code here</script>
</body>
</html>
于 2011-05-02T01:39:34.897 に答える
1

アンパサンドのコードに基づいて、スクリプトが次々に読み込まれるようにするためのチェーンをサポートする私のバージョンは次のとおりです。

var deferredJSFiles = ['jquery/jquery', 'file1', 'file2', 'file3'];
function downloadJSAtOnload() {
    if (!deferredJSFiles.length)
        return;
    var deferredJSFile = deferredJSFiles.shift();
    var element = document.createElement('script');
    element.src = deferredJSFile.indexOf('http') == 0 ? deferredJSFile : '/js/' + deferredJSFile + '.js';
    element.onload = element.onreadystatechange = function() {
        if (!this.readyState || this.readyState == 'loaded' || this.readyState == 'complete')
            downloadJSAtOnload();
    };
    document.body.appendChild(element);
}
if (window.addEventListener)
    window.addEventListener('load', downloadJSAtOnload, false);
else if (window.attachEvent)
    window.attachEvent('onload', downloadJSAtOnload);
else
    window.onload = downloadJSAtOnload;
于 2012-09-25T08:57:40.863 に答える
1

Modernizr.load() はここで言及する価値があると思います-依存関係の読み込みを非常にうまく処理します

于 2014-12-17T23:34:18.133 に答える
1

まあ、私には思えますが、あなたがしなければならないことは、a)ロード時に実行したいjQueryコードをjQueryファイルの最後に追加するか、b)次のdownloadJSAtOnloadように関数に追加することだけです:

<script type="text/javascript">

 // Add a script element as a child of the body
 function downloadJSAtOnload() {
 var element = document.createElement("script");
 element.src = "deferredfunctions.js";
 document.body.appendChild(element);
 $("#tabs").tabs(); // <==== NOTE THIS. This should theoretically run after the
                    // script has been appended, though you'll have to test this
                    // because I don't know if the JavaScript above will wait for
                    // the script to load before continuing
 }

 // Check for browser support of event handling capability
 if (window.addEventListener)
 window.addEventListener("load", downloadJSAtOnload, false);
 else if (window.attachEvent)
 window.attachEvent("onload", downloadJSAtOnload);
 else window.onload = downloadJSAtOnload;

</script>
于 2011-05-02T02:32:27.813 に答える
1

次のコードは、ウィンドウの読み込みが完了した後にスクリプトを読み込む必要があります。

<html>
<head>
    <script>
    var jQueryLoaded = false;
    function test() {
        var myScript = document.createElement('script');
        myScript.type = 'text/javascript';
        myScript.async = true;
        myScript.src = jQueryLoaded ? 'http://ajax.googleapis.com/ajax/libs/jquery/1.5.1/jquery.js' : 'http://ajax.googleapis.com/ajax/libs/jqueryui/1.8.11/jquery-ui.min.js';
        document.body.appendChild(myScript);

        if(!jQueryLoaded){
            alert('jquery was loaded');
            jQueryLoaded = true;
            test();
        } else {
            alert('jqueryui was loaded');   
        }
    }

    if (window.addEventListener){
        alert('window.addEventListener');
        window.addEventListener("load", test, false);
    } else if (window.attachEvent){
        alert('window.attachEvent');
        window.attachEvent("onload", test);
    } else{
        alert('window.onload');
        window.onload = test;
    }
    </script>
</head>
<body>
<p>Placeholder text goes here</p>
</body>
</html>

Chrome、FF、IE9で私のために働いた-それが役立つかどうか教えてください

于 2011-05-02T01:47:12.387 に答える
0

見てくださいjQuery.holdReady()

「jQueryのreadyイベントの実行を保留または解放します。」(jQuery 1.6以降)

http://api.jquery.com/jQuery.holdReady/

于 2011-05-29T19:55:31.067 に答える
0

必要なだけのようです<script defer>http://www.w3schools.com/tags/att_script_defer.asp

于 2011-05-02T03:10:24.517 に答える
-2

http://labjs.comを使用して html の最後にすべてのスクリプトをロードします。これは 100% のソリューションであり、gtmetrix ルールに対して何度もテストしました。例http://gtmetrix.com/reports/interactio.cz/jxomHSLV

于 2014-02-07T10:10:37.953 に答える