Javascript stopPropagation 与 stopImmediatePropagation

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/5299740/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-23 16:33:17  来源:igfitidea点击:

stopPropagation vs. stopImmediatePropagation

javascriptjquery

提问by Arjun

What's the difference between event.stopPropagation()and event.stopImmediatePropagation()?

event.stopPropagation()和 和有event.stopImmediatePropagation()什么区别?

回答by Dave

stopPropagationwill prevent any parenthandlers from being executed stopImmediatePropagationwill prevent any parent handlers and alsoany otherhandlers from executing

stopPropagation将防止任何被执行的处理程序stopImmediatePropagation将防止任何父处理程序,并且还任何其他处理程序从执行

Quick example from the jquery documentation:

jquery 文档中的快速示例

$("p").click(function(event) {
  event.stopImmediatePropagation();
});

$("p").click(function(event) {
  // This function won't be executed
  $(this).css("background-color", "#f00");
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

<p>example</p>

Note that the order of the event binding is important here!

请注意,事件绑定的顺序在这里很重要!

$("p").click(function(event) {
  // This function will now trigger
  $(this).css("background-color", "#f00");
});

$("p").click(function(event) {
  event.stopImmediatePropagation();
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

<p>example</p>

回答by Anurag

A small example to demonstrate how both these propagation stoppages work.

一个小例子来演示这两种传播停止是如何工作的。

var state = {
  stopPropagation: false,
  stopImmediatePropagation: false
};

function handlePropagation(event) {
  if (state.stopPropagation) {
    event.stopPropagation();
  }

  if (state.stopImmediatePropagation) {
    event.stopImmediatePropagation();
  }
}

$("#child").click(function(e) {
  handlePropagation(e);
  console.log("First event handler on #child");
});


$("#child").click(function(e) {
  handlePropagation(e);
  console.log("Second event handler on #child");
});

// First this event will fire on the child element, then propogate up and
// fire for the parent element.
$("div").click(function(e) {
  handlePropagation(e);
  console.log("Event handler on div: #" + this.id);
});


// Enable/disable propogation
$("button").click(function() {
  var objectId = this.id;
  $(this).toggleClass('active');
  state[objectId] = $(this).hasClass('active');
  console.log('---------------------');
});
div {
  padding: 1em;
}

#parent {
  background-color: #CCC;
}

#child {
  background-color: #000;
  padding: 5em;
}

button {
  padding: 1em;
  font-size: 1em;
}

.active {
  background-color: green;
  color: white;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="parent">
  <div id="child">&nbsp;</div>
</div>

<button id="stopPropagation">Stop Propogation</button>
<button id="stopImmediatePropagation" ">Stop Immediate Propogation</button>

There are three event handlers bound. If we don't stop any propagation, then there should be four alerts - three on the child div, and one on the parent div.

绑定了三个事件处理程序。如果我们不停止任何传播,那么应该有四个警报——三个在子 div 上,一个在父 div 上。

If we stop the event from propagating, then there will be 3 alerts (all on the inner child div). Since the event won't propagate up the DOM hierarchy, the parent div won't see it, and its handler won't fire.

如果我们阻止事件传播,那么将会有 3 个警报(都在内部子 div 上)。由于该事件不会向上传播 DOM 层次结构,父 div 不会看到它,它的处理程序也不会触发。

If we stop propagation immediately, then there will only be 1 alert. Even though there are three event handlers attached to the inner child div, only 1 is executed and any further propagation is killed immediately, even within the same element.

如果我们立即停止传播,那么只会有 1 个警报。即使有 3 个事件处理程序附加到内部子 div,也只执行 1 个事件处理程序并且任何进一步的传播都会立即终止,即使在同一个元素中也是如此。

回答by Aron Rotteveel

From the jQuery API:

jQuery API

In addition to keeping any additional handlers on an element from being executed, this method also stops the bubbling by implicitly calling event.stopPropagation(). To simply prevent the event from bubbling to ancestor elements but allow other event handlers to execute on the same element, we can use event.stopPropagation() instead.

Use event.isImmediatePropagationStopped() to know whether this method was ever called (on that event object).

除了阻止执行元素上的任何其他处理程序外,此方法还通过隐式调用 event.stopPropagation() 来停止冒泡。为了简单地防止事件冒泡到祖先元素但允许其他事件处理程序在同一元素上执行,我们可以使用 event.stopPropagation() 代替。

使用 event.isImmediatePropagationStopped() 了解是否曾经调用过此方法(在该事件对象上)。

In short: event.stopPropagation()allows other handlers on the same element to be executed, while event.stopImmediatePropagation()prevents everyevent from running.

简而言之:event.stopPropagation()允许执行同一元素上的其他处理程序,同时event.stopImmediatePropagation()阻止每个事件运行。

回答by SLaks

event.stopPropagationwill prevent handlers on parent elements from running.
Calling event.stopImmediatePropagationwill also prevent other handlers on the same element from running.

event.stopPropagation将阻止父元素上的处理程序运行。
调用event.stopImmediatePropagation还将阻止同一元素上的其他处理程序运行。

回答by nonopolarity

I am a late comer, but maybe I can say this with a specific example:

我是后来者,但也许我可以用一个具体的例子来说明这一点:

Say, if you have a <table>, with <tr>, and then <td>. Now, let's say you set 3 event handlers for the <td>element, then if you do event.stopPropagation()in the first event handler you set for <td>, then all event handlers for <td>will still run, but the event just won't propagate to <tr>or <table>(and won't go up and up to <body>, <html>, document, and window).

假设您有<table>, 和<tr>, 然后<td>。现在,让我们说你设置3个的事件处理程序<td>元素,那么如果你event.stopPropagation()在你设定的第一个事件处理程序<td>则所有事件处理程序<td>仍在运行,但该事件是不会传播到<tr><table>(并不会上升到<body>, <html>, document, 和window)。

Now, however, if you use event.stopImmediatePropagation()in your first event handler, then, the other two event handlers for <td>WILL NOT run, and won't propagate up to <tr>, <table>(and won't go up and up to <body>, <html>, document, and window).

但是现在,如果你使用event.stopImmediatePropagation()你的第一个事件处理程序,那么,对于其他两个事件处理程序<td>将不会运行,并且不会传播到<tr><table>(并不会上去达<body><html>document,和window)。

Note that it is not just for <td>. For other elements, it will follow the same principle.

请注意,它不仅适用于<td>. 对于其他元素,将遵循相同的原则。

回答by Sahil Kashetwar

1)event.stopPropagation():=>It is used to stop executions of its corresponding parent handler only.

1) event.stopPropagation():=>它仅用于停止执行其相应的父处理程序。

2) event.stopImmediatePropagation():=> It is used to stop the execution of its corresponding parent handler and also handler or function attached to itself except the current handler. => It also stops all the handler attached to the current element of entire DOM.

