#jQueryObject.queue()

根据参数的不同,jQueryObject.queue()有以下几种使用方法:

jQueryObject.queue( [queueName ] )

此方法可显示在选定元素上的将要执行的函数队列,返回值类型为数组。

参数queueName表示队列名称,默认为’fx’,即默认的jQuery队列,可省略。


	// 页面上有一个div,样式display:none 
	var $div = $("#divtest");
	$('body').on('click', function() {
		// 未绑定时 显示其队列
	    console.log('start', $div.queue());

	    $div.show(2000)
	        .animate({
	            left: "+=200"
	        }, 2000)
	        .slideToggle(1000)
	        .slideToggle("fast")
	        .animate({
	            left: "-=200"
	        }, 1500)
	        .hide("slow")
	        .show(1200);

	    // 显示将要执行的队列
	    console.log('end', $div.queue(), $div.queue().length);
	});
	// 结果如下:
	// start []
	// end ["inprogress", function, function, function, function, function, function] 7

点击页面后,加入click事件函数,第一次显示时还未在div上绑定动画效果,故没有要执行的函数,其队列为一个空数组。

之后在这个div上指定了七个动画,再次显示队列时,队列结果为一个数组,长度为7,第一个为“inprogress”表示在执行还未完毕,之后是6个待执行的function。

队列数组是在动态变化的,当执行情况发生改变时,队列结果也随之改变。请看下面例子:

jQueryObject.queue( [queueName ], newQueue )

可以用一个新的队列函数来替换当前队列。

参数queueName string类型 表示队列名称,默认为’fx'

参数newQueue 一个数组 表示新队列,用于替换当前队列的内容

仍用之前的示例:


	var $div = $("div");
	$('body').on('click', function() {   
	    $div.show(2000)
	        .animate({
	            left: "+=200"
	        }, 2000)
	        .slideToggle(1000)
	        .slideToggle("fast")
	        .animate({
	            left: "-=200"
	        }, 1500)
	        .hide("slow")
	        .show(1200);
	    
	    // 替换当前队列
	    $div.queue('fx',[]);
	    console.log('替换后队列', $div.queue());
	    // []
	});

结果为:

绑定动画后,又立即替换当前队列(当前队列为之后的6个动画),由于这里替换的为一个空队列。所以当当前的inprogress执行完毕后,之后就没有等待的队列内容了。所以动画也就停止了。

还可以指定新的函数队列:


	var $div = $("div");
	$div.queue("myQueue", [
	    function(next) {
	        alert("队列函数1"); 
	        next();
	    },
	    function(next) {
	        alert("队列函数2");
	        next();
	    },
	    function(next) {
	        alert("队列函数3");
	        next();
	    }
	]);
	// 显示在div上的队列
	console.log($div.queue());			// []
	console.log($div.queue('myQueue')); // [function, function, function]

由于之前不存在“myQueue”,原队列为空,所以替换队列的方法实际上时添加了一个新队列,名为:“muQueue”,其中有三个在队列中等待执行的函数。

$div.queue()显示默认的名为“fx”队列,由于其中没有排队中的函数,故为一个空数组。

$div.queue(‘myQueue’)显示默认的名为“myQueue”队列,队列内容就是我们为其添加的三个函数。

jQueryObject.queue( [queueName ], callback )

将添加一个新函数到队列中。

参数queueName string类型 表示队列名称,默认为’fx’,可省略。

参数callback 一个函数 表示将要添加到队列中的函数。


	$div.slideUp(1000).fadeIn(3000);

当这个语句被执行,这个元素开始立即做滑动动画,只有当滑动动画完成后才会执行渐入动画,也就是渐入动画还在队列中等待。

使用.queue方法,可以将一个函数加到队列末端:


	$div.slideUp(1000)
	    .queue('fx', function() {
	        $div.text('滑动完成!');
	        $(this).dequeue();
	    })
	    .fadeIn(3000)
	    .queue('fx', function() {
	        $div.text('渐入完成!');
	        $(this).dequeue();
	    });

	// 等价于下面这种写法
	$div.slideUp(1000, function() {
	        $div.text('滑动完成!');
	    })
	    .fadeIn(3000, function() {
	        $div.text('渐入完成!');           
	    });

该函数的功能类似于在动画方法中提供了回调函数,但是不要求在动画执行时指定回调函数。

值得注意的是,当使用.queue()添加一个函数的时候,我们应该保证在函数最后调用了 jQuery.dequeue(),这样就能让队列中的其它函数按顺序执行。

从jQuery 1.4开始,向队列中追加函数时,可以向该函数中传入next,作为第一个参数。当此函数调用时,会自动让队列中的下一个出列,来保证队列的正确移动。如下所示:


	$div.slideUp(1000)
	    .queue('fx', function(next) {
	        $div.text('滑动完成!');
	        next();    // 传入next,并调用next等同于下面的dequeue
	        // $(this).dequeue();
	    })
	    .fadeIn(3000)
	    .queue('fx', function(next) {
	        $div.text('渐入完成!');
	        next();
	        // $(this).dequeue();
	    });

#jQueryObject.dequeue()

顾名思义:即为出列,在jquery中队列的成员都是函数,出列的同时其也将被调用。

拿之前的例子:


	var $div = $("div");
	$div.queue("myQueue", [
	    function(next) {
	        alert("队列函数1"); 
	        next();
	    },
	    function(next) {
	        alert("队列函数2");
	        next();
	    },
	    function(next) {
	        alert("队列函数3");
	        next();
	    }
	]);
	// 显示在div上的队列
	console.log($div.queue());			// []
	console.log($div.queue('myQueue')); // [function, function, function]

