时间冒泡机制
在进行事件触发时或有事件冒泡的存在,会从底层不断往上冒泡进行事件触发。
例如代码:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title></title>
<style type="text/css">
#box{
100px;
height: 100px;
background-color: #333333;
}
#boxson{
50px;
height: 50px;
background-color: #999;
}
</style>
</head>
<body>
<div id="box">
<div id="boxson">
</div>
</div>
<script src="test.js"></script>
</body>
</html>
//test.js
var box = document.getElementById('box');
var boxSon = document.getElementById('boxson');
boxSon.addEventListener('click',function(){
console.log('clicked the boxson!')
})
box.addEventListener('click',function(){
console.log('clicked the box!')
})
当我们点击boxson时,在控制台仍可以看见box的事件也一并触发。这种自下而上的事件触发机制就是事件的冒泡触发。
解决办法
一、使用stopPropagation
修改boxSon监听事件为:
boxSon.addEventListener('click',function(e){
e.stopPropagation()
console.log('clicked the boxson!')
})
二、使用return false
修改box监听事件为:
box.addEventListener('click',function(e){
if(e.target == this){
console.log('clicked the box!')
}
})
判断e.target是否与触发的元素对象一致,一致才触发父元素的事件。
在jQuery中,还有return false等方法,在vue中可以添加@click.prevent组织默认事件的方法阻止冒泡
利用冒泡
冒泡的机制已经熟悉,冒泡不只是会带来麻烦,也可以利用冒泡来实现监听事件的代理。
事件代理,顾名思义,将原本元素标签的事件触发监听交由给其他元素进行代理。
例如一个div中存在多个带有事件监听的子标签:
<div id=‘obj1’>
<a href='#' click = 'func1()' id='a1'></a>
<a href='#' click = 'func2()' id='a2'></a>
<a href='#' click = 'func3()' id='a3'></a>
<a href='#' click = 'func4()' id='a4'></a>
<a href='#' click = 'func5()' id='a5'></a>
...
</div>
此时我们可以利用冒泡机制,在div中进行监听,从而进行统一处理
obj1.addEventListener('click',function(e){
var e=e||window.event;
if(e.target.nodeName.toLowerCase()=='h5'){
alert(e.target.innerHTML);
}
},false);