【问题标题】:Wait 300ms and then slide down menu using jQuery等待 300 毫秒,然后使用 jQuery 向下滑动菜单
【发布时间】:2012-09-02 07:32:03
【问题描述】:

我试过这个js代码:

<script type="text/javascript">

       $(document).ready( function() {
            var timer;
            $('.top-menu-first-ul li').hover(function(){
                        if(timer) {
                                clearTimeout(timer);
                                timer = null
                        }
                        timer = setTimeout(function() {
                                   $(this).find('ul').slideToggle(100);
                        }, 500)
            },
            // mouse out
            });
        });


</script>

使用这个 html:

<ul class="top-menu-first-ul">
    <li>
        <a href="http://google.com">Google</a>
        <ul class="top-menu-second-ul">
            <li><a href="http://translate.google.com">Google Translate</a></li>
            <li><a href="http://images.google.com">Google Images</a></li>
            <li><a href="http://gmail.google.com">Gmail</a></li>
            <li><a href="http://plus.google.com">Google Plus</a></li>
        </ul>
    </li>
    <li>
        <a href="http://facebook.com">Facebook</a>
    </li>
    <li>
        <a href="http://twitter.com">Twitter</a>
    </li>
</ul>

但它不起作用。

我想在鼠标悬停时显示子菜单,例如谷歌链接和其他将在 300 毫秒后出现。

所以,当用户快速将鼠标悬停在子菜单上并且不停留在悬停链接上至少 300 毫秒时,我需要阻止加载子菜单。

然后我需要在他离开链接时停止执行代码(或向上滑动)。因为如果他反复来回反复几次,他就会停止悬停,并且代码仍在执行自己多少次他将鼠标悬停在链接上。我需要以某种方式防止这种情况发生。

编辑:如果可能的话,我需要在没有像 hoverIntent 等插件的情况下解决这个问题,只需要普通的 javascript 和 jQuery

【问题讨论】:

    标签: javascript jquery


    【解决方案1】:

    我认为问题在于您在超时调用的函数中使用了$(this)。这个闭包内部的$(this) 与外部不同(在jQuery 为您设置的jQuery 事件处理程序内部)。 Here (jsfiddle) 是解决方案:

    $(document).ready( function() {
                $('.top-menu-first-ul li').mouseenter(mouseIn);
                $('.top-menu-first-ul li').mouseout(mouseOut);
    });
    function mouseIn(e){
        var target = $(this);
        var timer = setTimeout(function() {
                       target.find('ul').slideDown(100);
            }, 500);
        target.attr("data-timer", timer);
    }
    
    function mouseOut(e){
        var target = $(this);
        var timer = target.attr("data-timer");
        if(timer){
            clearTimeout(timer);
        }
        target.find('ul').slideUp(100)
    }
    ​
    

    更新此解决方案基于您的解决方案,但我建议使用@elclanrs 的解决方案,因为它更好(更具可读性,使用专门用于此目的的 jQuery API)。

    【讨论】:

    • 我刚刚签入了 Chrome 21、IE 10 和 Firefox 14,它可以在任何地方运行。
    • 啊,我明白了,当你移动鼠标点击翻译时... :)
    • @elclanrs 已经解决了这个问题(moseout->mouseleave),这里也是一样
    • 谢谢,但它不像 elclanrs 解决方案那样顺利。例如。当我在 ul 容器中时,我有时会出现并且不会消失等。但是,elclanrs 解决方案给了我错误 SyntaxError: Unexpected token ILLEGAL 并且仅在 Opera 中为我工作,出于某种奇怪的原因。
    • jsfiddle 在复制粘贴时创建了一些奇怪的字符。我想我坚持使用 jsbin
    【解决方案2】:

    使用stop() 防止动画怪异,使用delay() 等待300ms。 hover() 也已弃用,我建议改用 on()

    $('.top-menu-first-ul li').on({
      mouseover: function() {
        $(this).find('ul').stop(1,1).delay(300).slideDown(100);
      },
      mouseleave: function() {
        $(this).find('ul').stop(1,1).slideUp(100);
      }
    });
    

    演示: http://jsfiddle.net/elclanrs/6dtWz/

    【讨论】:

    • 谢谢,但是当我离开谷歌并想将鼠标悬停在谷歌翻译、谷歌邮件等子菜单项上时,它们就会消失。你能解决它吗?
    • 是的,只需将mouseout 更改为mouseleave。再次查看演示。
    • 谢谢,起初你的更新版本也不能正常工作,但我注意到如果我打开 jsfiddle 你的演示到 jquery 1.6 它将无法工作。所以,我已经将我的 jQuery 从 1.6.2 版本升级到最新的 1.8.1,它运行良好;)。谢谢。
    • 我太快了。它在 Chrome 中不起作用;(。它给了我意外的令牌错误。
    • 在 Opera 中效果很好,但在 Chrome、IE、Firefox 中却不行;(。这很奇怪。我已经重新启动了 WAMP、计算机等,但没有任何帮助。我正在运行 jQuery 1.8.1。这个很奇怪。为什么 OPera 是,而 Firefox 和 Chrome 不是?
    猜你喜欢
    • 2014-11-23
    • 2019-01-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-21
    • 2012-11-21
    • 2021-08-31
    相关资源
    最近更新 更多