JQuery Dialog的内存泄露问题解决方法


Posted in Javascript onJune 18, 2010

对于页面来说,JQuery中的Dialog从效果上来说还可以,而且使用简单,只要短短几行绑定的代码就可以实现弹出效果。
代码

$('#dialog').dialog({ 
autoOpen: false, 
width: 600, 
buttons: { 
"Ok": function() { 
$(this).dialog("close"); 
}, 
"Cancel": function() { 
$(this).dialog("close"); 
} 
} 
});

在一些JS交互性不多的一般页面来说,没有任何问题!但是对于交互性强的,需要动态加载与释放DOM的页面来说,它就是一个悲剧的东西!为什么这样说?大家看下下面的例子:

一段简单的代码,一个DIV是通过动态加载到页面上,然后对该DIV用Dialog进行绑定,以达到弹出的目的!下面的test元素就是<div id="test"></div>。
代码

function TestAppend() { 
$("#test").append('<div id="dialog"><div id="fileQueue"></div> <input type="file" name="uploadify" id="uploadify" />' + 
'<a href="javascript:upload();">上传</a>' + 
'<a href="javascript:$(#uploadify).uploadifyClearQueue()">取消上传</a><div>'); 
$('#dialog').dialog({ 
autoOpen: false, 
width: 600, 
buttons: { 
"Ok": function() { 
$(this).dialog("close"); 
}, 
"Cancel": function() { 
$(this).dialog("close"); 
} 
} 
}); 
return false; 
}

接着,我需要删除该DOM元素,一般来说,正常的做法都是$("#test").empty();这行简单的代码就完成了!这样有效吗?!当执行完这样代码后,你再用$('#dialog')来获取dialog元素,郁闷的事情发生了,既然获取到了!为什么!不是已经empty了吗!

下面我们来看下这一悲剧是如何造成的,

我们把注意点放到$('#dialog').dialog上面,然后看看JQuery的实现代码是如何写的,当我们跟踪代码到dialog类中的_create方法的时候,问题的原因找到了,看下面这段代码:

uiDialog = (self.uiDialog = $('<div></div>')) 
.appendTo(document.body) 
.hide() 
.addClass(uiDialogClasses + options.dialogClass) 
.css({ 
zIndex: options.zIndex 
}) 
// setting tabIndex makes the div focusable 
// setting outline to 0 prevents a border on focus in Mozilla 
.attr('tabIndex', -1).css('outline', 0).keydown(function(event) { 
if (options.closeOnEscape && event.keyCode && 
event.keyCode === $.ui.keyCode.ESCAPE) { 
self.close(event); 
event.preventDefault(); 
} 
}) 
.attr({ 
role: 'dialog', 
'aria-labelledby': titleId 
}) 
.mousedown(function(event) { 
self.moveToTop(false, event); 
}),

它既然也动态创建一个div,而且把该div加到了Body上面,然后把dialog中的元素从<div id=test>中移除,加入到该新的div中.....

这就是为什么我们$("#test").empty()后,却对内部的dialog没有起作用了!而且这有一个最不好的一个地方,也是最容易出现内存泄露的地方:它动态的在Body中创建了一个div,这样如果窗体不关闭的话,而你又在不察觉的情况下不断的使用上面的TestAppend方法来动态加载DOM,就会创建N个这样的div!

其实这个问题郁闷的地方不是在如何解决,而且隐藏的很深,很难发现!那么发现之后解决起来就变的简单多了:

if ($('#dialog')[0]) { 
$('#dialog').parent().empty(); 
$('#dialog').parent().remove(); 
}

