Javascript 尽管使用addEventListener在父级上设置了Click处理程序,但子级div触发器操作上的Click事件(已禁用事件冒泡))

Javascript 尽管使用addEventListener在父级上设置了Click处理程序,但子级div触发器操作上的Click事件(已禁用事件冒泡)),javascript,Javascript,我有三个盒子 第一个div main的id为“main”,并包含另外两个id为“menu\u header”和的框“menu\u options” 这是我的html <div id="main"> <div id="menu_header"> </div> <div id="menu_options"> </div> </div> <span>Something here</span>

我有三个盒子

第一个div main的id为
“main”
,并包含另外两个id为
“menu\u header”
的框“menu\u options”

这是我的html

<div id="main">
 <div id="menu_header">
  </div>
  <div id="menu_options">
  </div>
</div>
<span>Something here</span>
(忽略css转换,因为它已被注释掉)

这是我的javascript

function test(e){
 //if(e.target.id=="menu_options"){return};
 $('#menu_header').animate({top:'-10'},1000);
  //var t=document.getElementById('menu_header')
 // t.setAttribute('top','40px');
  t.style="position:relative;border:solid black;background:red;width:100px;top:60px;height:100px;"
}
document.getElementById('main').addEventListener('click',test,false)
最后这是我的实验室老鼠jsfiddle链接

在这个场景中,当我在id为“main”的父容器上设置一个click事件处理程序时,除了每次单击id为“menu\u options”的父容器子div时,它也会触发该处理程序之外,其他一切都正常工作

我找到了下面的链接,但是这里的
event.propogation()
解决方案在我的情况下似乎不起作用

一个令人讨厌的黑客攻击,防止在子div捕获事件时执行任何操作

if(e.target.id=="menu_header"){return};
我在javascript代码中注释了上述内容

问题:
为什么id为
“menu\u options”
的子div从id为
“main”
的父容器捕获事件,尽管我在
add EventListener
上设置了
false
,以防止事件冒泡。

您可以将事件冒泡限制为2个场景。 1.在每个DOM对象上放置Click事件,表示从子对象到父对象,并放置event.stropportation()。 2.使用e.target.id标识DOM对象并返回“false”。[我们正在使用它]

代码如下

<script>
        function test(e) {
            if (e.target.id == "menu_header") { return }
            else if (e.target.id == "menu_options") { return }
            $('#menu_header').animate({ top: '-10' }, 1000);
            var t = document.getElementById('menu_header')
            t.setAttribute('top','40px');
            t.style = "position:relative;border:solid black;background:red;width:100px;top:60px;height:100px;"
        }
         window.onload = function () {
        document.getElementById('main').addEventListener('click', test, false);
    }
</script>

功能测试(e){
如果(e.target.id==“菜单头”){return}
else if(e.target.id==“菜单选项”){return}
$('#菜单_头')。动画({top:'-10'},1000);
var t=document.getElementById('menu\u header')
t、 setAttribute('top','40px');
t、 style=“位置:相对;边框:纯黑色;背景:红色;宽度:100px;顶部:60px;高度:100px;”
}
window.onload=函数(){
document.getElementById('main').addEventListener('click',test,false);
}

尝试停止子元素中的传播。看

原因

false
传递给
.addEventListener()
不会禁用冒泡。它只是使事件在冒泡阶段而不是捕获阶段触发

当事件发生时,它从DOM的根开始并进入“捕获”阶段。这意味着事件从
文档
event.target
一路运行,同时触发它找到的任何“捕获”处理程序

一旦到达
事件.target
,它就会反转进程,并返回到
文档
,调用它找到的任何“冒泡”处理程序

因此,由于您将
false
作为第三个参数传递,因此将在最后一个“冒泡”阶段调用处理程序

因此,这并不能阻止嵌套元素调用处理程序


解决方案

如果您只想在单击实际元素时调用处理程序,而不想调用它的任何子元素,那么只要在
this
不等于
e.target
时停止处理程序即可

function test(e){
   if (this != e.target)
      return;

   $('#menu_header').animate({top:'-10'},1000);
   var t=document.getElementById('menu_header')
   t.setAttribute('top','40px');
   t.style="position:relative;border:solid black;background:red;width:100px;top:60px;height:100px;"
}
document.getElementById('main').addEventListener('click',test,false)

它是
event.stopPropagation()
,而不是
event.propagation()
。使用
addEventListener()
设置
false
不会禁用冒泡。这是可以理解的!。。我尝试使用if“(this!=e.target);return”。。。但是什么都没有发生…有什么建议吗?我用“document.getElementById('menu options')!=e.target”替换“this!=e.target”…坚持我的问题,这是问我为什么会遇到这个问题…我会接受这个答案…:d这真的很聪明…而且非常漂亮!谢谢,如果这是您正在寻找的解决方案,请将其标记为接受答案。
function test(){
 $('#menu_header').animate({top:'10'},1000);
  //var t=document.getElementById('menu_header')
 // t.setAttribute('top','40px');
  //t.style="position:relative;border:solid black;background:red;width:100px;top:60px;height:100px;"
}

function stopPropagation(e){
    e.stopPropagation();
}

document.getElementById('main').addEventListener('click',test,false);

document.getElementById('menu_header').addEventListener('click',stopPropagation,false);
function test(e){
   if (this != e.target)
      return;

   $('#menu_header').animate({top:'-10'},1000);
   var t=document.getElementById('menu_header')
   t.setAttribute('top','40px');
   t.style="position:relative;border:solid black;background:red;width:100px;top:60px;height:100px;"
}
document.getElementById('main').addEventListener('click',test,false)