循环通过jQuery函数Inifitly

时间:2012-11-13 11:06:49

标签: javascript jquery

我有一个jQuery动画,我想无限循环,我有当前的代码,但它只返回任何内容。

$(document).ready(function() { 
        var i = 0;
        document.write(i);

        function runTest(){
            $('#page_effect').fadeIn(1500).delay(3500).fadeOut(1500);
            $('#page_effect2').delay(7000).fadeIn(1500).delay(3500).fadeOut(1500);
            $('#page_effect3').delay(13900).fadeIn(1500).delay(3500).fadeOut(1500);
            $('#page_effect4').delay(21000).fadeIn(1500).delay(3500).fadeOut(1500);
            i++;
            runTest();
        }

       if(i === 0){
        runTest();
       }


     });

非常感谢! :)

4 个答案:

答案 0 :(得分:0)

首先,你不应该像这样链接动画,使用回调:

$("#page_effect").fadeIn(1500, function() { 
    $(this).delay(3500).fadeOut(1500);
});

这将等待3500ms fadeOut,但仅在1500ms fadeIn完成之后。 这种方式使用回调,您可以从上次回调中再次调用该函数:

function runTest(){

    ...

    $('#page_effect4').delay(21000).fadeIn(1500, function() {
         $(this).delay(3500).fadeOut(1500, function() {
              runTest();
              // this will be called only after the fadeout completes
         });
    });
}

答案 1 :(得分:0)

你正在排队动画,但从不“让步”回到浏览器,因为你只需要立即再次调用该功能。

浏览器永远不会进入其事件循环,动画也无法启动。

要解决此问题,您需要让浏览器等到所有动画都完成,然后再次排队:

$(function() {

     (function animate() {
          $('#page_effect').fadeIn(1500).delay(3500).fadeOut(1500);
          $('#page_effect2').delay(7000).fadeIn(1500).delay(3500).fadeOut(1500);
          $('#page_effect3').delay(13900).fadeIn(1500).delay(3500).fadeOut(1500);
          $('#page_effect4').delay(21000).fadeIn(1500).delay(3500).fadeOut(1500);

          // using deferred objects, ask for a promise that will be resolved
          // when all animations on the specified elements have been completed,
          // and when done, call myself to start all over again
          $('#page_effect,#page_effect2,#page_effect3,#page_effect4')
              .promise().done(animate);

     })();   // invoke immediately
});

我注意到你的四个单独的效果可能应该是连续运行的,但如果它们全部并行运行,那么基于.promise()的解决方案也会有效。

请参阅http://jsfiddle.net/alnitak/ZKevs/

请注意,如果您打算连续运行这些效果,那么您不应该只将它们排在一起 - 没有时间保证,下一个元素可能会在前一个元素完成之前开始动画。

传统的解决方案是在上一个动画中添加一个“动画完成”回调,但是你在这里有四个单独的动画,最终会被可怕的嵌套。

jQuery延迟对象也可以在这里提供帮助 - 请注意这如何消除了额外的计算.delay()调用:

$('#page_effect').fadeIn(1500).delay(3500).fadeOut(1500);

$('#page_effect').promise().done(function() {
    $('#page_effect2').fadeIn(1500).delay(3500).fadeOut(1500);
});

$('#page_effect2').promise().done(function() {
    $('#page_effect3').fadeIn(1500).delay(3500).fadeOut(1500);
});

$('#page_effect4').promise().done(function() {
    $('#page_effect4').fadeIn(1500).delay(3500).fadeOut(1500);
});

$('#page_effect4').promise.done(animate);

此时您可以看到每个动画链都是相同的并且可以重构:

function cycle($els) {
    var i = 0, n = $els.length;
    (function next() {
        var $this = $els.eq(i);
        i = (i + 1) % n;
        $this.fadeIn(1500).delay(3500).fadeOut(1500).promise().done(next);
    })();
});

cycle($('#page_effect,#page_effect2,#page_effect3,#page_effect4'));

答案 2 :(得分:0)

你可以将它们全部包装在一个函数中,并在最后一个动画结束后重新调用该函数:

function run(){

      $('#page_effect').fadeIn(1500).delay(3500).fadeOut(1500); 
      $('#page_effect2').delay(7000).fadeIn(1500).delay(3500).fadeOut(1500);             
      $('#page_effect3').delay(13900).fadeIn(1500).delay(3500).fadeOut(1500);             
      $('#page_effect4').delay(21000).fadeIn(1500).delay(3500).fadeOut(1500,run);
}

run();

实例:http://jsfiddle.net/nCs6N/

答案 3 :(得分:-1)

不要像那样递归地调用runTest(),你将耗尽函数堆栈。

而是使用setTimeout(runTest, 0);