How can I make a function wait until an animation

2019-05-10 23:35发布

问题:

I have used JQuery for a small animation work: a table #photos contains 9 photos and I would like to increase the width and height using the animate function on mouseover. But while the animation is running if the user moves to mouse to another photo it automatically triggers the next animation, so it's totally confused. What should I do? My code is:

$(function(){
  $("#photos tr td img").mouseover(function(){
    $(this).animate({"width":"1000px","height":"512px"},2000)
  });
  $("#photos tr td img").mouseout(function(){
    $(this).animate({"width":"100px","height":"50px"},2000)
  });       
});

回答1:

JQuery offers callbacks when the animation is complete. Then it might look like this for example:

var animating = false;
$(function(){ $("#photos tr td img").mouseover(
    function()
    {
        if(!animating)
            $(this).animate({"width":"1000px","height":"512px"},2000, easing, function() { animating = true; });
    }); 

    $("#photos tr td img").mouseout(
        function()
        {
            $(this).animate({"width":"100px","height":"50px"},2000, easing, function() { animating = false; }) 
        });
});


回答2:

You should stop any running animation before starting a new one to avoid the mess up. It's probably the best and straightforward solution for this specific problem.

$(function(){
  $("#photos tr td img").mouseover(function(){
    $(this).stop();
    $(this).animate({"width":"1000px","height":"512px"},2000)
  });
  $("#photos tr td img").mouseout(function(){
    $(this).animate({"width":"100px","height":"50px"},2000)
  });       
});


回答3:

In addition to the other answers I would look into using the hoverIntent plugin. This just avoids setting off a massive animation queue when the user sweeps the mouse over all photos. You only really want the animation if the user is actually hovered.



回答4:

I guess the answer depends on what you want to happen on the second mousover (while the first one is still animating).

1) If you want nothing to happen, you can have your first hover set an "animating" state on the whole TR, maybe like this:

  $tr = $(this).closest("tr");
  if ($tr.data("animating") != true) {
      $tr.data("animating",true);
      $(this)
        .stop(true,false)
        .animate({"width":"1000px","height":"512px"},2000, function(){
          $tr.data("animating",false);
      });
  }

2) If you want the original animation to end so your new image can animate, you'll need to .stop() the old one with the clearQueue and goToEnd parameters set to true. This will ensure that additional queued events (from a whole bunch of hovers) don't just keep happening for minutes, and it'll make the animation immediately skip to its final state:

  $(this).closest("tr").find("img:animated").stop(true,true);
  $(this).animate({"width":"1000px","height":"512px"},2000});


回答5:

Always check queue animation of element and never get conflict from now:

$(function(){
  $("#photos tr td img").mouseover(function(){
    if($(this).queue("fx").length == 0)
       $(this).animate({"width":"1000px","height":"512px"},2000)
  });
  $("#photos tr td img").mouseout(function(){
       $(this).animate({"width":"100px","height":"50px"},2000)
  });       
});