β

jquery动画之queue和dequeue

JDC | 京东设计中心 256 阅读

官方文档:

队列的本质是一个数组,对队列的理解先从数组的push和shift开始。

push是从数组尾端插入新的元素,shift是从数组首端删除元素;分别对应队列中得queue和dequeue。我们知道jquery所有动画基于animate方法,而animate的动画默认保存在名为fx的动画队列中。

queue就是将动画放进队列中,dequeue就是将动画从队列中删除并执行它。

$.fn.queue传参形式有:

  1. queue([queue_name]) 查看队列,传入队列名
  2. queue([queue_name], new_queue) 添加new_queue到队列中,对列名默认为fx,new_queue类型为数组
  3. queue([queue_name], callback) 添加callback回调函数到队列中,对列名默认为fx,callback类型为函数,当该函数被调用时,会从弹出队列中的下一个元素。

一、队列的存在和执行

我们在页面中常使用这样的语句:

$('#foo').slideUp().fadeIn();

它的执行顺序是元素先slideUp后再fadeIn,slideUp和fadeIn有先后顺序。jquery会默认地将它们放进名为fx的队列中,我们可以这样认为:

var fx = [slideUp, fadeIn];

    //相当于
    $('#foo').queue('fx', fx);

    //第一步:出列第一个元素slideUp并执行它
    $('#foo').dequeue('fx');    //fx = ['inprogress', fadeIn]

    //第二步:出列第二个元素fadeIn并执行它
    $('#foo').dequeue('fx');    //fx = ['inprogress']

    //第三步,队列fx为空,动画执行完毕
    fx = [];

通过不断的dequeue,fx每个元素逐个依次出列执行,直至队列没有元素。

所以我们很容易发现,当我们书写下面这个语句的时候,执行顺序并不是按照书写顺序来执行了:

$('#foo').slideUp().fadeIn().css({'width':'200px'});

它的执行顺序是元素宽度马上变成200px的同时,slideUp也在执行,slideUp执行完后再执行fadeIn。

二、队列的回调

官网中的例子:

$(document.body).click(function () {
        $("div")
                .show("slow")
                .animate({left : "+=200"}, 2000)
                .queue(function () {
                    $(this).addClass("newcolor").dequeue();
                })
                .animate({left : "-=200"}, 500)
                .queue(function () {
                    $(this).removeClass("newcolor").dequeue();
                })
                .slideUp();
    });

在click之后,div元素会先出现,再往右运动两秒,接着添加newcolor的类名,再往左回到起点,去除newcolor类名后收起来消失。

.queue(function () {
        $(this).addClass("newcolor").dequeue();
    })

这个匿名函数是queue的回调函数,$(this).dequeue()在这里的作用是弹出队列中的下一个元素。

如果我们将这句话中的dequeue去除会怎样呢?

$(document.body).click(function () {
        $("div")
                .show("slow")
                .animate({left : "+=200"}, 2000)
                .queue(function () {
                    $(this).addClass("newcolor");//.dequeue();
                })
                .animate({left : "-=200"}, 500)
                .queue(function () {
                    $(this).removeClass("newcolor").dequeue();
                })
                .slideUp();
    });

运行后可以知道脚本在执行完addClass(’newcolor’)后停止了。虽然队列中还有元素在排队,但是去除dequeue后没有将下个元素抛出,所以停止了执行。这就是dequeue的作用,弹出下一个元素,让队列执行下去。

如果将上面的脚本再修改下:

$(document.body).click(function () {
        $("div")
                .show("slow")
                .animate({left : "+=200"}, 2000)
                .queue(function () {
                    $(this).addClass("newcolor").dequeue();
                    $(this).slideDown("slow");//添加slideDown
                })
                .animate({left : "-=200"}, 500).queue(function () {
                    $(this).removeClass("newcolor").dequeue();
                })
                .slideUp();
    });

div中的fx队列最后会增加一个排队元素slideDown,所以最后slideUp收起收,又再缓缓地slideDown下来。

三、队列的自定义

我们可以通过这样的方式来创建自己的队列:

var queue = [
        function () {
            console.log('NO.1');
        },
        function () {
            console.log('NO.2');
        }
    ];
    $('div').queue('a1', queue);

这样我们创建了一个名为a1的队列,队列里有两个元素在排队。

打印队列长度:

$('div').queue('a1').length;//输出2

通过dequeue来让队列的第一个元素出列:

$('div’).dequeue('a1’);//输出NO.1

打印下队列现在的长度:

$('div’).queue(‘a1').length;//输出1

接着再dequeue一次,queue队列就会清空,全部队列出列执行完毕。

按照这个思路,我们可以运用之前学习的回调函数方法,将出列的方法放在回调函数中,在完成一个动画后调用出列,就可以将队列依次执行。

思路:

var queue = [
        function () {
            $('item-1').fadeIn(function(){
                $('div').dequeue('a1');
            });
        },
        function () {
            $('item-2').fadeIn(function(){
                $('div').dequeue('a1');
            });
        },
        function () {
            $('item-3').fadeIn(function(){
                $('div').dequeue('a1');
            });
        }
    ];
    $('div').queue('a1', queue);

    //触发动画
    $('div').dequeue('a1');

成型:

var queue = [
        function () {
            $('item-1').fadeIn(dequeue);
        },
        function () {
            $('item-2').fadeIn(dequeue);
        },
        function () {
            $('item-3').fadeIn(dequeue);
        }
    ];

    var dequeue = function(){
        $('div').dequeue('a1');
    };
    $('div').queue('a1', queue);

    //触发动画
    dequeue();

item-1,item-2,item-3会依次的出现。

四、队列的运用场景

在动画效果中需要按序来执行的时候都可以用到队列,特别是在动画绑定在不同的dom元素上和某些效果没有用到animate方法的时候。

案例:

  1. 京东双12头部文案出现顺序: http://sale.jd.com/act/J067lGoWuw.html
作者:JDC | 京东设计中心
京东设计中心
原文地址:jquery动画之queue和dequeue, 感谢原作者分享。

发表评论