jQuery移除元素自动解绑事件实现思路及代码


Posted in Javascript onMay 31, 2014

世界本该如此!

所以,在现代浏览器,如果你将一个元素从DOM树种进行移除的时候,浏览器会自动帮你绑定的事件进行解绑以释放其占用的内存。也许你猜到了,较老版本的浏览器则不会主动去做这件事,所以,当你的应用在较老版本的浏览器运行的越久,其消耗内存越多,应用就会变得越来越卡。因此,需要我们自己对要删除的元素进行事件解绑。

实现思路

用jQuery将元素移除的基本方法常用的有三个,一个是remove()方法,一个是html()方法,一个是empty()方法。我们可以对此三个方法进行进一步的封装,我们会在事件绑定的时候给绑定事件的元素添加一个属性标识,从要删除的元素中去寻找有此标识的元素,然后进行事件的完全解绑。一切都是那么的巧妙!需要注意的一点是,remove()方法在执行的时候会对其自身进行事件解绑,并且该方法可以接受一个选择器参数,以删除其子元素。

实现代码

有了实现思路,编码可以很快搞定。如下:

define(['jquery', 'underscore'], function () { 
var bindDirects = ['delegate', 'bind','on', 'hover', 'blur', 'change', 'click', 'dblclick', 'focus', 'keydown', 'keypress', 'keyup', 'mousedown', 'mouseenter', 'mouseleave', 'mousemove', 'mouseout', 'mouseover', 'mouseup', 'resize', 'scroll', 'select', 'submit']; 
var eMarker = '_addedEvent'; 
_.each(bindDirects, function (eventName) { 
var alias = $.fn[eventName]; 
$.fn[eventName] = function () { 
var $tar = _.isElement(this)?$(this):this; 
var hasEventAdded = $tar.attr(eMarker) || ''; 
var _en = eventName; 
if (hasEventAdded.length) { 
_en += ',' + hasEventAdded; 
} 
$tar.attr(eMarker, _en); 
return alias.apply(_.isElement(this)?$tar:this, [].slice.call(arguments)); 
}; 
}); 
// 为某一个元素移除绑定的事件 
function removeEvents($tar) { 
var addedEventsName = $tar.attr(eMarker); 
if (addedEventsName) { 
addedEventsName.replace(/[^,]+/g, function (eventName) { 
// 全部移除 
if (eventName === 'delegate') { 
$tar.undelegate(); 
} else { 
$tar.unbind(); 
} 
return eventName; 
}); 
} 
} var funcs = ['html','empty']; 
_.each(funcs, function (func) { 
var alias = $.fn[func]; 
$.fn[func] = function () { 
var $tar = _.isElement(this)?$(this):this; 
if($tar.length){ 
$tar.find('*[' + eMarker + ']').each(function (k, subEl) { 
try{ 
removeEvents($(subEl)); 
}catch(e){ 
console.error(e.message); 
} 
}); 
} 
var args = [].slice.call(arguments); 
return alias.apply($tar, args); 
}; 
}); 
// 扩展remove()方法 
var alias = $.fn.remove; 
$.fn.remove = function () { 
var $tar = _.isElement(this)?$(this):this, 
arg = arguments; 
if($tar.length && !arg.length){ 
$tar.find('*[' + eMarker + ']').each(function (k, subEl) { 
try{ 
removeEvents($(subEl)); 
}catch(e){ 
console.error(e.message); 
} 
}); 
} 
if(arg.length){ 
var selector = arg[0]; 
if(_.isString(selector)){ 
$tar.find(selector).each(function(k,curEl){ 
var $cur = $(curEl); 
$cur.find('*[' + eMarker + ']').each(function (k, subEl) { 
try{ 
removeEvents($(subEl)); 
}catch(e){ 
console.error(e.message); 
} 
}); 
removeEvents($cur); 
$cur.remove(); 
}); 
} 
} 
var args = [].slice.call(arguments); 
return alias.apply($tar, args); 
}; 
});

