【问题标题】:Loading order for script inside body and using jquery ready在正文中加载脚本的顺序并准备好使用jquery
【发布时间】:2014-02-22 04:22:37
【问题描述】:

我在 body 标签中有一个脚本。问题是一些代码在完成之前被加载,即使它位于文档就绪块中。就绪块中的代码不应该等待脚本标签中的代码完成吗?或者它只是推迟到脚本标签被渲染但不执行?

<html>
<head>
  <script data-main="script.js" src="/assets/js/require.js"></script>
</head>
<body>
  <script type="text/javascript">
    var foo = ${fromServer};

  </script>
</body>
</html>

script.js: 我希望这会等到脚本完成...

$(function() {
  // access script var from here, not set yet hmmmm
});

我很想知道这里发生了什么...

更新:

好的,这里是页面中的变量

  require.config({
        baseUrl: '/assets/js/app',
        shim: {
            d3: {
                exports: 'd3'
            },
            underscore: {
                exports: '_',
            },
            backbone: {
                deps: ['underscore', 'jquery'],
                exports: 'Backbone'
            },
            uidate: {
                deps: ['jquery']
            }
        },
        paths: {
            d3: '../lib/d3.v3',
            jquery: '../lib/jquery-2.0.3.min',
            underscore: '../lib/underscore',
            backbone: '../lib/backbone'

        }
    });

require([...], function(...) {
  //console.log here and foo is set and good to go
  var myCollection = new MyCollection(foo);

在 MyCollection 中:

// define(.... {
// var coll = Backbone.Collection.extend({

initialize: function() {
  console.log(this);
}

看着我看到的控制台:

 {length: 0, models: Array[0], _byId: Object, constructor: function, model: function…}

当我在 Chrome 控制台中展开对象时,实际上那里有模型......奇怪。如果我在 init 和 console.log(this) 中再次执行 setTimeout,则模型已设置。初始化模型的这种延迟来自哪里?

我也试过只加载一个数组,如:

var someColl = new MyCollection([ { ... }, { ... } ]);

这里也有同样的问题。

更新:我试图缩小问题的范围,console.log 在这里打印一个空数组

var testing = [{x:1,d:2},{x:3,d:8},{x:3,d:98}];
var myCollection = Backbone.Collection.extend({
    initialize: function() {
        console.log(JSON.stringify(this));
    }
});
var x = new myCollection(testing);

【问题讨论】:

  • 这可以帮助您了解document.ready何时执行stackoverflow.com/questions/3698200/…
  • MyCollection 对象的创建过程中发生了什么?里面有异步代码吗?此外,console.log(object) 可能会欺骗您,因为某些浏览器(如 Chrome)不会在您执行console.log(obj) 的确切时刻复制数据,因此实际日志可能不会在console.log() 的时刻显示正确的数据陈述。如果您 console.log() 一个实际值(例如字符串或数字),它不会说谎,或者您可以使用 console.log(JSON.stringify(object)) 将其全部转换为字符串,然后它也不会说谎。
  • 另外,您从哪个库获得$(function() {})?我假设是 jQuery,但看起来你可能正在使用其他东西。
  • 好吧,看来这与我的问题有关:stackoverflow.com/questions/9354932/…
  • 集合中没有异步代码,只是初始化和console.log(this)

标签: javascript backbone.js browser requirejs


【解决方案1】:

jQuery ready 在调用回调之前等待 DOM 完成加载。这大致相当于&lt;/body&gt; 标记被解析并且它前面的所有内容(包括任何脚本)都已经被解析。未标记为deferasync 的脚本将已经运行。

您的问题并不完全清楚您的问题到底是什么,但 jQuery 就绪块内的代码将在 &lt;head&gt;&lt;body&gt; 中的其他脚本执行后执行。

如果您使用 require.js 库异步加载脚本,则这些脚本可能会在文档准备好之前或之后加载,具体取决于文档加载中发生的其他情况。如果您需要协调这些脚本的异步加载时间,那么您必须使用 require.js 库中的功能才能知道这些脚本何时加载或在这些脚本中使用 document.ready 以确保它们等待用于解析文档的其余部分。

【讨论】:

  • 我的问题是,当从文档就绪回调访问时,脚本标签(正文内部)中的变量为空。我在回调中使用了 setTimeout,1 秒后设置了变量。所以看起来文档就绪回调不会等待 javascript 加载到正文中。
  • @amiawizard - 请显示您遇到问题的实际代码/结构。 jQuery ready 会等待内联 &lt;script&gt; 标签而不执行 defer 或 async 属性。
  • 在您的第 3 段中,如果 requirejs 加载的代码是在文档准备好后加载的,那么此时不应该设置正文脚本中的变量吗?
  • require.js 加载的代码没有保证加载顺序。它可能在 jquery 准备好之前或之后运行,事实上,可能会不时变化。
  • 嗯,是否可以将服务器端语言中的变量加载到 requirejs 脚本中?
猜你喜欢
  • 2018-08-02
  • 1970-01-01
  • 2015-05-17
  • 1970-01-01
  • 2019-01-23
  • 1970-01-01
  • 2015-07-12
  • 2021-02-22
  • 1970-01-01
相关资源
最近更新 更多