动态加载JavaScript文件

时间:2008-08-21 21:59:31

标签: javascript file import include

如何可靠地动态加载JavaScript文件?这将用于实现一个模块或组件,当'初始化'时,组件将根据需要动态加载所有需要的JavaScript库脚本。

使用该组件的客户端不需要将实现此组件的所有库脚本文件(并手动插入<script>标签)加载到其网页中 - 只需加载'主'组件脚本文件。 / p>

主流JavaScript库如何实现这一目标(Prototype,jQuery等)?这些工具是否将多个JavaScript文件合并为一个可再发行的'build'版本的脚本文件?或者他们是否动态加载辅助“库”脚本?

此问题的补充:是否有一种方法可以在加载动态包含的JavaScript文件后处理事件? Prototype对于文档范围的事件有document.observe。例如:

document.observe("dom:loaded", function() {
  // initially hide all containers for tab content
  $$('div.tabcontent').invoke('hide');
});

脚本元素有哪些可用事件?

27 个答案:

答案 0 :(得分:73)

您可以编写动态脚本标记(使用Prototype):

new Element("script", {src: "myBigCodeLibrary.js", type: "text/javascript"});

这里的问题是,当外部脚本文件完全加载时,我们不知道

我们经常希望我们的相关代码在下一行,并喜欢写一些类似的东西:

if (iNeedSomeMore) {
    Script.load("myBigCodeLibrary.js"); // includes code for myFancyMethod();
    myFancyMethod(); // cool, no need for callbacks!
}

有一种智能方法可以在不需要回调的情况下注入脚本依赖项。您只需通过同步AJAX请求来提取脚本,并在全局级别上评估脚本。

如果使用Prototype,则Script.load方法如下所示:

var Script = {
    _loadedScripts: [],
    include: function(script) {
        // include script only once
        if (this._loadedScripts.include(script)) {
            return false;
        }
        // request file synchronous
        var code = new Ajax.Request(script, {
            asynchronous: false,
            method: "GET",
            evalJS: false,
            evalJSON: false
        }).transport.responseText;
        // eval code on global level
        if (Prototype.Browser.IE) {
            window.execScript(code);
        } else if (Prototype.Browser.WebKit) {
            $$("head").first().insert(Object.extend(
                new Element("script", {
                    type: "text/javascript"
                }), {
                    text: code
                }
            ));
        } else {
            window.eval(code);
        }
        // remember included script
        this._loadedScripts.push(script);
    }
};

答案 1 :(得分:54)

javascript中没有import / include / require,但有两种主要方法可以达到你想要的效果:

1 - 您可以使用AJAX调用加载它,然后使用eval。

这是最简单的方法,但由于Javascript安全设置,它仅限于您的域名,并且使用eval可以打开错误和黑客的大门。

2 - 在HTML中添加带脚本URL的脚本标记。

绝对是最好的方式。您甚至可以从外部服务器加载脚本,并且在使用浏览器解析器评估代码时它是干净的。您可以将标签放在网页的头部或身体的底部。

这里讨论和说明了这两种解决方案。

现在,您必须了解一个大问题。这样做意味着您远程加载代码。现代Web浏览器将加载文件并继续执行当前脚本,因为它们异步加载所有内容以提高性能。

这意味着如果您直接使用这些技巧,在您要求加载后,您将无法在下一行使用新加载的代码,因为它仍将加载。

E.G:my_lovely_script.js包含MySuperObject

var js = document.createElement("script");

js.type = "text/javascript";
js.src = jsFilePath;

document.body.appendChild(js);

var s = new MySuperObject();

Error : MySuperObject is undefined

然后你重新加载点击F5的页面。它的工作原理!混乱...

那该怎么办呢?

好吧,你可以在我给你的链接中使用作者建议的黑客。总之,对于匆忙的人,他在加载脚本时使用en事件来运行回调函数。因此,您可以使用远程库将所有代码放在回调函数中。 E.G:

