aboutsummaryrefslogtreecommitdiffstats
path: root/src/queue.js
diff options
context:
space:
mode:
authorjaubourg <j@ubourg.net>2011-04-07 06:00:52 +0200
committerjaubourg <j@ubourg.net>2011-04-07 06:00:52 +0200
commit4552d135f404b78f4fa1494a3de2911b2e2e4773 (patch)
treed7177b0b0ef40893e9dbadf18b837c02043b8bef /src/queue.js
parentbb99899ca0de93dd12f5a53f409ff6f72bfcf94c (diff)
downloadjquery-4552d135f404b78f4fa1494a3de2911b2e2e4773.tar.gz
jquery-4552d135f404b78f4fa1494a3de2911b2e2e4773.zip
Adds fn.promise as a mean to observe the completion of animations on a set of elements. Only queued animations are handled for now, non-queued animations support coming soon. Effects unit tests updated to test the feature (needs more testing though).
Diffstat (limited to 'src/queue.js')
-rw-r--r--src/queue.js45
1 files changed, 44 insertions, 1 deletions
diff --git a/src/queue.js b/src/queue.js
index 9e3e2fb52..701d06ade 100644
--- a/src/queue.js
+++ b/src/queue.js
@@ -28,7 +28,8 @@ jQuery.extend({
type = type || "fx";
var queue = jQuery.queue( elem, type ),
- fn = queue.shift();
+ fn = queue.shift(),
+ defer;
// If the fx queue is dequeued, always remove the progress sentinel
if ( fn === "inprogress" ) {
@@ -49,6 +50,17 @@ jQuery.extend({
if ( !queue.length ) {
jQuery.removeData( elem, type + "queue", true );
+ // Look if we have observers and resolve if needed
+ if (( defer = jQuery.data( elem, type + "defer", undefined, true ) )) {
+ // Give room for hard-coded callbacks to fire first
+ // and eventually add another animation on the element
+ setTimeout( function() {
+ if ( !jQuery.data( elem, type + "queue", undefined, true ) ) {
+ jQuery.removeData( elem, type + "defer", true );
+ defer.resolve();
+ }
+ }, 0 );
+ }
}
}
});
@@ -93,6 +105,37 @@ jQuery.fn.extend({
clearQueue: function( type ) {
return this.queue( type || "fx", [] );
+ },
+
+ // Get a promise resolved when queues of a certain type
+ // are emptied (fx is the type by default)
+ promise: function( type, object ) {
+ if ( typeof type !== "string" ) {
+ object = type;
+ type = undefined;
+ }
+ type = type || "fx";
+ var defer = jQuery.Deferred(),
+ elements = this,
+ i = elements.length,
+ count = 1,
+ deferDataKey = type + "defer",
+ queueDataKey = type + "queue";
+ function resolve() {
+ if ( !( --count ) ) {
+ defer.resolveWith( elements, [ elements ] );
+ }
+ }
+ while( i-- ) {
+ if (( tmp = jQuery.data( elements[ i ], deferDataKey, undefined, true ) ||
+ jQuery.data( elements[ i ], queueDataKey, undefined, true ) &&
+ jQuery.data( elements[ i ], deferDataKey, jQuery._Deferred(), true ) )) {
+ count++;
+ tmp.done( resolve );
+ }
+ }
+ resolve();
+ return defer.promise();
}
});