在介绍事件的冒泡与捕获之前,我们先介绍为一个元素注册多个相同事件:
比如: 我们给一个盒子注册两次点击事件
//可以给同名的事件,绑定多个事件处理程序
//语法:对象.addEventListener(参数1,参数2,参数3);
//参数1:事件名(字符串),不要加on 例如:click 、 mouseover 、mouseout
//参数2:事件处理程序(函数名),当事件触发后哪个函数来处理
//参数3:是一个bool类型,可以不传,默认为fasle(代表冒泡)跟冒泡和捕获有关
//如果是true则表示捕获阶段
//如果有同名事件不会覆盖,而是会依次执行
//IE8及以前的版本不支持
btn.addEventListener('click',function ( ) {
alert('11111');
},false);
btn.addEventListener('click',function ( ) {
alert('2222');
},false);
现在介绍事件冒泡与事件捕获:
事件冒泡:
如果一个元素的事件被触发,那么它所有的父级元素的同名事件都会被触发.
注意点:只有当父级拥有同名事件的时候才会被触发.
window.onclick = function () {
alert("window被点击了");
}
document.onclick = function () {
alert("文档被点击了");
}
document.documentElement.onclick = function () {
alert("html被点击了");
}
document.body.onclick = function () {
alert("body被点击了");
}
document.getElementById("box").onclick = function () {
alert("我是骚粉的大盒子");
};
上述代码的执行顺序是:
box元素--> body-->HTML-->document-->window
事件捕获:
从最顶级的父元素一级一级往下找子元素触发同名事件,直到触发事件的元素为止.
注意点1:是去寻找与与父元素注册的同名事件的子元素
注意点2:因为事件捕获,只能通过addEventListener并且参数写true才是事件捕获
注意点3:其他情况都是冒泡(不是通过addEventListener添加、addEventListener参数为false)
window.addEventListener("click", function () {
alert("这是window");
},true)
document.addEventListener("click", function () {
alert("这是document");
},true)
document.documentElement.addEventListener("click", function (e) {
e = e || window.event;
alert("这是html");
// e.stopPropagation();//阻止事件冒泡和事件捕获
},true)
document.body.addEventListener("click", function () {
alert("这是body");
},true)
//参数3:默认是false,代表是支持事件冒泡
box.addEventListener("click", function () {
alert("这是box");
},true)
上述代码的执行顺序是:
window-->document-->HTML-->body-->box元素
我们知道了事件捕获以及事件的冒泡原理,但是有的时候,我们就只想让其子元素单独触发或者让其父元素单独触发,此时就需要用到阻止事件的捕获以及冒泡的方法.
* 1.阻止事件冒泡:让同名事件不要在父元素中冒泡(触发)
* 说人话:点击一个元素只会触发当前元素的事件,不会触发父元素的同名事件
* 语法: 事件对象.stopPropagation() IE8及之前不支持
* 事件对象.cancelBubble = true IE8之前支持
* 注意:如果想要阻止事件冒泡,一定要在触发事件的函数中接收事件对象
*2.阻止事件捕获:
*事件对象.stopPropagation() 除了可以阻止冒泡还可以阻止捕获
*IE8及以前没有捕获!
好了,我们利用事件的冒泡写一个案例:
需求:移入li标签颜色改变.
思路:如果想给父元素的多个子元素添加事件,我们可以只需要给父元素添加事件即可,然后通过获取事件源(e.target)就可以得知是哪一个子元素触发了这个事件
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
* {
margin: 0;
padding: 0;
}
ul {
border: 1px solid red;
width: 500px;
text-align: center;
margin: 100px auto;
}
#ul1 li {
list-style: none;
line-height: 30px;
font-size: 20px;
border: 1px solid #ccc;
}
</style>
</head>
<body>
<ul id="ul1">
<li>我是第1个li标签</li>
<li>我是第2个li标签</li>
<li>我是第3个li标签</li>
<li>我是第4个li标签</li>
<li>我是第5个li标签</li>
<li>我是第6个li标签</li>
<li>我是第7个li标签</li>
<li>我是第8个li标签</li>
<li>我是第9个li标签</li>
<li>我是第10个li标签</li>
</ul>
<script>
//需求: 1.给10个li标签移入添加背景高亮
// 2.移出背景颜色恢复
//思路:
// 给ul注册鼠标移入事件,通过获取事件源(e.target)就可以得知是哪一个子元素触发了这个事件
var ul1 = document.getElementById("ul1");
var DefalutColor = null; //全局变量存储默认的背景色
ul1.onmouseover = function(e){
//获取到的是对应的li标签对象
// console.log(e.target);
DefalutColor = e.target.style.backgroundColor; //将li标签默认的背景色赋给defalutColor
e.target.style.backgroundColor = 'yellow';
}
ul1.onmouseout = function(e){
e.target.style.backgroundColor = DefalutColor; //li标签默认的背景色
}
</script>
</body>
</html>
我们现在来探讨jQuery里面的关于事件的操作:
//解绑事件
$(selector).off();
注意点:
*1.如果不传参数就是解绑所有事件
*2.如果传参数就是解绑指定事件
//事件的触发
$(selector).click();
// event.stopPropagation() 阻止事件冒泡行为
// event.preventDefault() 阻止浏览器默认行为
// return false:既能阻止事件冒泡,又能阻止浏览器默认行为。