function loadScript(url, callback)
{
    // adding the script tag to the head as suggested before
   var head = document.getElementsByTagName('head')[0];
   var script = document.createElement('script');
   script.type = 'text/javascript';
   script.src = url;

   // then bind the event to the callback function 
   // there are several events for cross browser compatibility
   script.onreadystatechange = callback;
   script.onload = callback;

   // fire the loading
   head.appendChild(script);
}

然后在lambda函数中加载脚本后编写要使用的代码:

var myPrettyCode = function() {
    // here, do what ever you want
};

然后你运行所有:

loadScript("my_lovely_script.js", myPrettyCode);

好的,我明白了。但写这些东西真是太痛苦了。

那么,在这种情况下,你可以像往常一样使用梦幻般的免费jQuery框架,它可以让你在一行中做同样的事情:

$.getScript("my_lovely_script.js", function() {
    alert("Script loaded and executed.");
    // here you can use anything you defined in the loaded script
});

答案 2 :(得分:25)

我使用much less complicated version recentlyjQuery

<script src="scripts/jquery.js"></script>
<script>
  var js = ["scripts/jquery.dimensions.js", "scripts/shadedborder.js", "scripts/jqmodal.js", "scripts/main.js"];
  var $head = $("head");
  for (var i = 0; i < js.length; i++) {
    $head.append("<script src=\"" + js[i] + "\"></scr" + "ipt>");
  }
</script>

它在我测试过的每个浏览器中都运行良好:IE6 / 7,Firefox,Safari,Opera。

更新: jQuery-less版本:

<script>
  var js = ["scripts/jquery.dimensions.js", "scripts/shadedborder.js", "scripts/jqmodal.js", "scripts/main.js"];
  for (var i = 0, l = js.length; i < l; i++) {
    document.getElementsByTagName("head")[0].innerHTML += ("<script src=\"" + js[i] + "\"></scr" + "ipt>");
  }
</script>

答案 3 :(得分:19)

我做的基本上和你做的亚当一样,但稍加修改以确保我附加到head标签来完成工作。我只是创建了一个include函数(下面的代码)来处理脚本和css文件。

此函数还会检查以确保尚未动态加载脚本或CSS文件。它不会检查手动编码值,并且可能有更好的方法可以做到这一点,但它可以达到目的。

function include( url, type ){
    // First make sure it hasn't been loaded by something else.
    if( Array.contains( includedFile, url ) )
        return;

    // Determine the MIME-type
    var jsExpr = new RegExp( "js$", "i" );
    var cssExpr = new RegExp( "css$", "i" );
    if( type == null )
        if( jsExpr.test( url ) )
            type = 'text/javascript';
        else if( cssExpr.test( url ) )
            type = 'text/css';

    // Create the appropriate element.
    var tag = null;
    switch( type ){
        case 'text/javascript' :
            tag = document.createElement( 'script' );
            tag.type = type;
            tag.src = url;
            break;
        case 'text/css' :
            tag = document.createElement( 'link' );
            tag.rel = 'stylesheet';
            tag.type = type;
            tag.href = url;
            break;
    }

    // Insert it to the <head> and the array to ensure it is not
    // loaded again.
    document.getElementsByTagName("head")[0].appendChild( tag );
    Array.add( includedFile, url );
}

答案 4 :(得分:14)

另一个很棒的答案

$.getScript("my_lovely_script.js", function(){


   alert("Script loaded and executed.");
  // here you can use anything you defined in the loaded script

 });

https://stackoverflow.com/a/950146/671046

答案 5 :(得分:8)

以下是我发现的一些示例代码......有没有人有更好的方法?

  function include(url)
  {
    var s = document.createElement("script");
    s.setAttribute("type", "text/javascript");
    s.setAttribute("src", url);
    var nodes = document.getElementsByTagName("*");
    var node = nodes[nodes.length -1].parentNode;
    node.appendChild(s);
  }

答案 6 :(得分:6)

如果您已经加载了jQuery,则应使用$.getScript

这比其他答案更有优势,因为你有一个内置的回调函数(以保证在依赖代码运行之前加载脚本),你可以控制缓存。

