2009-12-14 10 views
2

J'ai une fonction jQuery qui fait un .clone() sur un objet, puis un .insertAfter() et un .slideDown() sur l'objet cloné. Cette fonction entière est enveloppée dans une boucle while. Je garderai ce aussi court et concis que possible et de montrer un exemple générique:jQuery while loop n'attend pas d'animation

while (statement) { 
    // code for clone and insert ... 
    $("#newly_created_object").slideDown(500); 
} 

Comment puis-je empêcher la prochaine boucle while de tir avant que l'animation .slideDown() (ou tout autre type d'animation pour cette matière) extrémités ?

Merci d'avance!

+0

J'ai ajouté une condition de fin explicite à mon code. – tvanfosson

Répondre

6

Vous pouvez créer et insérer tous les premiers éléments, les stocker dans un tableau. Ensuite, vous pouvez utiliser une fonction récursive pour sortir un élément du tableau et l'animer, en appelant votre fonction sur les éléments restants dans le gestionnaire de rappel pour l'animation - pour vous assurer que le premier est complet avant le démarrage suivant.

... 
    var elems = []; 
    while (statement) { 
     var elem = ...clone and insert element, returning element... 
     elems.push(elem); 
    } 

    animateElems(elems); 
} 


function animateElems(elems) 
{ 
    if (elems.length > 0) { 
     var elem = elems.shift(); 
     $(elem).slideDown(500, function() { 
      animateElems(elems); 
     } 
    } 
} 
+0

de loin la solution la plus élégante –

+0

D'accord, tout simplement génial! J'apprécie vraiment, merci! –

3

Vous devez rendre l'animation synchrone, mais ce n'est pas une bonne idée, car elle va bloquer le navigateur et ennuyer l'utilisateur. Voici une autre question sur ce sujet: JQuery synchronous animation

Une meilleure idée est d'utiliser la fonction de rappel, qui sera exécutée lorsque l'animation est terminée. Comme si:

function cloneAndInsert(elm){ 
    if(statement){ 
    // code for clone and insert 
    $("#newly_created_object").slideDown(500, function(){ 
     cloneAndInsert(elm); 
    }); 
    } 
} 

Ce code s'appellera lorsqu'il est fait avec un objet (récursivement).

+0

J'allais aller de l'avant avec votre solution, mais avec la solution de la télévision j'ai juste besoin d'ajouter quelques lignes, plutôt que de réécrire ma fonction qui est beaucoup plus complexe que l'exemple générique que j'ai donné plus haut. Néanmoins, merci, votre contribution a été très appréciée! –

1

Vous pouvez vérifier si l'élément est toujours animé comme ça:

while (statement) { 
    if ($("#newly_created_object").is(":animated")) continue; 
    $("#newly_created_object").slideDown(500); 
} 

Bien qu'il ne soit pas la meilleure solution, parce que vous garderez le navigateur de l'utilisateur occupé.

La bonne façon de faire des actions après l'animation est terminée:

$("#newly_created_object").slideDown(500, function() { 
    alert('this alert box appears when animation is finished'); 
});