当前位置: 首页 > 知识库问答 >
问题:

防止某些事件侦听器触发某个事件,但允许父侦听器触发

强烨
2023-03-14

有没有办法防止事件链中的一些听众为事件开火,但允许链上的其他人开火?

比如我有这个结构

<body>
    <div id="1">
       <div id="2">
          <button>Click Me</button>
       </div>
    </div>
</body> 

假设我已经将单击事件监听器连接到body、div#1和div#2。是否有可能在div#2事件监听器上阻止事件进入div#1或介于两者之间的任何其他监听器,并允许事件在body元素上触发?

我这样说是因为我使用谷歌地图和emberjs构建了一系列可以在地图上显示的交互式信息框。问题是ember将事件侦听器附加到body元素上,而google将它们附加到其他未知级别。当点击事件由托管在google maps覆盖中的emberjs HTML节点触发时,事件必须首先通过google maps处理程序,然后才能到达ember。

这导致了一些意想不到的副作用,比如谷歌地图认为我在点击其他标记。这个问题。在Infobox火焰上鼠标悬停事件在它后面的标记上

共有1个答案

宋伯寅
2023-03-14

您可以根据单击目标有条件地执行处理程序代码。在本例中,您可以看到,当单击按钮A时,会触发按钮b和div 1的事件,但不会触发div 2的事件。如果单击按钮B,则会触发所有三个按钮的事件。

另一种方法是,如果您自己不添加事件侦听器,但您知道必须在哪个节点上触发事件,例如在Ember和body元素中,您可以停止事件在您控制的处理程序中的传播,然后在body上触发单击事件。这不是最优雅的解决方案,但考虑到所描述的情况,我不确定是否还有其他方法。您可以通过单击按钮C查看此版本。

function log(s) {
  var e = document.createElement('div');
  e.innerHTML = s;
  document.body.appendChild(e);
}

document.getElementById('1').addEventListener('click', function (e) { log('Div 1 clicked'); });
document.getElementById('2').addEventListener('click', function (e) {
  if (event.target.id !== "a") {
      log('Div 2 clicked');
  }
});
document.getElementById('a').addEventListener('click', function (e) { log('Button A clicked'); });
document.getElementById('b').addEventListener('click', function (e) { log('Button B clicked'); });

document.body.addEventListener('click', function (e) { log('Ember click event fired'); });
document.getElementById('c').addEventListener('click', function (e) {
  log('Button C clicked');
  e.stopPropagation();
  document.body.click();
});
<div id="1">
  <div id="2">
    <button id="a">Button A</button>
    <button id="b">Button B</button>
    <button id="c">Button C</button>
  </div>
</div>
 类似资料:
  • 我通过infinispan缓存添加了CacheEntryExpired侦听器的n实现。addListener()方法。 侦听器事件在条目过期时激发。问题是,每次事件触发两次。 我验证(使用调试器和cache.getListeners())缓存不包含我的同一个侦听器的两个实例。getListeners的结果是: 所以只有一个听众。侦听器实现接口: 一个实现看起来像: 但是从接口中删除@CacheEn

  • 我有一个烧瓶API,我使用烧瓶SQLAlChemy来处理SQLite数据库。我有一个存储日志条目的表,我想将最大行数限制为n。因为插入也是使用原始SQL从烧瓶之外的另一个脚本进行的,所以我创建了一个触发器来检查行数,如果行数高于n,则删除最旧的行数: 此触发器按预期工作,但我正在努力使用烧瓶-sqlalChemy设置它。如何设置触发器/执行原始SQL使用烧瓶sqlalChemy?SQL只需要在db

  • 问题内容: 触发事件后,如何临时禁用onclick事件监听器(首选jQuery)? 例: 用户单击按钮并在下面触发此功能后,我想禁用onclick侦听器,因此不向django视图触发相同的命令。 非常感谢, 奥尔多 问题答案: 有很多方法可以做到这一点。例如: 要么 我们还可以使用事件委托来获得更清晰的代码和更好的性能: 如果执行完处理程序后不需要重新启用处理程序,则可以使用该 方法。它绑定只能执

  • 我有一个反应组件与材料ui滑块。每次这个组件呈现时,我都会收到这个警告:“将非被动事件侦听器添加到阻止滚动的‘触摸启动’事件中。考虑将事件处理程序标记为“被动”,以使页面更具响应性” 如何解决这个问题?

  • 我的代码使用jQuery。我有一个密码输入框,我想要得到输入的密码任何时候。 下面是我的代码: 我确信这是一个正确的代码,因为当我在浏览器的控制台中输入它时,它可以工作,但当我重新加载页面时,它就不工作了 我能做什么?

  • 从元素中移除事件侦听器。 使用 EventTarget.removeEventListener() 从元素中删除一个事件监听器。 省略第四个参数 opts ,则默认使用 false 或者根据添加事件监听器时使用的选项来指定它。 const off = (el, evt, fn, opts = false) => el.removeEventListener(evt, fn, opts); con