答案 7 :(得分:3)

  

有没有人有更好的方法?

我认为将脚本添加到正文会更容易,然后将其添加到页面的最后一个节点。怎么样:

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

答案 8 :(得分:3)

我已经使用了另一种我在网上找到的解决方案......这个解决方案属于creativecommons,并且会在调用函数之前检查源是否包含 ...

您可以在此处找到该文件:include.js

/** include - including .js files from JS - bfults@gmail.com - 2005-02-09
 ** Code licensed under Creative Commons Attribution-ShareAlike License 
 ** http://creativecommons.org/licenses/by-sa/2.0/
 **/              
var hIncludes = null;
function include(sURI)
{   
  if (document.getElementsByTagName)
  {   
    if (!hIncludes)
    {
      hIncludes = {}; 
      var cScripts = document.getElementsByTagName("script");
      for (var i=0,len=cScripts.length; i < len; i++)
        if (cScripts[i].src) hIncludes[cScripts[i].src] = true;
    }
    if (!hIncludes[sURI])
    {
      var oNew = document.createElement("script");
      oNew.type = "text/javascript";
      oNew.src = sURI;
      hIncludes[sURI]=true;
      document.getElementsByTagName("head")[0].appendChild(oNew);
    }
  }   
} 

答案 9 :(得分:3)

刚刚发现了YUI 3中的一个很棒的功能(在预览版中可用时)。您可以轻松地将依赖项插入YUI库和“外部”模块(您正在寻找的内容),而无需太多代码:YUI Loader

它还会在加载外部模块后立即回答有关正在调用的函数的第二个问题。

示例:

YUI({
    modules: {
        'simple': {
            fullpath: "http://example.com/public/js/simple.js"
        },
        'complicated': {
            fullpath: "http://example.com/public/js/complicated.js"
            requires: ['simple']  // <-- dependency to 'simple' module
        }
    },
    timeout: 10000
}).use('complicated', function(Y, result) {
    // called as soon as 'complicated' is loaded
    if (!result.success) {
        // loading failed, or timeout
        handleError(result.msg);
    } else {
        // call a function that needs 'complicated'
        doSomethingComplicated(...);
    }
});

完美地为我工作,并具有管理依赖关系的优势。有关example with YUI 2 calendar的信息,请参阅YUI文档。

答案 10 :(得分:3)

如果要加载 SYNC 脚本,则需要将脚本文本直接添加到HTML HEAD标记。添加它将触发 ASYNC 加载。要同步从外部文件加载脚本文本,请使用XHR。下面是一个快速示例(它正在使用此帖和其他帖子中的其他部分答案):

/*sample requires an additional method for array prototype:*/

if (Array.prototype.contains === undefined) {
Array.prototype.contains = function (obj) {
    var i = this.length;
    while (i--) { if (this[i] === obj) return true; }
    return false;
};
};

/*define object that will wrap our logic*/
var ScriptLoader = {
LoadedFiles: [],

LoadFile: function (url) {
    var self = this;
    if (this.LoadedFiles.contains(url)) return;

    var xhr = new XMLHttpRequest();
    xhr.onload = function () {
        if (xhr.readyState === 4) {
            if (xhr.status === 200) {
                self.LoadedFiles.push(url);
                self.AddScript(xhr.responseText);
            } else {
                if (console) console.error(xhr.statusText);
            }
        }
    };
    xhr.open("GET", url, false);/*last parameter defines if call is async or not*/
    xhr.send(null);
},

AddScript: function (code) {
    var oNew = document.createElement("script");
    oNew.type = "text/javascript";
    oNew.textContent = code;
    document.getElementsByTagName("head")[0].appendChild(oNew);
}
};

/*Load script file. ScriptLoader will check if you try to load a file that has already been loaded (this check might be better, but I'm lazy).*/

ScriptLoader.LoadFile("Scripts/jquery-2.0.1.min.js");
ScriptLoader.LoadFile("Scripts/jquery-2.0.1.min.js");
/*this will be executed right after upper lines. It requires jquery to execute. It requires a HTML input with id "tb1"*/
$(function () { alert($('#tb1').val()); });

