问题

在开发中经常有需要鼠标hover时对内容隐藏显示的需求,常用的方式是通过jquery的hover事件,配合show/hide进行实现,具体代码如下:
html:

<ul>
    <li>
        <p>标题1</p>
    </li>

    <li>
        <p>标题2</p>
    </li>
    <li>
        <p>标题3</p>
    </li>
</ul>

js:

 $(function () {
    $('ul li').hover(function () {
        $(this).children().show()
    }, function () {
        $('p').hide()
    })
})

这样实现起来是没有问题的,但是过于生硬,只是通过 display: block|none 的方式进行隐藏显示,毫无体验可言,所以改进一下,js如下:

$(function () {
    $('ul li').hover(function () {
        $(this).children().show(500) // 增加speed 500ms
    }, function () {
        $('p').hide(300) //增加speed 300ms
    })
})

嗯嗯,可以了,显示的时候增加了动画,不再生硬,但是,问题来了,当鼠标快速的移入移出的时候,即使鼠标已经停止运动,但是动画还没有停止,依然会按照鼠标移入移出的次数执行完成才会停止,这略微有点尴尬,需要解决一下。

解决办法

原本想到的是,既然移入移出有时间延迟,那可以加个延时,在移入的时候判断时候在执行,如果已经在执行动画过程,那么就不执行show,hide同理,但是失败了。
那么再看看其他的吧,hover不行,那使用mouseenter/mouseout事件呢,然而,效果是一样的。仔细想了下,应该是因为增加了speed之后,相当于每次移入移出,都把隐藏/显示的动画增加到了动画的队列中,所以当快速的进行时,即使鼠标停止了,但是队列中的事件还没有执行完,所以依然会按照当前的次数继续执行,直到完成为止。
那么既然这样,jq一定有自己的方式处理吧,要不然不可能就这样大家都忍受着或者都自己去想各种办法解决,果然,又搜了一下,原来jq已经提供了stop方法。
stop这个方法的用途就是用于停止动画或效果,在它们完成之前。它接受两个参数:stopAll:规定是否应该清除动画队列。默认是 false,即仅停止活动的动画,允许任何排入队列的动画向后执行;goToEnd:规定是否立即完成当前动画,默认是 false。默认地,stop() 会清除在被选元素上指定的当前动画。
修改js如下:

$(function () {
    $('ul li').hover(function () {
        $(this).children().stop(false, true).show(500)
    }, function () {
        $('p').stop(false, true).hide(300)
    })
})

嗯嗯,问题解决了,可以愉快的进进出出了。
看来jq用的太少了,对api也不够熟练啊,以后还是加强一下吧,嘻嘻。


李小疯子
5 声望2 粉丝