(jQuery 1.7.2 を対象としています。1.8pre では then()
が pipe()
と同じものになっているので、かわりに then()
を使っても動くようです。)
対象の要素が同じであれば、以下のように animate()
を連続して呼ぶと queue にアニメーションが溜まり、順番に実行されます。
$elem1.animate({left: 500}, 1000)
.animate({top: 300}, 1000)
.animate({left: 0}, 1000);
ところが queue は要素ごとであるため、対象の要素が違う場合は同じようにはいきません。そこで $.Deferred
を使うことで同様のことが実現できます。
$.Deferred(function(dfd) {
dfd.pipe(function() { return $elem1.animate({left: 500}, 1000); })
.pipe(function() { return $elem2.animate({top: 300}, 1000); })
.pipe(function() { return $elem1.animate({left: 0}, 1000); });
}).resolve();
pipe()
は、引数の関数の戻り値が observable である、つまり promise()
という関数プロパティを持っていると、その戻り値の Promise
を使って待ってくれます。animate()
は jQuery オブジェクトを返しますが、jQuery オブジェクトの promise()
は、要素のアニメーションが全て終わった時に resolve
される Promise
を返します。このため、アニメーションが順番に実行されるのです。
詳しくは以下を参照。