JavaScript事件
事件是文档和浏览器窗口中发生的特定的交互瞬间,我们与浏览器中web页面进行某些类型的交互时,事件就发生了。
事件可能是用户在某些内容上的点击,鼠标经过某个特定元素或按下键盘上的某些按键,事件还可能是web浏览器中发生的事情,比如说某个web页面加载完成,或者是用户滚动窗口或改变窗口大小。
JavaScript事件流
事件流描述的是从页面中接受事件的顺序,但有意思的是,微软(IE)和网景(Netscape)开发团队居然提出了两个截然相反的事件流概念,IE的事件流是事件冒泡流(event bubbling),而Netscape的事件流是事件捕获流(event capturing)。
事件冒泡
事件冒泡由IE提出,即事件开始时由最具体的元素接收,然后逐级向上传播到较为不具体的节点。利用该原理实现事件委托
1 |
|
正如上面我们所说的,它会从一个最具体的的元素接收,然后逐级向上传播, button=>p=>div=>body…事件冒泡可以形象地比喻为把一颗石头投入水中,泡泡会一直从水底冒出水面。
阻止事件冒泡
event.stopPropagation(); 或 event.stopImmediatePropagation(); 或 event.cancelBubble = true;
接着使用上面案例我们现在阻止它的冒泡行为
1 |
|
我们可以看到已经没有冒泡行为,需要注意的是前两个( stopPropagation()和stopImmediatePropagation() ) IE 低版本不支持。
事件捕获
事件捕获由网景提出,事件从最不具体的元素接收到最具体的元素接收
针对上面同样的例子,点击按钮,那么此时click事件会按照这样传播:(下面我们就借用addEventListener的第三个参数来模拟事件捕获流)
1 |
|
正如我们看到的,和冒泡流万全相反,从最不具体的元素接收到最具体的元素接收事件 body=>div=>p=>button
阻止事件捕获
event.stopPropagation(); 或 event.stopImmediatePropagation();
还是使用上面捕获案例来阻止捕获
1 |
|
我们可以看到已经没有捕获行为,需要注意的是前两个( stopPropagation()和stopImmediatePropagation() ) IE 低版本不支持。
DOM事件流
‘DOM2级事件’规定的事件流包含3个阶段,事件捕获阶段、处于目标阶段、事件冒泡阶段。首先发生的事件捕获为截获事件提供机会,然后是实际的目标接收事件,最后一个阶段是事件冒泡阶段,可以在这个阶段对事件做出响应。
在DOM事件流中,事件的目标在捕获阶段不会接收到事件,这意味着在捕获阶段事件从document到 <button> 就停止了,下个阶段是处于目标阶段,于是事件在 <button> 上发生,并在事件处理中被看成冒泡阶段的一部分,然后,冒泡阶段发生,事件又传播回document。
1 |
|
就是这样一个流程,先捕获,然后处理,然后再冒泡出去。
DOM 2级事件处理程序
DOM 2级事件定义了两方法:用于处理添加事件和删除事件的操作: 添加事件 addEventListener() 删除事件 removeEventListener()
所有DOM节点中都包含这两个方法,并且他们都包含3个参数:
- 要处理的事件方式(例如:click,mouseover,dbclick…..);
- 事件处理的函数,可以为匿名函数,也可以为命名函数(但如果需要删除事件,必须是命名函数);
- 一个布尔值,代表是处于事件冒泡阶段处理还是事件捕获阶段(true:表示在捕获阶段调用事件处理程序;false:表示在冒泡阶段调用事件处理程序)。
使用DOM 2级事件处理程序的主要好处是可以添加多个事件处理程序,事件处理会按照他们的顺序触发,通过addEventListener添加的事件只能用removeEventListener来移除,移除时传入的参数与添加时使用的参数必须相同,这也意味着添加的匿名函数将无法移除,(注意:我们默认的第三个参数都是默认false,是指在冒泡阶段添加,大多数情况下,都是将事件处理程序添加到事件的冒泡阶段,这样可以最大限度的兼容各个浏览器)
匿名函数
1 | //这是一个DOM 2级事件 添加事件最简单的方式 |
命名函数
1 |
|
添加两个事件试试
1 |
|
所以说,我们添加两个事件是可以的,事件的顺序就是按照我们程序写的顺序执行的
试试DOM 0级事件处理程序
1 |
|
只执行了第一个事件,第二个被忽略,这并不是我们想要的结果,而addEventLiener是会把两个事件都去执行的。
扩展 - 阻止默认行为
preventDefault
preventDefault它是事件对象(Event)的一个方法,作用是取消一个目标元素的默认行为。既然是说默认行为,当然是元素必须有默认行为才能被取消,如果元素本身就没有默认行为,调用当然就无效了。什么元素有默认行为呢?如链接 <a> ,提交按钮 <input type=”submit”> 等。当Event对象的cancelable为false时,表示没有默认行为,这时即使有默认行为,调用 preventDefault也是不会起作用的。
我们都知道,链接 <a> 的默认动作就是跳转到指定页面,下面就以它为例,阻止它的跳转:
1 |
|
这时候点击 a 标签没有任何动作,不会跳转到对应连接,阻止了它的默认行为。
stopPropagation
stopPropagation也是事件对象(Event)的一个方法,作用是阻止目标元素的冒泡事件,但是会不阻止默认行为。
return false
现在很多js代码都直接使用jQuery来写,在jQuery中使用return false时,相当于同时使用event.preventDefault和event.stopPropagation,它会阻止冒泡也会阻止默认行为。 但是使用原生js写时,return false只会阻止默认行为,不阻止冒泡。
谢谢阅读,以上借鉴自 https://www.cnblogs.com/christineqing/p/7607113.html