之前对DOM事件相关的概念都一直是一知半解,没有进行过系统的梳理,这几天花时间好好查阅了相关资料,在此做一个总结,对DOM事件相关的知识进行一个系统的梳理,方便以后进行回顾。
- DOM事件类型
大体分为三类
DOM0 | DOM2 | DOM3
DOM0:<div onclick="test"></div>
DOM2:dom.addEventListener(type,cb,boolean)
DOM3 :dom.addEventListener(type,cb,boolean)
主要是在dom2的基础上引入了更多的交互能力
如需了解更多DOM2与DOM3的区别,看这里。 - DOM事件流
- 事件捕获
- 目标阶段
- 事件冒泡
- 事件捕获具体流程
- 大概流程
window->document->body->...dom...->body->document->window
- 解释
先是有window
到document
再到body
,再到目标dom元素,这个阶段是捕获阶段,到达目标元素后,就是目标阶段,然后由目标元素到其父元素一直到window
对象,这个是冒泡阶段。 - 我们在点击页面的一个元素时,浏览器默认是获取dom层级最深的那个元素
- 注意在目标捕获阶段,目标元素上绑定的冒泡和捕获事件是依据它们绑定的先后循序执行的
- stopPropagation和stopImmediatePropagation
stopPropagation
是为了阻止目标元素后的冒泡事件的触发,对当前目标元素的冒泡事件是无法阻止的。stopImmediatePropagation
是阻止目标元素当前触发事件后面绑定的所有事件的触发。注意,是包含当前目标元素的。
- 大概流程
- target和currentTarget以及this
在使用addEventListener
添加事件时,会给回调函数传递一个event
对象,这个对象包含target
和currentTarget
这两个属性
- target
这个target指向的当前事件触发的DOM对象,比如如下结构<div id="f"><p>test</p></div>
,我再div上绑定了事件,实际情况是我点击的p元素,那么当事件在div上捕获或者冒泡到div时,这个target就是指向的p - currentTarget
指向当前事件生效的DOM对象,即绑定事件的DOM对象。 - this
如果回调函数是普通函数,这个this指向事件绑定的DOM对象,等同于currentTarget
。如果是箭头函数,则这个this与调用绑定函数作用域中的this
相同 - DOM0级绑定事件时的
this
<div onclick="test(this)"></div>
因为test(this)
的作用域是在currentTarget
中,所以this
指向currentTarget
<div onclick="test()"></div>
这种写法test中的this指向全局window
- target
- 事件委托/代理
因为事件冒泡和事件捕获,我们可以在目标元素的父元素上绑定事件,通过target
来判断目标对象,从而减少绑定事件数量。 - 自定义事件
- Event
定义事件
let ev = new Event('test',{ bubbles: true});
绑定事件
dom.addEventListener('test',cb,true)
触发事件
dom.dispatchEvent(ev)
- CustomEvent
定义事件
let ev = new CustomEvent('test',{detail:123});
绑定事件
dom.addEventListener('test',cb,true)
触发事件
dom.dispatchEvent(ev)
两者的区别在于CustomEvent
可以携带detail
信息,在整个事件流中传递。
- Event
本文参考自如下资料
1. 事件模型