Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

One Div animation after another using deferred object

Animate the Div after the previous Div animation has completed using deferred object. This simple method works with the two functions f1 and f2, however when I introduce f3 it fails.

Is there a better way I can achieve this using the deferred object?

JSFiddle: https://jsfiddle.net/j0bgzjvd/

var deferred = $.Deferred();

function animationAgent(element, prevElement) {
  $(prevElement).promise().done( function () {
    return $(element).css("display", "block").animate({width:360},2000, "linear")
  });
}

function f1() {
  animationAgent("#div1"); 
} 

function f2() {
  animationAgent("#div2", "#div1"); 
} 

function f3() {
  animationAgent("#div3", "#div2"); 
}

deferred.resolve();
deferred.done( [ f1, f2, f3 ] );
div {
  width: 200px; 
  height: 200px; 
  background-color: red; 
  margin-bottom: 10px; 
  display: none;  
}
<script src="https://code.jquery.com/jquery-1.10.2.js"></script>

<div id="div1"></div>
<div id="div2"></div>
<div id="div3"></div>
like image 743
jcoulston2 Avatar asked Jan 31 '16 12:01

jcoulston2


People also ask

What is the difference between defer and reject in JavaScript?

When the request is complete, the deferred is resolved (with defer.resolve ); if an error occurs, the deferred is rejected (with defer.reject ). If the promise already exists, the callback is attached to the existing deferred; otherwise, the promise is first created and then the callback is attached.

Can You animate inside a Div?

There are several approaches to animating inside a div that can stretch your skills. To get the broadest support we can’t rely on CSS alone right now, though we can still get pretty far.

What is deferred () method in jQuery?

This JQuery.Deferred () method in JQuery is a function which returns the utility object with methods which can register multiple callbacks to queues. It calls the callback queues, and relay the success or failure state of any synchronous or asynchronous function.

How to create an overlay effect for two <div> elements?

Creating an overlay effect for two <div> elements can be easily done with CSS. This can be done with the combination of the CSS position and z-index properties. The z-index of an element defines its order inside a stacking context.


1 Answers

You will find it simpler to :

  • make animationAgent() into a simple, promise-returning worker function that knows only about the element it animates, and nothing about the sequence in which it is to be used (ie omit prevElement),
  • arrange for functions f1(), f2() and f3(), to return the promise returned to them by animationAgent().

Then you have the basis for building a reliable animation sequence.

function animationAgent(element) {
    return $(element).css("display", "block").animate({width:360}, 2000, "linear").promise();
}
function f1() {
    return animationAgent("#div1"); 
} 
function f2() {
    return animationAgent("#div2"); 
} 
function f3() {
    return animationAgent("#div3"); 
}

f1().then(f2).then(f3);

DEMO

Alternatively, construct the .then chain mechanistically from an array of function references :

function animationAgent(element) {
    return $(element).css("display", "block").animate({width:360}, 2000, "linear").promise();
}
function f1() {
    return animationAgent("#div1"); 
} 
function f2() {
    return animationAgent("#div2"); 
} 
function f3() {
    return animationAgent("#div3"); 
}

[f1, f2, f3].reduce(function(promise, fn) {
    return promise.then(function() {
        return fn();
    });
}, $.when());

DEMO

Or, as the three animations are identical, you can avoid the need for individual functions by constructing the .then chain from an array of element selectors and calling animationAgent() directly :

function animationAgent(element) {
    return $(element).css("display", "block").animate({width:360}, 2000, "linear").promise();
}

['#div1', '#div2', '#div3'].reduce(function(promise, selector) {
    return promise.then(function() {
        return animationAgent(selector);
    });
}, $.when());

DEMO

like image 92
Roamer-1888 Avatar answered Nov 10 '22 11:11

Roamer-1888