javascript事件监听与事件委托实例详解


Posted in Javascript onAugust 16, 2019

本文实例讲述了javascript事件监听与事件委托。分享给大家供大家参考,具体如下:

事件监听与事件委托

在js中,常用到element.addEventListener()来进行事件的监听。但是当页面中存在大量需要绑定事件的元素时,这种方式可能会带来性能影响。此时,我们可以用事件委托的方式来进行事件的监听。

每个事件都经历三个阶段

  • 捕获
  • 到达目标
  • 冒泡

事件委托需要用到事件的冒泡,冒泡就是事件发生时,上层会一层一层的接收这个事件。

如下页面结构:

<body>
  <div id="div1">
    <div id="div2">
      <button>按钮</button>
    </div>
  </div>
</body>

当点击按钮,首先button接收到事件,然后向上层冒泡,接着id="div1"接收到事件,接着是id="div2",一直到达document的顶层。

所以可以添加一个事件处理器到父级,由他接收所有子节点的事件信息。这就是事件委托。

事件监听与事件委托性能比较

通过构建若干个button元素,并为其绑定事件监听器来比较事件监听与事件委托的性能。

1.构建若干个button元素,并添加到body中

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <title></title>
</head>
<body id='body'>
  <script type="text/javascript">
    var body = document.getElementById('body');
    var fragment = document.createDocumentFragment();
    for (var i = 0; i < 100; i++) {
      var btn = document.createElement('button');
      btn.id = i;
      btn.className = 'btn';
      btn.type = 'button';
      btn.innerText = '按钮'
      fragment.appendChild(btn);
    }
    body.appendChild(fragment);
  </script>
</body>
</html>

此时页面生成了100个按钮,id为0到99,class为'btn';fragment是一个文档片段,相比较下面这种代码的好处是

for(var i = 0;i<100;i++){
  var btn=document.createElement('button');
  body.appendChild(btn);
}

前者页面只重排一次,后者页面重排了100次;所以若遇到大模块添加dom时,最好使用fragment

2.为button绑定事件监听器,并设置时间戳

var btn = document.querySelectorAll('.btn');
var date1 = new Date();
for (var i = 0; i < btn.length; i++) {
    (function(i) {
      btn[i].addEventListener('click', function() {
        console.log(i);
      });
    })(i)
}

3.给body绑定click事件,实现事件的委托

var date2 = new Date();
body.addEventListener('click', function(e) {
    var element = e.target;
    if (element.className == 'btn') {
      console.log(element.id);
    }
})
var date3 = new Date();

下面我们来通过时间戳分析一下这两种方式的性能。

console.log(date2 - date1);
console.log(date3 - date1);

通过改变button的数量,得到以下数据(单位:ms):

在360兼容模式下:

  • 当button数量为100时,平均为 6 0
  • 当button数量为400时,平均为 20 0
  • 当button数量为1000时,平均为 48 0

在新版谷歌下:

  • 当button数量为1000时,平均为 3 0

可见当页面中有大量元素需要绑定事件时,并不是所有的事件都会被触发,而这时对所有需要监听的元素都绑定事件处理器无疑是要花费代价的,而通过事件委托的方式可以很好的解决性能问题,不需要为每个元素都绑定事件监听器。但是要写一些逻辑代码来判断事件源。所以,如果你的web项目对性能要求极为苛刻,事件委托也不失于一种优雅的选择

PS:这里再为大家附上javascript系统自带事件参考表供大家参考查询:

javascript事件与功能说明大全:
http://tools.3water.com/table/javascript_event

更多关于JavaScript相关内容可查看本站专题:《JavaScript事件相关操作与技巧大全》、《JavaScript常用函数技巧汇总》、《javascript面向对象入门教程》、《JavaScript错误与调试技巧总结》、《JavaScript数据结构与算法技巧总结》及《JavaScript数学运算用法总结》

希望本文所述对大家JavaScript程序设计有所帮助。