还是那句话,了解的越多,你能做的就越多!
Javascript 相关文章推荐
tbody元素支持嵌套的注意方法
Mar 24 Javascript
jQuery JSON的解析方式分享
Apr 05 Javascript
js带按钮的提示框可供选择示例代码
Sep 17 Javascript
javascript date格式化示例
Sep 25 Javascript
JavaScript中的类数组对象介绍
Dec 30 Javascript
JS实现先显示大图后自动收起显示小图的广告代码
Sep 04 Javascript
基于jQuery实现多标签页切换的效果(web前端开发)
Jul 24 Javascript
可输入文字查找ajax下拉框控件 ComBox的实现方法
Oct 25 Javascript
JS 对java返回的json格式的数据处理方法
Dec 05 Javascript
Vue+Typescript中在Vue上挂载axios使用时报错问题
Aug 07 Javascript
JavaScript实现秒杀时钟倒计时
Sep 29 Javascript
如何在Express4.x中愉快地使用async的方法
Nov 18 Javascript
jQuery操作select下拉框的text值和value值的方法
May 31 #Javascript
js中的for如何实现foreach中的遍历
May 31 #Javascript
javascript 小数取整简单实现方式
May 30 #Javascript
JQuery给元素绑定click事件多次执行的解决方法
May 29 #Javascript
jquery获取tagName再进行判断
May 29 #Javascript
自定义jquery模态窗口插件无法在顶层窗口显示问题
May 29 #Javascript
Jquery 获取指定标签的对象及属性的设置与移除
May 29 #Javascript
You might like
用户的详细注册和判断
2006/10/09 PHP
DW中链接mysql数据库时,建立字符集中文出现乱码的解决方法
2010/03/27 PHP
CodeIgniter配置之SESSION用法实例分析
2016/01/19 PHP
Yii2实现同时搜索多个字段的方法
2016/08/10 PHP
Laravel如何使用Redis共享Session
2018/02/23 PHP
JavaScript 动态改变图片大小
2009/06/11 Javascript
Js动态添加复选框Checkbox的实例方法
2013/04/08 Javascript
javascript级联下拉列表实例代码(自写)
2013/05/10 Javascript
AngularJS Controller作用域
2017/01/09 Javascript
原生和jQuery的ajax用法详解
2017/01/23 Javascript
JS实现的找零张数最小问题示例
2017/11/28 Javascript
基于vue2.0动态组件及render详解
2018/03/17 Javascript
JavaScript实现学生在线做题计时器功能
2018/12/05 Javascript
解决vuex刷新状态初始化的方法实现
2019/08/15 Javascript
Vue Components 数字键盘的实现
2019/09/18 Javascript
浅探express路由和中间件的实现
2019/09/30 Javascript
vue 更改连接后台的api示例
2019/11/11 Javascript
jQuery实现简单弹幕效果
2019/11/28 jQuery
[11:33]DAC2018 4.5SOLO赛决赛 MidOne vs Paparazi第二场
2018/04/06 DOTA
Python实现去除列表中重复元素的方法小结【4种方法】
2018/04/27 Python
解决python3读取Python2存储的pickle文件问题
2018/10/25 Python
Python装饰器限制函数运行时间超时则退出执行
2019/04/09 Python
python3使用腾讯企业邮箱发送邮件的实例
2019/06/28 Python
Python Tkinter图形工具使用方法及实例解析
2020/06/15 Python
详解Pandas 处理缺失值指令大全
2020/07/30 Python
Python读取ini配置文件传参的简单示例
2021/01/05 Python
matplotlib绘制多子图共享鼠标光标的方法示例
2021/01/08 Python
使用html5实现表格实现标题合并的实例代码
2019/05/13 HTML / CSS
Airbnb爱彼迎官网:成为爱彼迎房东,赚取收入
2019/03/14 全球购物
Talbots官网:美国成熟女装品牌
2019/11/15 全球购物
晚宴邀请函范文
2014/01/15 职场文书
就业协议书
2014/09/12 职场文书
2015年销售员工作总结范文
2015/04/07 职场文书
人生一定要学会的三样东西:放下、忘记、珍惜
2019/08/21 职场文书
Mysql 用户权限管理实现
2021/05/25 MySQL
Python Flask搭建yolov3目标检测系统详解流程
2021/11/07 Python