事件是用户或浏览器自己执行的某种动作,是文档或者浏览器发生的一些交互瞬间,比如点击(click)按钮等。JS与html之间的交互式通过事件实现的 DOM 支持大量事件
<html> <body> <div id="div1"> <div id="div2"> <button></button> </div> </div> </body> </html>
当点击按钮button,页面上哪些元素会出发这个事件,上面的div2,div1等是否也会出发这个点击事件。
这就牵扯到事件流,从上面的思考,我们知道它描述的是事件触发顺序,那上文中是按钮和其容器元素都触发吗,它们谁先触发呢?这可不是确定的,得看是哪种类型的事件流了。
事件捕获
看上面的代码
首先按照 Window–>Document–>html–>body–>div1—>div2–>button顺序看有没有函数监听。即从外向内找监听函数,叫事件捕获
事件冒泡
然后按照 botton–>div2–>div1–>body–>html–>Document–>Window顺序看有没有函数监听。即从内向外找监听函数,叫事件冒泡
如图所示
DOM事件流
事件流有三个阶段:事件捕获阶段,目标阶段,事件冒泡阶段
事件绑定API
W3C: xxx.baba.addEventListener(‘click’, fn, bool), 如果bool不传或为falsy, 则fn使用事件冒泡, 反之则fn使用事件捕获。
如果bool不传或为falsy就让fn走冒泡,即当浏览器在冒泡阶段发现xxx有监听函数 就会调用fn并提供事件信息
如果bool为true就让fn走捕获 即当浏览器在捕获阶段发现xxx有监听函数 调用fn并提供事件信息
特例
只有一个div被监听(不考虑父子同时被监听)
fn分别在捕获阶段和冒泡阶段监听click事件
用户点击的元素就是开发者监听
div.addEventLisenter('click', f1) div.addEventLisenter('click',f2,true) 请问,f1先执行还是f2先执行? 调换位置 div.addEventLisenter('click',f2,true) div.addEventLisenter('click', f1) 谁先执行 错误答案:f2先执行 正确答案:谁先监听谁先执行
取消冒泡
捕获不可以取消,但是冒泡可以
e.stopPropagation() 可以中断冒泡,浏览器不在往上走
不可阻止默认动作
有些事件不能阻止默认动作
MDN搜索scroll event
Bubbles–>该事件是否冒泡
Cancelable –> 开发者是否可以阻止冒泡