event事件对象有三种易混淆的方法,本文讲述他们之间的区别:javascript
首先,咱们看看他们在MDN上的介绍:html
咱们来看一个代码示例,当点击一个form中的submit按钮时会将form提交处理,此时若是使用Event.preventDefault,就能够在点击submit按钮时避免表格提交。java
<form id="myForm" action="/my-handling-form-page" method="post"> <div> <label for="name">姓名:</label> <input type="text" id="name" /> </div> <div> <label for="mail">电子邮箱:</label> <input type="email" id="mail" /> </div> <div> <label for="msg">消息:</label> <textarea id="msg"></textarea> </div> <div class="button"> <button type="submit">发送你的消息</button> </div> </form>
$('#myForm').on('submit', function(e) { e.preventDefault(); // 什么都不会发生 });
Event.preventDefault能确保表格不会被提交,但他不能阻止来自冒泡阶段的submit或点击事件,其余两种方法就是解决这个问题的。post
stopPropagation 保证当前事件再也不进一步冒泡,经过如下代码示例说明:网站
<div class="container"> <a href="#" class="element">点击我!</a> </div>
$('.container').on('click', function(e) { console.log('container 被点击了'); }); $('.element').on('click', function(e) { e.preventDefault(); // 此时连接不会跳转 console.log('element 被点击了'); });
此时点击连接,console会显示:code
"element 被点击了" "container 被点击了"
这时若是添加Event.stopPropagation:orm
$('.container').on('click', function(e) { console.log('container 被点击了'); }); $('.element').on('click', function(e) { e.preventDefault(); // 此时连接不会跳转 e.stopPropagation(); // 此时事件冒泡被阻止 console.log('element 被点击了'); });
再次点击连接,会看到:htm
"element 被点击了"
以上两种方法已经能够解决咱们在事件处理中90%的问题,接下来介绍一种没法解决情形。
一样是使用上面的示例,但此次咱们给<a/>添加2个class,一个是被全部<a/>共享的class: item,另外一个是独有的class: element,假设这两个class对当前网站的功能很重要。对象
<div class="container"> <a href="#" class="item element">Click Me!</a> </div>
咱们首先使用以前提到的Event.stopPropagation事件
$('.element').on('click', function(e) { e.preventDefault(); // 此时连接不会跳转 e.stopPropagation(); // 此时事件冒泡被阻止 console.log('element 被点击了'); }); $('.item').on('click', function(e) { console.log('item 被点击了'); });
当咱们点击<a/>时,将会显示:
"item 被点击了" "element 被点击了"
这个现象会发生是由于item与element在DOM中是被平等对待的,与以前<a/>被点击而后冒泡到父级div不一样,此次咱们点击同时触发了item与element的事件,此时使用stopPropagation没法阻止这种事件。
stopImmediatePropagation登场~
他能够阻止事件冒泡而且阻止相同事件的其余侦听器被调用。
$('.element').on('click', function(e) { e.preventDefault(); // 此时连接不会跳转 e.stopImmediatePropagation(); // item的点击事件将被阻止 console.log('element 被点击了'); }); $('.item').on('click', function(e) { console.log('item 被点击了'); });
这里咱们要注意的一点是:stopImmediatePropagation的代码要尽可能放到其余同级竞争事件代码的上面,如上面的例子中,为了使stopImmediatePropagation起做用,咱们将element的事件监听代码放到了item以前!
运行最后一例中的代码,将只会看到:
"element 被点击了"