JavaScript事件(二)冒泡与委派

本文深入探讨了事件冒泡的概念,解释了如何通过event.cancelBubble阻止事件冒泡,并通过示例展示了事件委托的实现,允许对动态添加的元素进行事件处理。此外,还详细阐述了事件的绑定方式,包括addEventListener和attachEvent,以及它们在事件传播过程中的差异,包括捕获阶段、目标阶段和冒泡阶段。最后,讨论了W3C的事件传播标准和不同浏览器的实现差异。

  • 事件冒泡(Bubble)

-所谓冒泡指的就是事件的向上传导,当后代元素上的事件被触发时,其祖先元素的相同事件也会被触发

-在开发中大部分情况冒泡都是有用的,如果不希望冒泡发生可以通过事件对象取消冒泡event.cancelBubble=true。

-bubble事件属性返回一个布尔值,如果事件是冒泡类型,则返回true,否则返回false。

例:部分代码

var box=document.getElementById("box");

var innerBox=document.getElementById("innerBox");

innerBox.onclick=function(event){

//事件对象

event=event||window.event;

//取消冒泡

event.cancelBubble=true;

alert("innerBox的点击事件被触发了");

};

box.onclick=function(event){

//事件对象

event=event||window.event;

//取消冒泡

event.cancelBubble=true;

alert("box的点击事件被触发了");

};

document.body.onclick=function(){

alert("body的点击事件被触发了");

}

我们希望只绑定一次事件

  • 事件的委派

指将事件统一绑定给元素共同的祖先元素,这样当后代元素上的事件触发时,会一直冒泡到祖先元素,从而通过祖先元素的响应函数来处理事件,即可应用到多个元素上,即使元素时后添加的,我们可以尝试将其绑定给元素的共同的祖先元素。

实例:为每个a标签绑定一个单击响应事件,新添加的超链接也不需要重新绑定

<body>

<button id="btn">添加列表项</button>

<ul id="list">

<li><a href="javascript:;">列表一</a></li>

<li><a href="javascript:;">列表二</a></li>

<li><a href="javascript:;">列表三</a></li>

</ul>

<script>

window.onload=function(){

var list=document.getElementById("list");

var allA=list.getElementsByTagName("a");

var btn=document.getElementById("btn");

btn.onclick=function(){

var li=document.createElement("li");

li.innerHTML='<a href="javascript:;">新建列表项</a>';

list.appendChild(li);

}

list.onclick=function(event){

event=event||window.event;

// console.log(event.target.nodeName);

if(event.target.nodeName=="A"){

alert("a标签被点击了");

}

}

}

</script>

</body>

  • 事件的绑定

语法:对象.事件=函数形式绑定事件

它只能同时为同一个元素绑定同一事件一次,不能绑定多次,如果绑定多次,后面的会覆盖掉前面的

  1. addEventListener()

通过这个方法 也可以为元素绑定响应函数

参数说明:

-事件的字符串不加on

-回调函数,当事件触发时该函数会被调用

-是否在捕获阶段触发事件,都需要一个布尔值,一般传false;

使用addEventListener()可以同时为一个元素的相同事件绑定多个响应函数

这样当事件被触发时,响应函数将会按照函数的绑定顺序执行

btn.addEventListener("click",function(){

alert(1);

},false);

btn.addEventListener("click",function(){

alert(2);

},false);

  1. attachEvent()

在IE8中可以使用attachEvent()来绑定事件

参数:

-事件的字符串要on

-回调函数,可以同时为一个事件绑定多个处理函数,不用的是他是后绑定先执行,执行顺序和addEventListener()相反

btn.attachEvent("onclick",function(){

alert(1);

});

btn.attachEvent("onclick",function(){

alert(2);

});

  1. This

addEventListener()中的this,是绑定事件的对象

attachEvent()中的this,是window

需要统一两个方法的this

99

 

  • 事件的传播

  - 关于事件的传播网景公司和微软公司有不同的理解

  - 微软公司认为事件应该是由内向外传播,也就是当事件触发时,应该先触发 当前元素上的事件,然后再向当前元素的祖先元素上传播,也就说事件应 该在冒泡阶段执行。

- 网景公司认为事件应该是由外向内传播的,也就是当前事件触发时,应该先触发当前元素的最外层的祖先元素的事件,然后在向内传播给后代元素

- W3C综合了两个公司的方案,将事件传播分成了三个阶段

  1.捕获阶段

  - 在捕获阶段时从最外层的祖先元素,向目标元素进行事件的捕获,但是默认此时不会触发事件

2.目标阶段

- 事件捕获到目标元素,捕获结束开始在目标元素上触发事件

3.冒泡阶段

- 事件从目标元素向他的祖先元素传递,依次触发祖先元素上的事件

- 如果希望在捕获阶段就触发事件,可以将addEventListener()的第三个参数设置为true

  一般情况下我们不会希望在捕获阶段触发事件,所以这个参数一般都是false

  - IE8及以下的浏览器中没有捕获阶段

W3C:万维网联盟,是Web技术领域最具权威和影响力的国际中立性技术标准机构

### JavaScript 事件处理中的捕获、冒泡和委托 #### 捕获冒泡的概念 在JavaScript中,DOM树上的事件流分为三个阶段:捕获阶段、目标阶段以及冒泡阶段。对于大多数浏览器而言,在默认情况下只会经历目标阶段和冒泡阶段。 - **捕获阶段**:从最外层的祖先元素向内传递到触发事件的具体元素。 - **目标阶段**:到达实际发生事件的那个特定元素上。 - **冒泡阶段**:由具体的目标元素向外层层向上返回至文档根节点[^1]。 #### 使用 `addEventListener` 方法配置不同阶段的行为 为了能够响应不同的事件传播阶段,可以利用 `element.addEventListener()` 函数,并通过其第三个参数来决定是否启用捕获模式: ```javascript // 启用捕获阶段监听 someElement.addEventListener('click', function(event){ console.log('Capturing phase'); }, true); // 默认为冒泡阶段监听 someElement.addEventListener('click', function(event){ console.log('Bubbling phase'); }); ``` 上述代码展示了如何分别针对捕获期和冒泡期内发生的点击事件注册相应的处理器[^3]。 #### 实现事件委托 考虑到大型应用程序可能涉及大量相似类型的子组件,直接给每一个单独绑定事件可能会造成不必要的资源消耗。因此推荐采用一种称为“事件委派”的技术——即把事件监听器附加在一个共同父容器上来间接管理多个后代元素上的相同类型事件。 下面是一个简单的例子说明了这一点: ```html <ul id="myList"> <li>Item 1</li> <li>Item 2</li> <!-- 更多列表项 --> </ul> <script> document.getElementById('myList').addEventListener('click', (event) => { if (!event.target.matches('li')) return; const itemText = event.target.textContent.trim(); alert(`You clicked on ${itemText}`); }); </script> ``` 在这个案例里,即使 `<ul>` 下面有成百上千个 `<li>` 子标签也不必分别为它们各自设立独立的点击监听逻辑;相反只需要一次性的设定好作用于整个无序列表即可实现同样的效果[^2]。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值