答案 11 :(得分:2)

jquery使用.append()函数为我解决了这个问题 - 用它来加载完整的jquery ui包

/*
 * FILENAME : project.library.js
 * USAGE    : loads any javascript library
 */
    var dirPath = "../js/";
    var library = ["functions.js","swfobject.js","jquery.jeditable.mini.js","jquery-ui-1.8.8.custom.min.js","ui/jquery.ui.core.min.js","ui/jquery.ui.widget.min.js","ui/jquery.ui.position.min.js","ui/jquery.ui.button.min.js","ui/jquery.ui.mouse.min.js","ui/jquery.ui.dialog.min.js","ui/jquery.effects.core.min.js","ui/jquery.effects.blind.min.js","ui/jquery.effects.fade.min.js","ui/jquery.effects.slide.min.js","ui/jquery.effects.transfer.min.js"];

    for(var script in library){
        $('head').append('<script type="text/javascript" src="' + dirPath + library[script] + '"></script>');
    }

使用 - 在导入jquery.js之后在html / php / etc的头部,你只需要包含这样一个文件就可以加载到你的整个库中,然后将它附加到头...

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

答案 12 :(得分:2)

有一个新的提议的ECMA标准,名为dynamic import,最近已整合到Chrome和Safari中。

SELECT *
FROM (
    SELECT *, LAG(Rate, 1, 0) OVER (ORDER BY UpdateDate) AS PrevRate
    FROM #TempRate
    ) A
WHERE Rate > PrevRate

答案 13 :(得分:2)

保持简洁,简洁,易于维护! :

// 3rd party plugins / script (don't forget the full path is necessary)
var FULL_PATH = '', s =
[
    FULL_PATH + 'plugins/script.js'      // Script example
    FULL_PATH + 'plugins/jquery.1.2.js', // jQuery Library 
    FULL_PATH + 'plugins/crypto-js/hmac-sha1.js',      // CryptoJS
    FULL_PATH + 'plugins/crypto-js/enc-base64-min.js'  // CryptoJS
];

function load(url)
{
    var ajax = new XMLHttpRequest();
    ajax.open('GET', url, false);
    ajax.onreadystatechange = function ()
    {
        var script = ajax.response || ajax.responseText;
        if (ajax.readyState === 4)
        {
            switch(ajax.status)
            {
                case 200:
                    eval.apply( window, [script] );
                    console.log("library loaded: ", url);
                    break;
                default:
                    console.log("ERROR: library not loaded: ", url);
            }
        }
    };
    ajax.send(null);
}

 // initialize a single load 
load('plugins/script.js');

// initialize a full load of scripts
if (s.length > 0)
{
    for (i = 0; i < s.length; i++)
    {
        load(s[i]);
    }
}

此代码只是一个简短的功能示例,可能需要其他功能,以便在任何(或给定)平台上提供全面支持。

答案 14 :(得分:2)

我们在工作中使用的技术是使用AJAX请求请求javascript文件,然后使用eval()返回。如果您正在使用原型库,则它们在Ajax.Request调用中支持此功能。

答案 15 :(得分:1)

一个荒谬的单行代码,对于那些认为加载js库不应使用多于一行代码的人:P

await new Promise((resolve, reject) => {let js = document.createElement("script"); js.src="mylibrary.js"; js.onload=resolve; js.onerror=reject; document.body.appendChild(js)});

很明显,如果要导入的脚本是模块,则可以使用import(...)函数。

答案 16 :(得分:1)

Dynamic module import landed in Firefox 67+

(async () => {
   await import('./synth/BubbleSynth.js')
})()

具有错误处理功能:

(async () => {
    await import('./synth/BubbleSynth.js').catch((error) => console.log('Loading failed' + error))
})()

https://caniuse.com/#feat=es6-module-dynamic-import

答案 17 :(得分:1)

对于那些喜欢单线的人:

