1.事件的冒泡
指时间的向上传播。
当后代元素的事件被触发时,其祖先元素的相同事件也会被触发。
取消冒泡的方法:event.cancelBubble=true:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
<!--事件的冒泡指的是事件的向上传导。
当后代元素的事件被触发,其祖先元素的相同事件也会被触发
在开发中大部分的冒泡都是有用的如果不希望有事件的冒泡,
可以通过event.cancelBubble=true来取消-->
<script>
window.onload=function(){
var bBox=document.getElementById("bBox");
var sBox=document.getElementById("sBox");
var max=document.getElementById("maxBox");
bBox.onclick=function(){
console.log("bBox");
};
//取消sBox的冒泡
/* sBox.οnclick=function(event){
event=event||window.event;
event.cancelBubble=true;
console.log("sBox");
};
*/
sBox.onclick=function(){
console.log("sBox");
};
max.onclick=function(){
console.log("maxBox");
};
};
</script>
<style>
*{
margin:0px;
padding:0px;
}
#sBox{
width:100px;
height:200px;
background-color: thistle;
}
#bBox{
width:200px;
height:100px;
background-color: olivedrab;
}
</style>
</head>
<body id="maxBox">
<div id="bBox">
<div id="sBox"></div>
</div>
</body>
</html>
执行结果:
点击空白处:
点击bBox:
点击sBox:
取消sBox冒泡之后点击sBox:
2.事件的委派
指将后代元素所共有的事件统一绑定要他们的同一个祖先元素上面。当触发了后代元素相应的事件的时候,会冒泡到祖先元素上,通过祖先元素的响应函数来处理事件
好处:给祖先元素绑定响应事件,减少了后代元素绑定响应函数的次数,提高了程序的效率
例子:
为ul绑定响应函数,当点击超链接的时候响应事件
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
<script>
/*事件的委派
将同一类型的事件绑定给一个祖先元素,当事件在后代元素中被触发时,
会一直冒泡到祖先元素.从而通过祖先的响应函数来处理事件
好处:减少了事件绑定的次数
应用:
为新增的超链接绑定单击相应函数,如果一个个添加的话太过繁琐
直接给祖先元素添加
对后代元素加以判断
如果是,则执行,否则不执行*/
window.onload=function(){
var add=document.getElementById("add");
var parent=document.getElementById("parent");
add.onclick=function(){
var li=document.createElement("li");
li.innerHTML='<a οnclick="javascript:;" class="link">超链接三</a>';
parent.appendChild(li);
};
parent.onclick=function(event){
event=event||window.event;
if(event.target.className=="link")
console.log("你刚才点击了一下超链接");
};
};
</script>
</head>
<body>
<ul id="parent" style="list-style-type: none;">
<li><a onclick="javascript:;" class="link">超链接一</a></li>
<li><a onclick="javascript:;" class="link">超链接二</a></li>
<li><a onclick="javascript:;" class="link">超链接三</a></li>
<li><button id="add">add a</button></li>
</ul>
</body>
</html>
如何识别是不是触发了对应的后代元素
通过event.target.className=“class名”
3.事件的绑定
addEventListener() ------------其他浏览器
attachEvent()--------------------IE8以及以下浏览器
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
<script>
/*通过对象.事件=函数的方式只能为一个事件绑定一个响应函数,
如果绑定了多个响应函数的话,前面的响应函数将会被覆盖掉
为一个事件绑定多个响应函数的方法:
addEventListener();
参数1:触发事件,不要on
参数2:回调函数
参数3:是否在触发的捕获阶段触发,布尔值,一般传入false
响应函数的触发是按正序触发
上面的方法不适用于IE8以及以下浏览器:
IE8以及以下浏览器使用
attachEvent();
参数1:触发事件,要on
参数2:回调函数
响应函数的触发时逆序*/
window.onload=function(){
var but=document.getElementById("but");
/*but.addEventListener("click",function(){
console.log("触发第一个绑定的单击事件");
},false);
but.addEventListener("click",function(){
console.log("触发第二个绑定的单击事件");
},false);
but.addEventListener("click",function(){
console.log("触发第三个绑定的单击事件");
},false);*/
/*var bot=document.getElementById("bot");
bot.attachEvent("onclick",function(){
console.log("IE触发第一个单击事件");
});
bot.attachEvent("onclick",function(){
console.log("IE触发第二个单击事件");
});
bot.attachEvent("onclick",function(){
console.log("IE触发第三个单击事件");
});*/
//创建一个通用的方法myAddEvent(obj,event,callback)
/*参数1:对象
参数2:事件
参数3:回调函数
*/
myAddEvent(but,"click",function(){
console.log("myAddEvent");
});
function myAddEvent(obj,af,callback){
/*addEventListener()中的this,是绑定事件的对象
attachEvent()中的this,是window
如果要使用this的话,可以使用call方法,将obj传入.
例:callback.call(obj)*/
if(obj.attachEvent){
obj.attachEvent("on"+af,callback);
}else{
obj.addEventListener(af,callback,false);
}
}
};
</script>
</head>
<body>
<button id="but">onclick</button>
<button id="bot">IE onclick</button>
</body>
</html>
4.事件的传播
事件的传播
关于事件的传播网景公司和微软公司有不同的理解
-微软公司认为事件应该是由内向外传播,也就是当事件触发时,应该先触发当前元素上的事件
然后再向当前元素的祖先元素向上传播,也就是说事件应该在冒泡阶段执行
-网景公司认为事件应该是由外向内传播的,也就是当前事件触发时,应该先触发当前元素的最外层的祖先元素的事件,然后再向内传播给后代元素
-w3c综合了两个公司的方案,将事件传播分为三个阶段
(1).捕获阶段
在捕获阶段时从最外层的祖先元素,向目标元素进行事件的捕获,但是默认此时不会触发事件
(2).目标阶段
事件捕获到目标元素,捕获结束开始在目标元素上触发事件
(3).冒泡阶段
事件从目标元素向他的祖先元素传递,依次触发祖先元素上的事件
如果希望在捕获阶段就触发事件,可以将addEventListener()的第三个参数设置为true
一般情况下我们不希望在捕获阶段触发事件,所有这个参数一般是false
IE8以及以下的浏览器,没有捕获阶段