作为小白的我,面试总是被问事件流,我虽然没有一脸懵逼,但是也没有说清楚,自己对自己的回复都不满意,何况面试官,回来后我就特别花时间了解了一下,其中的精髓我有点明白了,就是不知道有没有了解到骨髓。
- 啥叫事件?
事件其实分为很多种,窗口事件,表单事件,键盘事件,鼠标事件等,窗口事件有比如onbeforeonload,onblur,onfocus,onload,onresize等,表单事件有比如onblur,onchange,onfocus,onformchange,onselect,onsubmit等,键盘事件有onkeydown,onkeydown,onkeyup,鼠标事件有onclick,ondrag,ondragend,onmousedown,onmousemove,onmouseup,onscroll等。
作为一个前端开发,结合平时的使用情况,下面我主要讲下onclick这个事件,大家能理解事件流就行,至于其他的事件有兴趣的可自行研究下。
- 啥叫事件流
之前看到这个名字这么高大上的感觉,我自己给他加了一个比喻,比如打井。打井的时候钻头一步一步向下,这个过程就是事件捕获阶段,可以截获事件,不让它往下传递,也就是关掉机器,让它停在那里(呔,小样,给我老实呆着!)当然如果你不捕获事件,让他继续传递,它就会传递到最里面的节点,到达目的地,这时钻洞工作结束,以上叫做捕获阶段,到达目的地之后,其实就开始进入目标阶段了 ,这时候就是触发你绑定事件的时候(按照事件绑定的先后顺序),接着,水开始慢慢往上涨啦,这时就是冒泡阶段了,从最里面节点开始,再继续往外传递。不过,这时候也是可以阻止冒泡的,stopPropagation/stopImmediatePropagation,比如你再旁边打了个洞,或者你拿着水泵把水吸走了,哈哈,反正就是没让水继续涨,阻止了冒泡的进行,那也是ok的。 - 具体是怎样
具体怎样还是代码来检验把,网上看到一个很好的例子,自己点击点击看看可能效果吧,嘻嘻。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
</head>
<body>
<div id="a">
<div id="b">
<div id="c"></div>
</div>
</div>
<style>
#a{
width: 300px;
height: 300px;
background: pink;
}
#b{
width: 200px;
height: 200px;
background: blue;
}
#c{
width: 100px;
height: 100px;
background: yellow;
}
</style>
<script>
// 事件流分为三个主要过程,捕获阶段,目标阶段,冒泡阶段,
// 捕获阶段可以通过在addEventListener方法最后一个参数传一个true进去,就可以截获事件了,
// 捕获阶段如果里面阻止了捕获和冒泡,也就是执行了stopPropagation、stopImmediatePropagation方法,那就会被打断传递。
// 到达节点目标之后就是目标阶段了,这时候绑定事件是按照顺序执行的,没有捕获或者冒泡之说
// 目标阶段结束之后就是冒泡阶段,addEventListener方法最后一个参数不传或传false,这时候也可以执行stopPropagation、stopImmediatePropagation方法,阻止事件传递
var a = document.getElementById("a"),
b = document.getElementById("b"),
c = document.getElementById("c");
c.addEventListener("click", function (event) {
// 冒泡阶段
console.log("c1");
});
c.addEventListener("click", function (event) {
// 捕获阶段
console.log("c2");
}, true);
b.addEventListener("click", function (event) {
// 捕获阶段
console.log("b1");
}, true);
b.addEventListener("click", function (event) {
// 冒泡阶段
console.log("b2");
event.stopImmediatePropagation();
});
a.addEventListener("click", function (event) {
// 捕获阶段
console.log("a1");
}, true);
a.addEventListener("click", function (event) {
// 冒泡阶段
console.log("a2")
});
a.addEventListener("click", function (event) {
// 捕获阶段
console.log("a3");
event.stopImmediatePropagation();
}, true);
a.addEventListener("click", function (event) {
// 捕获阶段
console.log("a4");
}, true);
</script>
</body>
</html>