仅仅这样在页面上是没有任何反应的。也就是说虽然排好了队伍,但是队伍还没开始动。就好像去医院挂号排队,但是医院还没上班,都还在排队等待的状态。这时候就需要deQueue调用一下。

开始页面是没有反应的,我们在控制台执行了$div.dequeue(‘myQueue’);命令后,队列才开始移动,依次弹出队列函数1、2、3。

前面讲到了使用.queue()方法添加的函数内部的最后需要使用deQueue来使得队列中的其他函数顺序运行。

.dequeue()调用时,队列中的最前端的下一个队列函数被移出队列,并被执行。

“myQueue”是一个队列。首次执行$div.dequeue(‘myQueue’);时,队列的最前端即为队列函数1,所以队列函数1出列并被执行,此时队列最前端变成了队列函数2。由于在第一个函数中传入了next,并在它函数内部的最后调用了next,故使得队列开始自动移动。

在每个队列函数内部最后使用deQueue()或者传入next并调用,都能使队列自动移动。

如果两者都没使用,那么必须一次一次手动调用deQueue()来使队列移动。

例如:


	var $div = $("div");
	$div.queue("myQueue", [
	    function() {
	        alert("队列函数1"); 			        
	    },
	    function(next) {
	        alert("队列函数2");			        
	    },
	    function(next) {
	        alert("队列函数3");			        
	    }
	]);			

为了保证队列能够自动移动,请务必在使用.queue()方法添加的队列函数中调用.deQueue()方法或在队列函数中传入next,并调用。

#jQueryObject.clearQueue

clearQueue([queueName])

参数queueName string类型 表示队列名称,默认为’fx’,可省略。

清空对象上尚未执行的所有队列函数。

不传递参数时(即队列名为“fx”,jQuery默认都将队列函数加入此队列),.clearQueue方法类似于stop(true)

不同之处:

1、stop(true)可以使得其在当前状态立即停止。而.clearQueue会等待当前动作完成后停止。

2、stop(true)只能清空动画队列,而.clearQueue可清空在此对象上指定队列名下的所有队列函数。jQuery API文档上如此描述,实际测试两者都清空了fx下的所有队列函数,无论是否为动画。测试版本2.2.3和3.1.1)


	var $div = $("div");
	$('#start').on('click', function() {
	    (function go() {
	        $div.queue(function(next) {
	                $div.addClass('yellow');
	                next();
	            })
	            .animate({
	                left: "+=200"
	            }, 2000)
	            .animate({
	                left: "-=200"
	            }, 1500)
	            .queue(function(next) {
	                $div.removeClass('yellow');
	                next();
	            })
	            .animate({
	                top: "+=10"
	            }, go);

	    })();
	});
	// clearQueue清空
	$('#end1').on('click', function() {
	    $div.clearQueue();
	    console.log($div.queue());
	    
	});
	// stop(true)清空
	$('#end2').on('click', function() {       
	    $div.stop(true);
	    console.log($div.queue());        
	});		

stop(true)使得其在当前状态立即停止:

.clearQueue会等待当前动作完成后停止:

#$.queue()和$.dequeue()

除了jQuery对象上有上面介绍的队列方法之外,在jQuery本身也有queuedequeue这两个方法。用法和jQuery对象上的类似,只需要将第一个参数传入要操作的dom对象即可,其他参数依次后推。

我们使用$.queue()方法对我们的第一个示例代码进行改写:


	// 页面上有一个div,样式display:none 
	var $div = $("#divtest");
	$('body').on('click', function() {
	        // 未绑定时 显示其队列
	        console.log('start', $.queue($div[0],'fx'));    // $.queue($div[0],'fx') 替换了$div.queue()
	        // console.log('start', $div.queue());

	        $div.show(2000)
	            .animate({
	                left: "+=200"
	            }, 2000)
	            .slideToggle(1000)
	            .slideToggle("fast")
	            .animate({
	                left: "-=200"
	            }, 1500)
	            .hide("slow")
	            .show(1200);

	        // 显示将要执行的队列
	        console.log('end', $.queue($div[0],'fx'), $.queue($div[0],'fx').length);
	        // console.log('end', $div.queue(), $div.queue().length);
	    });
	    // 结果如下:
	    // start []
	    // end ["inprogress", function, function, function, function, function, function] 7

$.dequeue()也是相同的,下面我们使用$.dequeue来触发队列移动。


	var $div = $("#divtest");
	
	// 给div添加一个名为myQueue的队列
	$div.queue("myQueue", [
	    function(next) {
	        alert("队列函数1");
	        next();
	    },
	    function(next) {
	        alert("队列函数2");
	        next();
	    },
	    function(next) {
	        alert("队列函数3");
	        next();
	    }
	]);

前面我们演示了使用$div.dequeue来使队列移动,使用$.dequeue( el , [queueName ])也同样可以实现。

直接挂在jQuery对象本身上的方法属于低级API,而在jQuery对象上使用的方法属于高级API,低级API通常作为工具方法或为高级API服务的,例如这里的jQuery对象上的.queue方法内部实际就是调用的$.queue并将第一个参数替换成了this

我们在使用时,操作具体dom元素时,尽可能使用jQuery对象上的方法,这样清楚明了,可读性较高。