# 事件冒泡与事件捕获

3 min read
Table of Contents

事件流描述的是从页面中接受事件的顺序,主要是事件冒泡和事件捕获。

事件冒泡

事件冒泡(event bubbling),即事件开始时由最具体的元素接收,然后逐级向上传播到 window 对象。

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Document</title>
</head>
<body>
<div id="myDiv">Click</div>
</body>
</html>

当点击了 div 元素,事件传播 div -> body -> html -> Document -> window。

事件捕获

事件捕获(event capturing),是由事件从 window 对象开始接收事件,然后逐级向下传播到具体元素。

如上代码,点击掉了 div 元素,事件传播 window -> Document -> html -> body -> div。

DOM 事件流

三个阶段:事件捕获阶段,处于目标阶段和事件冒泡阶段。

新增事件和删除事件的操作:addEventListener(type, listener [, options]) 和 removeEventListener(type, listener [, options])

事件委托

事件委托就是利用事件的冒泡原理,把元素的响应事件代理到其父辈元素上,可以减少循环绑定。

<!-- 普通的html列表标签 -->
<ul id="list">
<li>item 1</li>
<li>item 2</li>
<li>item 3</li>
</ul>
/* 普通的遍历元素注册事件监听 */
var items = document.getElementsByTagName('li')
for (var i = 0; i < items.length; i++) {
items[i].addEventListener('click', function (e) {
e.target.parentNode.removeChild(e.target)
})
}
/* 事件委托 */
var list = document.getElementById('list')
list.addEventListener('click', function (e) {
list.removeChild(e.target)
})

event 对象的属性和方法

属性/方法类型说明
targetElement事件的目标
currentTargetElement其事件处理程序当前正在处理事件的那么元素,即触发事件的元素
preventDefaultFunction取消事件的默认行为
stopPropagationFunction取消事件的进一步捕获或冒泡

target 与 currentTarget

<div class="container">
<button>Click me</button>
</div>
const div = document.querySelector('.container')
div.addEventListener('click', (e) => {
console.log('target', e.target)
console.log('currentTarget', e.currentTarget)
})

当我们点击按钮的时候,我们可以看到不同的输出结果

target <button>Click me</button>
currentTarget <div class="container">...</div>
  • targt 是触发事件的根元素
  • currentTarget 是处理该事件的元素

不会触发冒泡的事件

  • scroll
  • blur
  • focus
  • mouseentter
  • mouseleave

其他

React 的事件体系就是基于事件委托建立的,其中有很大的部分都是处理不同事件之间的差异性的,对于这些不会冒泡的事件,React 也进行了处理。

React 的事件系统可以参考上一篇的《React事件系统》

参考链接


More Posts

# React事件系统

3 min read

React 基于 Virtual DOM 实现了一个 SyntheticEvent(合成事件)层,我们所定义的事件处理器会接收到一个 SyntheticEvent 对象的实例。所有事件都自动绑定到最外层上。如果需要访问原生事件对象,可以使用 nativeEvent 属性。

# Promise

7 min read

Promise 对象表示异步操作的最终完成(或失败)及其结果值。