JavaScript中的event.stopPropagation方法用于阻止事件冒泡,这样该事件不会继续向上级元素传递。
不过今天我想讲的是event.stopImmediatePropagation,它除了具有event.stopPropagation方法的阻止事件冒泡的功能外,还有另一个功能,就是会中止执行在它后面添加/执行的同类型事件。也就是说干完我这件事件,后面的同类型的事情就都不用干了。
示例:
document.body.addEventListener("click", function () { console.log("1"); }); document.body.addEventListener("click", function (ev) { // 在它后面添加的同类型函数不会再执行了,但是早于它添加的函数还是会执行 ev.stopImmediatePropagation(); console.log("2"); }); document.body.addEventListener("click", function () { console.log("3"); });
本来,由addEventListener添加的同类型事件会按照添加的顺序依次执行。这个例子中就是点击页面会依次输出1、2、3。
在2中加了ev.stopImmediatePropagation()之后,第二个添加的事件执行完,后面添加的同类型事件就不会执行了——不会输出3了。
注意:
1.stopImmediatePropagation方法会阻止的是同类型的,比如在click事件里执行了stopImmediatePropagation方法,并不能阻止在其后添加的其他类型的事件。
2.在执行stopImmediatePropagation的事件里,在stopImmediatePropagation后面的代码依然会执行。(如上例会继续输出2)。
ps:jQuery有个event.isImmediatePropagationStopped方法来检测该事件上是否设置了stopImmediatePropagation方法。但是原生JavaScript里好像没自带这个检测的方法。
JavaScript中阻止事件冒泡
原生JavaScript写法附带兼容性处理:
if (!!window.attachEvent) { //区分浏览器指派事件 document.getElementById("a").attachEvent("onclick",fun,false); }else{ document.querySelector("#a").addEventListener("click",fun,false); } function fun (event) { //处理event对象的兼容性 var e=event||window.event; //firefox里的event是临时的,不是window下的全局变量 //停止事件冒泡 e.stopPropagation?e.stopPropagation():e.cancelBubble=true; //低版本ie使用cancelBubble属性,其他浏览器使用stopPropagation方法 //阻止浏览器默认行为 e.preventDefault?e.preventDefault():e.returnValue = false; //低版本ie设置returnValue属性,其他浏览器使用preventDefault方法 }
IE8及更低版本的IE,添加事件要使用私有的attachEvent(),也不支持stopPropagation()和preventDefault(),真是毒瘤啊。
如果使用jQuery的话,写起来更加方便,因为jQuery已经做了兼容性处理,我们用w3c标准方法就行了:
$("a").click(function (e) { e.stopPropagation(); //停止事件冒泡 e.preventDefault(); //阻止浏览器默认行为 return false; //同时停止冒泡和阻止默认行为。 });
注意,jQuery中的return false和原生JavaScript里的return false是有区别的:
原生JavaScript中的return false不会停止冒泡,只会阻止默认行为。但jQuery中的return false会同时停止冒泡和阻止默认行为。