import('./myscript.js');

有可能出现错误,例如:

从原始位置访问“ http://..../myscript.js”处的脚本 “ http://127.0.0.1”已被CORS政策禁止:否 请求中出现“ Access-Control-Allow-Origin”标头 资源。

在这种情况下,您可以回退至:

fetch('myscript.js').then(r => r.text()).then(t => new Function(t)());

答案 18 :(得分:1)

这是一个加载JS文件的函数的简单示例。相关要点:

  • 你不需要jQuery,所以你最初可以用它来加载jQuery.js文件
  • 与回调异步
  • 它确保只加载一次,因为它会保留一个带有已加载URL记录的机箱,从而避免使用网络
  • 与jQuery $.ajax$.getScript相反,您可以使用nonce,从而解决CSP unsafe-inline的问题。只需使用属性script.nonce
  • 即可
var getScriptOnce = function() {

    var scriptArray = []; //array of urls (closure)

    //function to defer loading of script
    return function (url, callback){
        //the array doesn't have such url
        if (scriptArray.indexOf(url) === -1){

            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;
                    if (typeof callback === 'function') {
                        callback();
                    }
                    script.onload = script.onreadystatechange = null;
                    head.removeChild(script);

                    scriptArray.push(url);
                }
            };

            head.appendChild(script);
        }
    };
}();

现在您只需

即可使用它
getScriptOnce("url_of_your_JS_file.js");

答案 19 :(得分:1)

Here是一个简单的回调和IE支持:

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("head")[0].appendChild(script);
}

loadScript("https://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js", function () {

     //jQuery loaded
     console.log('jquery loaded');

});

答案 20 :(得分:1)

我迷失在所有这些样本中,但今天我需要从我的主.js加载外部.js,我这样做了:

sonar.issuesReport.html.enable

答案 21 :(得分:1)

我编写了一个简单的模块,可以自动执行在JavaScript中导入/包含模块脚本的工作。试一试,请多给一些反馈! :)有关代码的详细说明,请参阅此博客文章:http://stamat.wordpress.com/2013/04/12/javascript-require-import-include-modules/

var _rmod = _rmod || {}; //require module namespace
_rmod.on_ready_fn_stack = [];
_rmod.libpath = '';
_rmod.imported = {};
_rmod.loading = {
    scripts: {},
    length: 0
};

_rmod.findScriptPath = function(script_name) {
    var script_elems = document.getElementsByTagName('script');
    for (var i = 0; i < script_elems.length; i++) {
        if (script_elems[i].src.endsWith(script_name)) {
            var href = window.location.href;
            href = href.substring(0, href.lastIndexOf('/'));
            var url = script_elems[i].src.substring(0, script_elems[i].length - script_name.length);
            return url.substring(href.length+1, url.length);
        }
    }
    return '';
};

_rmod.libpath = _rmod.findScriptPath('script.js'); //Path of your main script used to mark the root directory of your library, any library


_rmod.injectScript = function(script_name, uri, callback, prepare) {

    if(!prepare)
        prepare(script_name, uri);

    var script_elem = document.createElement('script');
    script_elem.type = 'text/javascript';
    script_elem.title = script_name;
    script_elem.src = uri;
    script_elem.async = true;
    script_elem.defer = false;

    if(!callback)
        script_elem.onload = function() {
            callback(script_name, uri);
        };

    document.getElementsByTagName('head')[0].appendChild(script_elem);
};

_rmod.requirePrepare = function(script_name, uri) {
    _rmod.loading.scripts[script_name] = uri;
    _rmod.loading.length++;
};

_rmod.requireCallback = function(script_name, uri) {
    _rmod.loading.length--;
    delete _rmod.loading.scripts[script_name];
    _rmod.imported[script_name] = uri;

    if(_rmod.loading.length == 0)
        _rmod.onReady();
};

_rmod.onReady = function() {
    if (!_rmod.LOADED) {
        for (var i = 0; i < _rmod.on_ready_fn_stack.length; i++){
            _rmod.on_ready_fn_stack[i]();
        });
        _rmod.LOADED = true;
    }
};