Javascript 相关文章推荐
js对象的构造和继承实现代码
Dec 05 Javascript
javascript实现tabs选项卡切换效果(自写原生js)
Mar 19 Javascript
Jquery封装tab自动切换效果的具体实现
Jul 13 Javascript
jQuery实现自动调整字体大小的方法
Jun 15 Javascript
js实现对ajax请求面向对象的封装
Jan 08 Javascript
JS实现向iframe中表单传值的方法
Mar 24 Javascript
浅谈在Vue-cli里基于axios封装复用请求
Nov 06 Javascript
小程序图片剪裁加旋转的示例代码
Jul 10 Javascript
vue框架制作购物车小球动画效果实例代码
Sep 26 Javascript
Object.keys() 和 Object.getOwnPropertyNames() 的区别详解
May 21 Javascript
小程序实现上下切换位置
Nov 16 Javascript
js实现简单图片拖拽效果
Feb 22 Javascript
使用Vue-Awesome-Swiper实现旋转叠加轮播效果&amp;平移轮播效果
Aug 16 #Javascript
详解Vue中组件传值的多重实现方式
Aug 16 #Javascript
详解vue+axios给开发环境和生产环境配置不同的接口地址
Aug 16 #Javascript
JavaScript JSON数据处理全集(小结)
Aug 15 #Javascript
JointJS JavaScript流程图绘制框架解析
Aug 15 #Javascript
基于vue写一个全局Message组件的实现
Aug 15 #Javascript
vue element-ui table组件动态生成表头和数据并修改单元格格式 父子组件通信
Aug 15 #Javascript
You might like
星际争霸兵种名称对照表
2020/03/04 星际争霸
PHP实现数组array转换成xml的方法
2016/07/19 PHP
使用vs code编辑调试php配置的方法
2019/01/29 PHP
JavaScript Array Flatten 与递归使用介绍
2011/10/30 Javascript
jquery实现图片按比例缩放示例
2014/07/01 Javascript
JavaScript中的console.trace()函数介绍
2014/12/29 Javascript
JS烟花背景效果实现方法
2015/03/03 Javascript
JQuery调用绑定click事件的3种写法
2015/03/28 Javascript
jQuery判断一个元素是否可见的方法
2015/06/05 Javascript
jquery UI Datepicker时间控件的使用方法(终结版)
2015/11/07 Javascript
jQuery内存泄露解决办法
2016/12/13 Javascript
WebSocket实现简单客服聊天系统
2017/05/12 Javascript
详解使用nodeJs安装Vue-cli
2017/05/17 NodeJs
Angular2 之 路由与导航详细介绍
2017/05/26 Javascript
bootstrap精简教程_动力节点Java学院整理
2017/07/14 Javascript
JavaScript callback回调函数用法实例分析
2018/05/08 Javascript
如何基于JS截获动态代码
2019/12/25 Javascript
VUE实时监听元素距离顶部高度的操作
2020/07/29 Javascript
js实现淘宝浏览商品放大镜功能
2020/10/28 Javascript
python中enumerate函数用法实例分析
2015/05/20 Python
Python使用面向对象方式创建线程实现12306售票系统
2015/12/24 Python
Tensorflow的可视化工具Tensorboard的初步使用详解
2018/02/11 Python
计算机二级python学习教程(1) 教大家如何学习python
2019/05/16 Python
新手入门Python编程的8个实用建议
2019/07/12 Python
Python Opencv任意形状目标检测并绘制框图
2019/07/23 Python
浅谈keras的深度模型训练过程及结果记录方式
2020/01/24 Python
Python IDLE或shell中切换路径的操作
2020/03/09 Python
python MultipartEncoder传输zip文件实例
2020/04/07 Python
详解python with 上下文管理器
2020/09/02 Python
Python类绑定方法及非绑定方法实例解析
2020/10/09 Python
css3动画事件—webkitAnimationEnd与计时器time事件
2013/01/31 HTML / CSS
H5 canvas中width、height和style的宽高区别详解
2018/11/02 HTML / CSS
FitFlop美国官网:英国符合人体工学的鞋类品牌
2018/10/05 全球购物
Java servlet面试题
2012/03/04 面试题
会展策划与管理专业大学生职业生涯规划
2014/02/07 职场文书
辩论会主持词
2015/07/03 职场文书