事件冒泡与事件捕获
事件冒泡和捕获分别是是由微软和网景公司提出的,这两个概念都是为了解决页面中事件流(事件发生顺序)的问题。
<div>
<p>点击</p>
</div>
事件冒泡: 子级元素先触发,父级元素后触发,即p先触发,div后触发。发生事件的顺序为 p -> div -> body -> html -> document。
事件捕获: 父级元素先触发,子级元素后触发,即div先触发,p后触发。发生事件的顺序为 document -> html -> body -> div -> p。
在DOM0级事件中(ele.onclick=function(){} ),在IE、Firefox、Chrome、opera下事件执行顺序都是事件冒泡。
在DOM2级事件中(ele.addEventListener(event, fn, boolean)),当第3个参数为true时表示事件捕获,为false时表示事件冒泡,默认为false。
事件委托
事件委托: 利用事件冒泡的原理,将多个子元素上的(一类型)事件,放在父元素上,在父元素上创建一个事件处理程序来管理这一类型的所有事件。
事件委托的优点:
1) 由于每一个函数都是对象,对象会占用内存,内存的占用关系到性能,而使用事件委托后,会减少事件处理程序。因此,减少了内存占用,性能更好。
2) 如果要为许多DOM元素绑定事件,需要多长访问DOM,设置事件处理程序所需时间更长,整个页面就绪需要的时间越多。事件委托技术可以避免对每个字元素添加事件监听器,减少操作DOM节点的次数,从而减少浏览器的重绘和重排,提高代码的性能。
例:
<ul>
<li data-id="1">1</li>
<li data-id="2">2</li>
<li data-id="3">3</li>
</ul>
<script>
let ulEle = document.querySelector('ul');
ulEle.onclick = function (event) {
let val = event.target.dataset.id;
if (typeof val !== 'undefined') {
alert(val);
}
}
</script>
扩展
DOM0级事件绑定和DOM2级事件绑定
DOM0级事件绑定
DOM0级事件绑定的原理
1.给当前元素的某一私有属性(onXXX)赋值的过程;(之前属性默认值是null,如果我们赋值了一个函数,就相当于绑定了一个方法)
2.当我们赋值成功(赋值一个函数),此时浏览器会把DOM元素和赋值的的函数建立关联,以及建立DOM元素的行为监听,当某一行为被用户触发,浏览器会把赋值的函数执行
DOM0级事件绑定的特点:
1.在DOM0级事件绑定中,只能给当前元素的某一个行为绑定一个方法,绑定多个方法时,最后一次绑定的事件会替换前面绑定的。
2.移除事件绑定时只需要赋值为null。
例:
// 绑定事件
btn.onclick = function() {
console.log('123');
// 移除事件
btn.onclick = null;
}
DOM2级事件绑定:
DOM2级事件绑定的原理
1.DOM2级事件绑定使用的 addEventListener/attachEvent方法都是在eventTarget这个内置类的原型上定义的,调用的时候,首先要通过原型链找到这个方法,然后执行完成事件的绑定效果。
2.浏览器会给当前元素的行为开辟一个事件池(事件队列)[浏览器有一个统一的事件池,每个元素绑定的行为都在这里,通过相关标准区分],通过 addEventListener/attachEvent进行事件绑定时,会把绑定的方法放在事件池中。
3.当元素的某一行为被触发,浏览器回到对应事件池中,把当前放在事件池的所有方法按序依次执行
DOM2级事件绑定的特点
1.所有DOM0支持的行为,DOM2都可以用,DOM2还支持DOM0没有的事件行为(这样说比较笼统)【浏览器会把一些常用事件挂载到元素对象的私有属性上,让我们可以实现DOM0事件绑定,DOM2:凡是浏览器给元素天生设置的事件在DOM2中都可以使用】
2.DOM2中可以给当前元素的某一事件行为绑定多个不同方法(因为绑定的所有方法都放在事件池中)
3.事件的移除:事件类型、绑定的方法、传播阶段三个完全一致,才可以完成移除(因此在绑定方法时,尽量不要用匿名函数,否则不好移除)
注:在DOM第一代升级迭代的时候,事件绑定依然沿用DOM0级绑定的方式。
例:
// 添加事件
divEle.addEventListener('click', say);
function say() {
console.log(123);
// 移除事件
divEle.removeEventListener('click', say);
}
参考文章:
JS基础知识(十一)DOM0和DOM2级事件:
https://blog.csdn.net/qq_2338...
浅谈事件冒泡与事件捕获: https://segmentfault.com/a/11...
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。