2) event.stopImmediatePropagation():=> 用于停止执行其相应的父处理程序以及附加到自身的处理程序或函数(当前处理程序除外)。=> 它还停止附加到整个 DOM 的当前元素的所有处理程序。

Here is the example: Jsfiddle!

这是示例:Jsfiddle

Thanks, -Sahil

谢谢,-Sahil

回答by Robert Siemer

Surprisingly, allother answers only say half the truth or are actually wrong!

令人惊讶的是,所有其他答案只说了一半的事实或实际上是错误的!

  • e.stopImmediatePropagation()stops any further handler from being called for this event, no exceptions
  • e.stopPropagation()is similar, but does still call all handlers for this phaseon this elementif not called already
  • e.stopImmediatePropagation()停止为此事件调用任何进一步的处理程序,没有例外
  • e.stopPropagation()是相似的,但确实还呼吁所有的处理程序这一阶段这个元素如果不是已经叫

What phase?

什么阶段?

E.g. a click event will always first go all the way down the DOM (called “capture phase”), finally reach the origin of the event (“target phase”) and then bubble up again (“bubble phase”). And with addEventListener()you can register multiple handlers for both capture and bubble phase independently. (Target phase calls handlers of both types on the target without distinguishing.)

例如,一个点击事件总是首先沿着 DOM 向下(称为“捕获阶段”),最后到达事件的起点(“目标阶段”),然后再次冒泡(“冒泡阶段”)。并且addEventListener()您可以独立地为捕获和冒泡阶段注册多个处理程序。(目标阶段在不区分的情况下调用目标上的两种类型的处理程序。)

