事件流
js 事件的执行过程分为捕获阶段(由外层节点传播到内层节点)和冒泡阶段(由内层节点传播到外层节点),即先执行捕获阶段的代码,后执行冒泡阶段的代码
事件冒泡
js 事件中的代码默认在冒泡阶段执行,以下图为例,点击box2时,会依次触发box2的点击事件【冒泡阶段执行】、box1的点击事件【冒泡阶段执行】、window的点击事件【冒泡阶段执行】。
window.addEventListener("click", function (e) {
if (e.target.id === "box2") {
console.log("点击box2触发window的click事件");
} else if (e.target.id === "box1") {
console.log("点击box1触发window的click事件");
} else {
console.log("触发了window的click事件");
}
});
document.getElementById("box1").addEventListener("click", function (e) {
console.log("触发了box1的click事件");
});
document.getElementById("box2").addEventListener("click", function (e) {
console.log("触发了box2的click事件");
});
事件捕获
给 addEventListener 函数的第三个参数传入 true ,便会将事件中的代码改为在捕获阶段执行,此时点击box2时,会依次触发window的点击事件【捕获阶段执行】,box2的点击事件【冒泡阶段执行】,box1的点击事件【冒泡阶段执行】。
window.addEventListener(
"click",
function (e) {
if (e.target.id === "box2") {
console.log("点击box2触发window的click事件");
} else if (e.target.id === "box1") {
console.log("点击box1触发window的click事件");
} else {
console.log("触发了window的click事件");
}
},
//改为在捕获阶段执行
true
);
document.getElementById("box1").addEventListener("click", function (e) {
console.log("触发了box1的click事件");
});
document.getElementById("box2").addEventListener("click", function (e) {
console.log("触发了box2的click事件");
});
阻止事件的传播
使用
e.stopPropagation()
范例:点击box2时,只触发box2的点击事件,不触发box1和window的点击事件
window.addEventListener("click", function (e) {
if (e.target.id === "box2") {
console.log("点击box2触发window的click事件");
} else if (e.target.id === "box1") {
console.log("点击box1触发window的click事件");
} else {
console.log("触发了window的click事件");
}
});
document.getElementById("box1").addEventListener("click", function (e) {
console.log("触发了box1的click事件");
});
document.getElementById("box2").addEventListener("click", function (e) {
console.log("触发了box2的click事件");
// 阻止事件继续传播
e.stopPropagation();
});
实战范例
需求:
- 点击box2时,只执行window点击事件中通过点击box2触发window点击事件的代码,不执行box1的点击事件代码
- 点击box1时,只执行box1的点击事件代码,不执行window点击事件中通过点击box1触发window点击事件的代码
window.addEventListener(
"click",
function (e) {
if (e.target.id === "box2") {
console.log("点击box2触发window的click事件");
// 阻止事件继续传播
e.stopPropagation();
} else if (e.target.id === "box1") {
return;
console.log("点击box1触发window的click事件");
} else {
console.log("触发了window的click事件");
}
},
true
);
document.getElementById("box1").addEventListener("click", function (e) {
console.log("触发了box1的click事件");
});
document.getElementById("box2").addEventListener("click", function (e) {
console.log("触发了box2的click事件");
});