事件流
事件流描述的就是从页面中接收事件的顺序。而 IE 和 Netscape 提出了完全相反的事件流概念。IE事件流是事件冒泡,而Netscape的事件流就是事件捕获。
事件冒泡
IE的事件流叫做事件冒泡。即事件开始时由最具体的元素(文档中嵌套层次最深的那个节点)接收,然后逐级向上传播到较为不具体的节点(文档)。所有现代浏览器都支持事件冒泡,并且会将事件一直冒泡到window对象。

事件捕获
事件捕获的思想是不太具体的节点应该更早的接收到事件,而在最具体的节点应该最后接收到事件。事件捕获的用意在于事件到达预定目标之前捕获它。IE9+、Safari、Chrome、Opera和Firefox支持,且从window开始捕获(尽管DOM2级事件规范要求从document)。由于老版本浏览器不支持,所以很少有人使用事件捕获。

addEventListener的第三个参数
addEventListener的第三个参数就是为冒泡和捕获准备的.
addEventListener有三个参数:
1 | element.addEventListener(event, function, useCapture) |
第一个参数是需要绑定的事件
第二个参数是触发事件后要执行的函数
第三个参数默认值是false,表示在事件冒泡阶段调用事件处理函数;如果参数为true,则表示在事件捕获阶段调用处理函数。
冒泡的案例
1 | <div id="click_div"> |
当我们点击click_p的时候,执行结果如下:p 冒泡事件 -> div 冒泡事件
捕获的案例
1 | <div id="click_div"> |
当我们点击click_p的时候,执行结果如下:div 捕获事件 -> p 捕获事件
事件捕获vs事件冒泡
当事件捕获和事件冒泡一起存在的情况,事件又是如何触发呢。

这里记被点击的DOM节点为target节点
- document 往 target节点,捕获前进,遇到注册的捕获事件立即触发执行
- 到达target节点,触发事件(到达target节点,触发事件(对于target节点上,捕获与冒泡事件的执行顺序取决于注册顺序)
- target节点 往 document 方向,冒泡前进,遇到注册的冒泡事件立即触发
1 | <div id="click_div"> |
当我们点击click_p的时候,执行结果如下:div 捕获事件 -> p 冒泡事件 -> p 捕获事件 -> div 冒泡事件
阻止冒泡和捕获
方法一:
cancelBubble 已经不在标准中了,相信迟到会移除这一特性的。
1 | event.cancelBubble = true; // IE下阻止冒泡、捕获 |
方法二:
event.stopPropagation() 方法阻止事件冒泡到父元素,阻止任何父事件处理程序被执行。
1 | event.stopPropagation() // 其它浏览器下阻止冒泡、捕获 |
阻止冒泡的案例
1 | <div id="click_div"> |
当我们点击click_p的时候,执行结果如下:p 冒泡事件
阻止捕获的案例
1 | <div id="click_div"> |
当我们点击click_p的时候,执行结果如下:div 捕获事件