And this is what the other answers are incorrect about:

这就是其他答案不正确的地方:

  • quote: “event.stopPropagation() allows other handlers on the same element to be executed”
  • correction: if stopped in the capture phase, bubble phase handlers will never be reached, also skipping them on the same element
  • quote: “event.stopPropagation() [...] is used to stop executions of its corresponding parent handler only”
  • correction: if stopped in the capture phase, handlers on any children, including the targetaren't called either, not only parents
  • 引用:“event.stopPropagation() 允许执行同一元素上的其他处理程序”
  • 更正:如果在捕获阶段停止,将永远不会到达气泡阶段处理程序,也会在同一元素上跳过它们
  • 引用:“event.stopPropagation() [...] 仅用于停止其相应父处理程序的执行”
  • 更正:如果在捕获阶段停止,则不会调用任何孩子的处理程序,包括目标,不仅是父母

A fiddleand mozilla.org event phaseexplanation with demo.

一个小提琴和mozilla.org事件阶段与演示说明。

回答by Rahul Kumar

event.stopPropagation()allows other handlers on the same element to be executed, while event.stopImmediatePropagation()prevents every event from running. For example, see below jQuery code block.

event.stopPropagation()允许执行同一元素上的其他处理程序,而event.stopImmediatePropagation()阻止每个事件运行。例如,请参阅下面的 jQuery 代码块。

$("p").click(function(event)
{ event.stopImmediatePropagation();
});
$("p").click(function(event)
{ // This function won't be executed 
$(this).css("color", "#fff7e3");
});

If event.stopPropagationwas used in previous example, then the next click event on p element which changes the css will fire, but in case event.stopImmediatePropagation(), the next p click event will not fire.

如果在前面的示例中使用了event.stopPropagation,则将触发 p 元素上更改 css 的下一个单击事件,但在event.stopImmediatePropagation() 的情况下,将不会触发下一个 p 单击事件。

回答by Abhilash

Here I am adding my JSfiddle example for stopPropagation vs stopImmediatePropagation. JSFIDDLE

在这里,我为 stopPropagation 与 stopImmediatePropagation 添加了我的 JSfiddle 示例。 JSFIDDLE

let stopProp = document.getElementById('stopPropagation');
let stopImmediate = document.getElementById('stopImmediatebtn');
let defaultbtn = document.getElementById("defalut-btn");


stopProp.addEventListener("click", function(event){
 event.stopPropagation();
  console.log('stopPropagation..')
  
})
stopProp.addEventListener("click", function(event){
  console.log('AnotherClick')
  
})
stopImmediate.addEventListener("click", function(event){
  event.stopImmediatePropagation();
    console.log('stopimmediate')
})

stopImmediate.addEventListener("click", function(event){
    console.log('ImmediateStop Another event wont work')
})

defaultbtn.addEventListener("click", function(event){
    alert("Default Clik");
})
defaultbtn.addEventListener("click", function(event){
    console.log("Second event defined will also work same time...")
})
div{
  margin: 10px;
}
<p>
The simple example for event.stopPropagation and stopImmediatePropagation?
Please open console to view the results and click both button.
</p>
<div >
<button id="stopPropagation">
stopPropagation-Button
</button>
</div>
<div  id="grand-div">
  <div class="new" id="parent-div">
    <button id="stopImmediatebtn">
    StopImmediate
    </button>
  </div>
</div>
<div>
<button id="defalut-btn">
Normat Button
</button>
</div>