当前加上这段后代码后,再做$("#dialog")来测试下,期望的结果终于出现了!dialog元素消失了!
Javascript 相关文章推荐
Javascript拓展String方法小结
Jul 08 Javascript
javascript基于HTML5 canvas制作画箭头组件
Jun 25 Javascript
JS+CSS实现模仿浏览器网页字符查找功能的方法
Feb 26 Javascript
微信小程序中使元素占满整个屏幕高度实现方法
Dec 14 Javascript
原生js封装自定义滚动条
Mar 24 Javascript
微信小程序开发入门基础教程
Apr 19 Javascript
利用JavaScript的%做隔行换色的实例
Nov 25 Javascript
JQuery 又谈ajax局部刷新
Nov 27 jQuery
使用vue-router beforEach实现判断用户登录跳转路由筛选功能
Jun 25 Javascript
vue自定义移动端touch事件之点击、滑动、长按事件
Jul 10 Javascript
node中的session的具体使用
Sep 14 Javascript
微信小程序实现滑动操作代码
Apr 23 Javascript
通过jQuery打造支持汉字,拼音,英文快速定位查询的超级select插件
Jun 18 #Javascript
jquery ready()的几种实现方法小结
Jun 18 #Javascript
JQuery在光标位置插入内容的实现代码
Jun 18 #Javascript
JavaScript Chart 插件整理
Jun 18 #Javascript
JavaScript在IE和Firefox浏览器下的7个差异兼容写法小结
Jun 18 #Javascript
Javascript下IE与Firefox下的差异兼容写法总结
Jun 18 #Javascript
js打印纸函数代码(递归)
Jun 18 #Javascript
You might like
ThinkPHP3.1新特性之动态设置自动完成和自动验证示例
2014/06/19 PHP
ThinkPHP 框架实现的读取excel导入数据库操作示例
2020/04/14 PHP
FireFox下XML对象转化成字符串的解决方法
2011/12/09 Javascript
基于JavaScript实现继承机制之构造函数方法对象冒充的使用详解
2013/05/07 Javascript
jQuery网页右侧广告跟随滚动代码分享
2020/04/20 Javascript
基于jquery实现即时检查格式是否正确的表单
2016/05/06 Javascript
AngularJS动态绑定ng-options的ng-model实例代码
2017/06/21 Javascript
详解Vue.directive 自定义指令
2019/03/27 Javascript
Vue自定义全局Toast和Loading的实例详解
2019/04/18 Javascript
Vue 3.0 前瞻Vue Function API新特性体验
2019/08/12 Javascript
微信小程序网络请求实现过程解析
2019/11/06 Javascript
原理深度解析Vue的响应式更新比React快
2020/04/04 Javascript
js+canvas实现刮刮奖功能
2020/09/13 Javascript
[04:59]DOTA2-DPC中国联赛 正赛 Ehome vs iG 选手采访
2021/03/11 DOTA
python django事务transaction源码分析详解
2017/03/17 Python
Python序列循环移位的3种方法推荐
2018/04/09 Python
解决python "No module named pip" 的问题
2018/10/13 Python
python实现自动解数独小程序
2019/01/21 Python
python处理DICOM并计算三维模型体积
2019/02/26 Python
python openpyxl使用方法详解
2019/07/18 Python
python两个list[]相加的实现方法
2020/09/23 Python
移动端html5 meta标签的神奇功效
2016/01/06 HTML / CSS
纽约著名的服装辅料来源:M&J Trimming
2017/07/26 全球购物
英国男士时尚购物网站:Stuarts London
2017/10/22 全球购物
Sahajan美国:阿育吠陀护肤品牌
2021/01/09 全球购物
生物技术专业毕业生求职信范文
2013/12/14 职场文书
英语专业学生个人求职信范文
2014/01/06 职场文书
出纳员岗位职责风险
2014/03/06 职场文书
前台文员职责范本
2014/03/07 职场文书
学生个人自我鉴定
2014/03/26 职场文书
学校募捐倡议书
2014/05/14 职场文书
学习十八大的心得体会
2014/09/01 职场文书
小学教师见习总结
2015/06/23 职场文书
配置Kubernetes外网访问集群
2022/03/31 Servers
【DOTA2】当街暴打?PSG LGD vs VG - DPC 2022 WINTER TOUR CN
2022/04/02 DOTA
Window server 2012 R2 AD域的组策略相关设置
2022/04/28 Servers