requirejs 加载脚本进度

标签 requirejs

冒着问一个愚蠢的问题的风险,我会尝试一下。

RequireJs 加载依赖项时是否可以显示进度指示器?

例如:

require(['jquery'], function($) {

    // Well, jQuery loaded in quite some time due to a low-speed connection
    //
    // Or maybe I wanted to show an overlay to prevent user of clicking on UI widgets until the load is complete
});

如果有一些插件没有出现在我的 Google 搜索中,我不想开始修改 RequireJS 源代码。

感谢你的帮助。

最佳答案

可以显示微调器或进度指示器,但不能显示栏本身。我可以获得 requirejs 的状态(当前正在加载或空闲),但不能获得已加载/需要加载模块的百分比,因为它们的依赖项在每个模块加载时解析,但不是在开始时解析。

但是,无论如何,至少有一个简单的微调器的页面比在用户等待时只是空白页面要好得多。

无需更改 requirejs!所以..

假设我们有文件 require.conf.js

require.config({...})
require(["app"], function () { 

// main entry point to your hugde app's code 
});

它是由 html 加载的
<script data-main="require.conf" type="text/javascript" src="bower_components/requirejs/require.js"></script>

这是标准的 requirejs 场景。让我们将指标添加到
<div id="requirejs-loading-panel">
    <div id="requirejs-loading-status"></div>
    <div id="requirejs-loading-module-name"></div>
</div>

好的,让我们 catch requirejs 的名为 require.onResourceLoad 的函数并做所有需要的魔法。它会在每个模块加载时被 requirejs 调用,将 requirejs 的上下文传递给 dep 树和所有其他人员。我们将使用上下文来确定 requirejs 是否正在加载某些内容。我是在预定的计时器调用中完成的,因为 onResourceLoad() 仅在加载时调用,而不是在加载完成时调用。这段代码需要添加到require.js.conf中:
require.onResourceLoad = function (context, map, depMaps) {


    var loadingStatusEl = document.getElementById('requirejs-loading-status'),
        loadingModuleNameEl = document.getElementById('requirejs-loading-module-name');
    var panel = document.getElementById('requirejs-loading-panel');

    if (loadingStatusEl && loadingModuleNameEl) {


        if (!context) { // we well call onResourceLoad(false) by ourselves when requirejs is not loading anything => hide the indicator and exit

            panel.style.display = "none";
            return;
        }

        panel.style.display = ""; // show indicator when any module is loaded and shedule requirejs status (loading/idle) check
        clearTimeout(panel.ttimer); 
        panel.ttimer = setTimeout(function () {


            var context = require.s.contexts._;
            var inited = true;
            for (name in context.registry) {
                var m = context.registry[name];

                if (m.inited !== true) {
                    inited = false;
                    break;
                }

            } // here the "inited" variable will be true, if requirejs is "idle", false if "loading"

            if (inited) {
                require.onResourceLoad(false);  // will fire if module loads in 400ms. TODO: reset this timer for slow module loading
            }

        }, 400)
        if (map && map.name) { // we will add one dot ('.') and a currently loaded module name to the indicator

            loadingStatusEl.innerHTML = loadingStatusEl.innerHTML += '.'; //add one more dot character
            loadingModuleNameEl.innerHTML = map.name + (map.url ? ' at ' + map.url : '');
        }
    } else {


    }


};

一个问题是:我们无法以某种方式弄清楚需要加载多少模块,因此我们无法计算加载进度的实际百分比。但是,至少,我们可以找出我们是否正在加载某些内容(并且事件获取当前正在加载的模块名称)并将其显示给紧张的用户

关于requirejs 加载脚本进度,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15581563/

相关文章:

javascript - 使用 TimelineJS 和 AMD

javascript - Squire 正在打破其他测试

javascript - 如何绕过 RequireJS 加载全局模块?

javascript - 带有完美滚动条 jQuery 插件的 Requirejs

javascript - 使用 RequireJS 和 JSDoc3 记录 Marionette 模块

requirejs - AMD 结构化网络应用程序中的 Mixpanel 2.2 - 例如需要.js

全局使用模块的一个实例的 JavaScript 最佳实践

javascript - 在不明确要求 Assets 的情况下将 webpack 与 jade-loader 一起使用

javascript - 为什么我们必须在 require.js 中加载 data-main 两次?

backbone.js - Backbone/RequireJS 模型数据存储