IE下使用cloneNode注意事项分享


Posted in Javascript onNovember 22, 2012

cloneNode 是 HtmlElement 原型链上的方法,用于创建指定 dom 节点的拷贝,它接受一个布尔参数 include_all,如果 include_all 设置为 true,则副本会带有指定节点的所有子节点。

然而,script 标签也是 dom 节点,cloneNode 对其依然有效,经实测各浏览器(尤其是IE)对 cloneNode 执行结果表现不一致,主要现象为以下两种:

IE,至少是 IE8 及以下,对某节点 cloneNode 时,如果该节点包含 script 节点,那么 script 节点的脚本内容“有可能”会被再次执行一次。
非 IE 浏览器,cloneNode 某节点,包含的 script 节点的脚本内容不会被再次执行。
IE 以外的浏览器表现令我很满意,而针对于上面所述 IE 的“有可能”,还分以下两种情况:

如果 cloneNode 一个 script 节点,无论该节点是外链脚本,还是内嵌脚本,均不会被再次执行。
如果 cloneNode 一个其它节点,该节点下包含的内嵌脚本不会被执行,而包含的外链脚本,会被再次执行一次。
这里有一个 demo 复现了 IE 下 cloneNode 的这个问题。

看到这里,你是不是要被绕晕了?解决方法很简单,不用管是什么浏览器,cloneNode 之前,把目标节点下所有的 script 标签移除即可,因为脚本已经执行过,移除它的标签并不会造成影响,如下:

function cloneNode(dom){ 
var scripts = dom.getElementsByTagName("script"); 
for(var i = scripts - 1, s; i >= 0; i --){ 
s = scripts[i]; 
s.parentNode.removeChild(s); 
} 
return dom.cloneNode(true); 
}

因此,我们在使用 cloneNode(true) 时一定要注意思考:所复制节点内的所有子节点是否都是需要的?尽量把不需要的都干掉,避免造成负作用影响,再举个例子,如果复制 div 中包含 iframe,而 iframe 的页面里有脚本 parent.xxx…,那么 iframe 里的这些脚本必然会再重新执行一次,iframe 页本身没问题(也不一定),但由于它操作了 parent,那么这个 parent 造成的影响就难以估量了。解决方法是 cloneNode 之后,把副本里包含的 iframe 干掉,当然,如果剧情所需,iframe 不能干掉的话,就在 iframe 页里的脚本自行做判断了。

另外,cloneNode 目标节点内包含 link 标签的话,这个估计也会有些影响,我没有做实验,如果没用的话,也是 removeChild 了之,以绝后患。

Javascript 相关文章推荐
js 跨域和ajax 跨域问题小结
Jul 01 Javascript
jQueryUI如何自定义组件实现代码
Nov 14 Javascript
引用外部脚本时script标签关闭的写法
Jan 20 Javascript
Javascript字符串对象的常用方法简明版
Jun 26 Javascript
纯js代码实现未知宽高的元素在指定元素中垂直水平居中显示
Sep 12 Javascript
只需五句话搞定JavaScript作用域(经典)
Jul 26 Javascript
JavaScript中cookie工具函数封装的示例代码
Oct 11 Javascript
JavaScript数据结构之链表的实现
Mar 19 Javascript
Vue.js学习记录之在元素与template中使用v-if指令实例
Jun 27 Javascript
javascript 中模板方法单例的实现方法
Oct 17 Javascript
jquery绑定事件 bind和on的用法与区别分析
May 22 jQuery
JS typeof fn === 'function' && fn()详解
Aug 22 Javascript
jquery remove方法应用详解
Nov 22 #Javascript
FusionCharts图表显示双Y轴双(多)曲线
Nov 22 #Javascript
ECMAScript 创建自己的js类库
Nov 22 #Javascript
javascript克隆对象深度介绍
Nov 20 #Javascript
Extjs显示从数据库取出时间转换JSON后的出现问题
Nov 20 #Javascript
JS中toFixed()方法引起的问题如何解决
Nov 20 #Javascript
JavaScript实现拼音排序的方法
Nov 20 #Javascript
You might like
Smarty Foreach 使用说明
2010/03/23 PHP
php与flash as3 socket通信传送文件实现代码
2014/08/16 PHP
解决ThinkPHP关闭调试模式时报错的问题汇总
2015/04/22 PHP
php7连接MySQL实现简易查询程序的方法
2020/10/13 PHP
使用js解决由border属性引起的div宽度问题
2013/11/26 Javascript
Javascript实现返回上一页面并刷新的小例子
2013/12/11 Javascript
用js正确判断用户名cookie是否存在的方法
2014/01/28 Javascript
js实现遮罩层划出效果是生成div而不是显示
2014/07/29 Javascript
JS中FRAME的操作问题实例分析
2014/10/21 Javascript
node.js中的console.info方法使用说明
2014/12/09 Javascript
基于vue2的table分页组件实现方法
2017/03/20 Javascript
简单好用的nodejs 爬虫框架分享
2017/03/26 NodeJs
Vue.js学习教程之列表渲染详解
2017/05/17 Javascript
js中apply和Math.max()函数的问题及区别介绍
2018/03/27 Javascript
详解vue2.0 资源文件assets和static的区别
2018/11/27 Javascript
layer.alert自定义关闭回调事件的方法
2019/09/27 Javascript
JS常见错误(Error)及处理方案详解
2020/07/02 Javascript
Webpack3+React16代码分割的实现
2021/03/03 Javascript
Python之os操作方法(详解)
2017/06/15 Python
Python中scatter函数参数及用法详解
2017/11/08 Python
OpenCV+python手势识别框架和实例讲解
2018/08/03 Python
Python修改文件往指定行插入内容的实例
2019/01/30 Python
对django中foreignkey的简单使用详解
2019/07/28 Python
基于Python数据结构之递归与回溯搜索
2020/02/26 Python
python GUI库图形界面开发之PyQt5时间控件QTimer详细使用方法与实例
2020/02/26 Python
韩国江南富人区高端时尚百货商场:Galleria(格乐丽雅)
2018/03/27 全球购物
Zalando Lounge瑞士:时尚与生活方式购物俱乐部
2020/03/12 全球购物
亿阳信通股份有限公司C#笔试题
2016/12/06 面试题
毕业自我评价范文
2013/11/17 职场文书
商务经理岗位职责
2014/07/30 职场文书
办公室主任个人总结
2015/02/28 职场文书
谢师宴家长答谢词
2015/09/30 职场文书
学习习近平主席讲话心得体会
2016/01/20 职场文书
WordPress多语言翻译插件 - WPML使用教程
2021/04/01 PHP
weblogic服务建立数据源连接测试更新mysql驱动包的问题及解决方法
2022/01/22 MySQL
Redis如何实现验证码发送 以及限制每日发送次数
2022/04/18 Redis