为什么mouseleave会触发

时间:2009-07-26 13:04:57

标签: javascript jquery

我正在尝试开发自己的手风琴/滑动菜单。 (作为一个附带问题,任何可以轻松定制/剥皮的好东西?)

我发现当我滑下“内部”菜单时似乎会触发。由于它是“内在的”,我的鼠标肯定没有离开#mainnav

我的测试页here

没有恼人的测试警告here

$("#mainnav").mouseleave(function() {
    alert("mouseleave #mainnav");
});

更完整的来源:

$(function() {
    $("#mainnav > li > a").hover(mouseOver);
    $("#mainnav").mouseleave(function() {
        alert("mouseleave #mainnav");
    });
});
function mouseOver() {
    $(this).next("ul").slideDown("fast", function() {
        $("li:has(ul) > a", this).hover(mouseOver);
    });
}
#mainnav, #mainnav ul {
    list-style: none;
    padding: 0;
    margin: 0;
    background: #bbb;
}
#mainnav ul {
    display: none;
    margin: 5px 10px;
}
#mainnav a {
    display: block;
    padding: 5px 10px;
    margin: 2px 0;
    background: yellow;
}
<ul id="mainnav">
    <li><a href="#">Test</a></li>
    <li><a href="#">Test</a></li>
    <li><a href="#">Test</a></li>
    <li> 
        <a href="#">Test</a>
        <ul>
            <li><a href="#">Test</a></li>
            <li> 
                <a href="#">Test 1</a>
                <ul>
                    <li><a href="#">Test</a></li>
                    <li><a href="#">Test</a></li>
                    <li><a href="#">Test</a></li>
                </ul>
            </li>
            <li><a href="#">Test</a></li>
        </ul>
    </li>
    <li><a href="#">Test</a></li>
    <li><a href="#">Test</a></li>
</ul>

5 个答案:

答案 0 :(得分:0)

jQuery UI accordion使用ThemeRoller生成的CSS。您甚至可以进一步自定义ThemeRoller生成的CSS。

关于你的问题,我怀疑这是jQuery模拟事件的问题(它是微软专有的)。 jQuery站点上的示例使用DIV和段落,它似乎像宣传的那样工作。您可能希望尝试停止“悬停”事件的传播,以查看是否可以阻止子项上的mouseout触发父项上的mouseleave。

编辑:我刚刚注意到您的悬停方法只有一个回调。我相信它需要两个,你需要在两者中停止传播。以下似乎可以做到这一点但是要使其工作(因为在任一端留下锚点都有事件块)我必须用填充5将整个事物包装在DIV中并将mouseleave事件附加到它。

$(function() {
    $("#mainnav > li > a").hover(
         mouseOver,
         mouseOut
    );
    $("#navContainer").mouseleave(function() {
        alert("mouseleave #mainnav");
    });
});

function mouseOver(e) {
    $(this).next("ul").slideDown("fast", function() {
        $("li:has(ul) > a", this).hover(mouseOver, mouseOut);
    });
    e.stopPropagation();
}
function mouseOut(e) {
    e.stopPropagation();
}

<div id="navContainer" style="padding: 5;">
   ... your list ...
</div>

答案 1 :(得分:0)

没有一个JQuery手风琴/滑动菜单/任何不易剥皮和定制的东西。他们都使用CSS。

答案 2 :(得分:0)

您似乎找到了一种可靠的方法,可以通过该脚本使Google Chrome崩溃。奇怪的。

也许您还需要选择所有子元素。

$("#mainnav, #mainnav > *").mouseleave(function() {
    alert("mouseleave #mainnav");
});

答案 3 :(得分:0)

旧帖子,我知道,但对于未来的访问者: 测试页面没有loger live :( 但我认为这是因为监听mouseleave的元素从鼠标中心开始移动到指针下方,离开了你。

如果是这种情况,在进入和离开事件时(或在动画/效果发生之前)测量指针到鼠标中心元素的距离,可以判断鼠标是“接近”还是“离开”元件。这样,你可以在触发“mouseleave”效果/动作/功能之前“等待”一秒钟。

答案 4 :(得分:-2)

使用Web Inspector。 Safari有一个,Firefox有firebug。抓住其中一个,你会注意到只要你输入一个列表项就会发生这种情况。你要离开mainnav。我认为您不了解Box Model和JQuery事件系统的工作方式。 Here's a good resource on Box Model(按照他提到的链接并阅读所有这些内容,在您能够理解您的问题之前,有必要了解这一点)。 Here is the events/mouseleave page in JQuery's documentation.如果你很久以前就读过这篇文章,你就不会在这里问这个问题。他们甚至为你大胆。他们的文件非常好。

  当指针移入或移出子元素时,

Mouseout 会触发,而 mouseleave 则不会。

我不打算为你编写代码,你需要自己学习这些东西。这是JQuery / CSS的一个重要部分,如果您打算编写自己的脚本,则无法跳过它。