//you can rename based on your liking. I chose require, but it can be called include or anything else that is easy for you to remember or write, except import because it is reserved for future use.
var require = function(script_name) {
    var np = script_name.split('.');
    if (np[np.length-1] === '*') {
        np.pop();
        np.push('_all');
    }

    script_name = np.join('.');
    var uri = _rmod.libpath + np.join('/')+'.js';
    if (!_rmod.loading.scripts.hasOwnProperty(script_name) 
     && !_rmod.imported.hasOwnProperty(script_name)) {
        _rmod.injectScript(script_name, uri, 
            _rmod.requireCallback, 
                _rmod.requirePrepare);
    }
};

var ready = function(fn) {
    _rmod.on_ready_fn_stack.push(fn);
};

// ----- USAGE -----

require('ivar.util.array');
require('ivar.util.string');
require('ivar.net.*');

ready(function(){
    //do something when required scripts are loaded
});

答案 22 :(得分:1)

有专门为此目的而设计的脚本。

yepnope.js内置于Modernizr中,lab.js是更优化的(但用户友好版本较少。

我不会建议通过像jquery或prototype这样的大型库来实现这一点 - 因为脚本加载器的一个主要好处是能够尽早加载脚本 - 你不应该等到jquery&amp;在运行检查之前加载所有dom元素,以查看是否要动态加载脚本。

答案 23 :(得分:0)

我知道我的答案对于这个问题来说有点迟了,但是,这是 www.html5rocks.com - Deep dive into the murky waters of script loading中的一篇很棒的文章。

在该文章中得出的结论是,在浏览器支持方面,动态加载JavaScript文件而不阻止内容呈现的最佳方法是以下方式:

考虑到您有四个名为script1.js, script2.js, script3.js, script4.js的脚本,您可以使用应用async = false 来执行此操作:

[
  'script1.js',
  'script2.js',
  'script3.js',
  'script4.js'
].forEach(function(src) {
  var script = document.createElement('script');
  script.src = src;
  script.async = false;
  document.head.appendChild(script);
});

现在,规范:一起下载,全部下载后立即执行。

Firefox&lt; 3.6,Opera说:我不知道这个“异步”的东西是什么,但事实上我按照添加的顺序执行通过JS添加的脚本。

Safari 5.0说:我理解“异步”,但不明白用JS将其设置为“false”。我会在他们降落后立即以任何顺序执行你的脚本。

IE&lt; 10说:不知道“异步”,但有一个使用“onreadystatechange”的解决方法。

其他一切都说:我是你的朋友,我们将在本书中做到这一点。

现在,IE的完整代码&lt; 10解决方法:

var scripts = [
  'script1.js',
  'script2.js',
  'script3.js',
  'script4.js'
];
var src;
var script;
var pendingScripts = [];
var firstScript = document.scripts[0];

// Watch scripts load in IE
function stateChange() {
  // Execute as many scripts in order as we can
  var pendingScript;
  while (pendingScripts[0] && pendingScripts[0].readyState == 'loaded') {
    pendingScript = pendingScripts.shift();
    // avoid future loading events from this script (eg, if src changes)
    pendingScript.onreadystatechange = null;
    // can't just appendChild, old IE bug if element isn't closed
    firstScript.parentNode.insertBefore(pendingScript, firstScript);
  }
}

// loop through our script urls
while (src = scripts.shift()) {
  if ('async' in firstScript) { // modern browsers
    script = document.createElement('script');
    script.async = false;
    script.src = src;
    document.head.appendChild(script);
  }
  else if (firstScript.readyState) { // IE<10
    // create a script and add it to our todo pile
    script = document.createElement('script');
    pendingScripts.push(script);
    // listen for state changes
    script.onreadystatechange = stateChange;
    // must set src AFTER adding onreadystatechange listener
    // else we’ll miss the loaded event for cached scripts
    script.src = src;
  }
  else { // fall back to defer
    document.write('<script src="' + src + '" defer></'+'script>');
  }
}

稍后一些技巧和缩小,它是362字节

!function(e,t,r){function n(){for(;d[0]&&"loaded"==d[0][f];)c=d.shift(),c[o]=!i.parentNode.insertBefore(c,i)}for(var s,a,c,d=[],i=e.scripts[0],o="onreadystatechange",f="readyState";s=r.shift();)a=e.createElement(t),"async"in i?(a.async=!1,e.head.appendChild(a)):i[f]?(d.push(a),a[o]=n):e.write("<"+t+' src="'+s+'" defer></'+t+">"),a.src=s}(document,"script",[
  "//other-domain.com/1.js",
  "2.js"
])

答案 24 :(得分:0)

像这样......

<script>
     $(document).ready(function() {
          $('body').append('<script src="https://maps.googleapis.com/maps/api/js?key=KEY&libraries=places&callback=getCurrentPickupLocation" async defer><\/script>');
     });
</script>

答案 25 :(得分:0)

我已经用工作示例调整了上面的一些帖子。 在这里,我们也可以将css和js放在同一数组中。

$(document).ready(function(){

if (Array.prototype.contains === undefined) {
Array.prototype.contains = function (obj) {
    var i = this.length;
    while (i--) { if (this[i] === obj) return true; }
    return false;
};
};

/* define object that will wrap our logic */
var jsScriptCssLoader = {

jsExpr : new RegExp( "js$", "i" ),
cssExpr : new RegExp( "css$", "i" ),
loadedFiles: [],

loadFile: function (cssJsFileArray) {
    var self = this;
    // remove duplicates with in array
    cssJsFileArray.filter((item,index)=>cssJsFileArray.indexOf(item)==index)
    var loadedFileArray = this.loadedFiles;
    $.each(cssJsFileArray, function( index, url ) {
            // if multiple arrays are loaded the check the uniqueness
            if (loadedFileArray.contains(url)) return;
            if( self.jsExpr.test( url ) ){
                $.get(url, function(data) {
                    self.addScript(data);
                });

            }else if( self.cssExpr.test( url ) ){
                $.get(url, function(data) {
                    self.addCss(data);
                });
            }

            self.loadedFiles.push(url);
    });

    // don't load twice accross different arrays

},
addScript: function (code) {
    var oNew = document.createElement("script");
    oNew.type = "text/javascript";
    oNew.textContent = code;
    document.getElementsByTagName("head")[0].appendChild(oNew);
},
addCss: function (code) {
    var oNew = document.createElement("style");
    oNew.textContent = code;
    document.getElementsByTagName("head")[0].appendChild(oNew);
}

};


//jsScriptCssLoader.loadFile(["css/1.css","css/2.css","css/3.css"]);
jsScriptCssLoader.loadFile(["js/common/1.js","js/2.js","js/common/file/fileReader.js"]);
});

答案 26 :(得分:0)

所有主要的javascript库,如jscript,prototype,YUI都支持加载脚本文件。例如,在YUI中,加载核心后,您可以执行以下操作来加载日历控件

var loader = new YAHOO.util.YUILoader({

    require: ['calendar'], // what components?

    base: '../../build/',//where do they live?

    //filter: "DEBUG",  //use debug versions (or apply some
                        //some other filter?

    //loadOptional: true, //load all optional dependencies?

    //onSuccess is the function that YUI Loader
    //should call when all components are successfully loaded.
    onSuccess: function() {
        //Once the YUI Calendar Control and dependencies are on
        //the page, we'll verify that our target container is 
        //available in the DOM and then instantiate a default
        //calendar into it:
        YAHOO.util.Event.onAvailable("calendar_container", function() {
            var myCal = new YAHOO.widget.Calendar("mycal_id", "calendar_container");
            myCal.render();
        })
     },

    // should a failure occur, the onFailure function will be executed
    onFailure: function(o) {
        alert("error: " + YAHOO.lang.dump(o));
    }

 });

// Calculate the dependency and insert the required scripts and css resources
// into the document
loader.insert();