动态加载script文件的两种方法


Posted in Javascript onAugust 15, 2013

动态加载script到页面大约有俩方法

第一种就是利用ajax方式,把script文件代码从后台加载到前台,然后对加载到的内容通过eval()执行代码。第二种是,动态创建一个script标签,设置其src属性,通过把script标签插入到页面head来加载js,相当于在head中写了一个<script src="..."></script>,只不过这个script标签是用js动态创建的
比如说是我们要动态地加载一个callbakc.js,我们就需要这样一个script标签:

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

如下代码就是如何通过js来创建这个标签(并且加到head中):
var head= document.getElementsByTagName('head')[0]; 
var script= document.createElement('script'); 
script.type= 'text/javascript'; 
script.src= 'call.js'; 
head.appendChild(script);

当加载完call.js, 我们就要调用其中的方法。不过在header.appendChild(script)之后我们不能马上调用其中的js。因为浏览器是异步加载这个js的,我们不知道他什么时候加载完。然而我们可以通过监听事件的办法来判断helper.js是否加载完成。(假设call.js中有一个callback方法)
var head= document.getElementsByTagName('head')[0]; 
var script= document.createElement('script'); 
script.type= 'text/javascript'; 
script.onreadystatechange= function () { 
if (this.readyState == 'complete') 
callback(); 
} 
script.onload= function(){ 
callback(); 
} 
script.src= 'helper.js'; 
head.appendChild(script);

我设了2个事件监听函数, 因为在ie中使用onreadystatechange, 而gecko,webkit 浏览器和opera都支持onload。事实上this.readyState == 'complete'并不能工作的很好,理论上状态的变化是如下步骤:
0 uninitialized
1 loading
2 loaded
3 interactive
4 complete
但是有些状态会被跳过。根据经验在ie7中,只能获得loaded和completed中的一个,不能都出现,原因也许是对判断是不是从cache中读取影响了状态的变化,也可能是其他原因。最好把判断条件改成this.readyState == 'loaded' || this.readyState == 'complete'

参考jQuery的实现我们最后实现为:

var head= document.getElementsByTagName('head')[0]; 
var script= document.createElement('script'); 
script.type= 'text/javascript'; 
script.onload = script.onreadystatechange = function() { 
if (!this.readyState || this.readyState === "loaded" || this.readyState === "complete" ) { 
help(); 
// Handle memory leak in IE 
script.onload = script.onreadystatechange = null; 
} }; 
script.src= 'helper.js'; 
head.appendChild(script);

还有一种简单的情况就是可以把help()的调用写在helper.js的最后,那么可以保证在helper.js在加载完后能自动调用help(),当然最后还要能这样是不是适合你的应用。

另外需要注意:

1.因为script标签的src可以跨域访问资源,所以这种方法可以模拟ajax,解决ajax跨域访问的问题。
2.如果用ajax返回的html代码中包含script,则直接用innerHTML插入到dom中是不能使html中的script起作用的。粗略的看了下jQuery().html(html)的原代码,jQuery也是先解析传入的参数,剥离其中的script代码,动态创建script标签,所用jQuery的html方法添加进dom的html如果包含script是可以执行的。如:

jQuery("#content").html("<script>alert('aa');<\/script>");
Javascript 相关文章推荐
javascript中的变量作用域以及变量提升详细介绍
Oct 24 Javascript
JS实现定时页面弹出类似QQ新闻的提示框
Nov 07 Javascript
javascript记录文本框内文字个数检测文字个数变化
Oct 14 Javascript
jquery Validation表单验证使用详解
Sep 12 Javascript
JavaScript来实现打开链接页面的简单实例
Jun 02 Javascript
Vue.js每天必学之内部响应式原理探究
Sep 07 Javascript
详解angular2采用自定义指令(Directive)方式加载jquery插件
Feb 09 Javascript
jQuery选择器之子元素过滤选择器
Sep 28 jQuery
React从react-router路由上做登陆验证控制的方法
May 10 Javascript
巧妙运用v-model实现父子组件传值的方法示例
Apr 07 Javascript
js利用拖放实现添加删除
Aug 27 Javascript
正则表达式基础与常用验证表达式
Jun 16 Javascript
js string 转 int 注意的问题小结
Aug 15 #Javascript
Jquery右下角抖动、浮动 实例代码(兼容ie6、FF)
Aug 15 #Javascript
js控制表单操作的常用代码小结
Aug 15 #Javascript
固定网页背景图同时保持图片比例的思路代码
Aug 15 #Javascript
jQuery UI 实现email输入提示实例
Aug 15 #Javascript
javascript中如何处理引号编码&amp;#034;
Aug 15 #Javascript
Jquery中val()表单取值赋值的实例代码
Aug 15 #Javascript
You might like
C# Assembly类访问程序集信息
2009/06/13 PHP
Yii中render和renderPartial的区别
2014/09/03 PHP
PHP生成树的方法
2015/07/28 PHP
php获取'/'传参的值简单方法
2017/07/13 PHP
Laravel Validator自定义错误返回提示消息并在前端展示
2019/05/09 PHP
JavaScript中Math对象使用说明
2008/01/16 Javascript
Javascript 中文字符串处理额外注意事项
2009/11/15 Javascript
深入分析JSON编码格式提交表单数据
2015/06/25 Javascript
JavaScript学习笔记之ES6数组方法
2016/03/25 Javascript
JavaScript获取服务器端时间的方法
2016/11/29 Javascript
jquery获取下拉框中的循环值
2017/02/08 Javascript
Angular 表单控件示例代码
2017/06/26 Javascript
JS实现按钮控制计时开始和停止功能
2017/07/27 Javascript
js实现拖拽上传图片功能
2017/08/01 Javascript
vue 自定义组件 v-model双向绑定、 父子组件同步通信的多种写法
2017/11/27 Javascript
vue 实现通过手机发送短信验证码注册功能
2018/04/19 Javascript
解决vue this.$forceUpdate() 处理页面刷新问题(v-for循环值刷新等)
2018/07/26 Javascript
Vue2.0学习系列之项目上线的方法步骤(图文)
2018/09/25 Javascript
详解微信小程序之scroll-view的flex布局问题
2019/01/16 Javascript
vue实现中部导航栏布局功能
2019/07/30 Javascript
[38:40]2018DOTA2亚洲邀请赛 4.6淘汰赛 mineski vs LGD 第一场
2018/04/10 DOTA
Python实现向QQ群成员自动发邮件的方法
2014/11/19 Python
通过Python来使用七牛云存储的方法详解
2015/08/07 Python
python内置函数:lambda、map、filter简单介绍
2017/11/16 Python
用Python实现数据的透视表的方法
2018/11/16 Python
Python实现的登录验证系统完整案例【基于搭建的MVC框架】
2019/04/12 Python
使用Python画出小人发射爱心的代码
2019/11/23 Python
python如何获取apk的packagename和activity
2020/01/10 Python
django有外键关系的两张表如何相互查找
2020/02/10 Python
Java爬虫技术框架之Heritrix框架详解
2020/07/22 Python
appium+python自动化配置(adk、jdk、node.js)
2020/11/17 Python
英国和爱尔兰的自炊式豪华度假小屋:Rural Retreats
2018/06/08 全球购物
Chain Reaction Cycles俄罗斯:世界上最大的在线自行车商店
2019/08/27 全球购物
关于Java String的一道面试题
2013/09/29 面试题
SQL基础查询和LINQ集成化查询
2022/01/18 MySQL
前端canvas中物体边框和控制点的实现示例
2022/08/05 Javascript