创建jquery无限动画不使用递归?

时间:2015-03-07 13:25:55

标签: javascript jquery recursion

如何使用jquery创建无限动画, 但不使用递归方式?

我找到的递归解决方案:jQuery .animate() callback infinite loop

使用递归的问题是: 动画时,currrent页面的浏览器选项卡将占用更多更多的内存。

2 个答案:

答案 0 :(得分:3)

您实际上在假设代码是“递归”时犯了一个错误。它是递归。您的评论“当前页面的浏览器选项卡将占用更多更多内存。”不是因为该代码中的任何递归。如果每秒有内存泄漏(根据您的意见),那么问题就在其他地方。

代码的实例实际上是通过嵌套的堆栈调用顺序运行而不是(即线性而非递归)。

使用您链接的最基本示例:

function start() {
    $('#element').animate({}, 5000, 'linear', start);
}
start();

这是实际发生的事情:

  • 定义了一个名为start的函数,然后调用一次
  • start内,启动动画操作,然后start立即退出!
  • animate只是将信息添加到元素的单个动画队列中,然后返回。
  • 动画队列由一个单独的进程(单个计时器等)逐步处理。
  • 当排队的条目达到预期的结束状态时,它会调用回调 - 存储在排队条目中的全局start函数。
  • 这个简单在动画队列中添加了另一个条目并退出。

基本上代码看起来是递归的,但由于操作是异步的,通过队列,它不是递归的。我不知道这些是否有官方名称,所以我只称它们为链式回调。

答案 1 :(得分:0)

更新测试结果

结论......所有方法都会耗尽相同数量的内存,最终会被释放,不会永远存在,所以不是真正的问题。

示例1

这是OP最初在Chrome中内存使用量增加的问题。

(function($){
    $(function(){  //document.ready

        function start() {
                $('#animate').animate({'margin-left':'150px'}, 1000, function () {
                    $(this).animate({'margin-left':'50px'}, 1000, 'linear', start);                
                });
        }
        start();

    });
})(jQuery);

示例2

目前的解决方案包括Bergi要求的回调,以避免在setinterval中潜在的“漂移”。

(function($){

    $(function(){  //document.ready

    });

    (function customSwipe(element) {
        element
            .animate({"margin-left" : "150px"}, 1000)
            .animate({"margin-left" : "50px"}, 1000, function(){
                setTimeout(function(){
                    customSwipe(element);
                }, 2000);
            });
    })($('#animate'));

})(jQuery);

示例3

我给出的原始答案,使用setInterval()

(function($){
    $(function(){  //document.ready

            setInterval(function(){
                    $("#animate").animate({'margin-left':'150px'},1000);
                    $("#animate").animate({'margin-left':'50px'},1000);
            },2000); 

    });
})(jQuery);

Skeleton w / Jquery

空页面只有#animate元素

(function($){
    $(function(){  //document.ready



    });
})(jQuery);
TAB打开10分钟后

数据

CODE            STARTING    ENDED
Example 1       14.300k     19.996k
Example 2       14.300k     20.020k
Example 3       14.300k     20.344k
Skeleton w/ jQuery  14.300k     15.868k

有趣的是,什么都没做的代码仍然略微增加了使用量。当使用和释放内存时,这些值会上下移动。另一件事是使用任务管理器中的“清除内存”按钮来查看有多少用过的内存是垃圾等待收集。

25分钟后的数据

Example 1       14.300k     18.640k
Example 2       14.300k     18.724k
Example 3       14.300k     18.876k
Skeleton w/ jQuery  14.300k     15.868k

结论......所有方法都会耗尽相同数量的内存,最终会被释放,不会永远存在,所以不是真正的问题。

因此,只使用最稳定的声音代码将是最佳选择,示例2将是我的选择。

使用CALLBACK更新

您是否尝试将setTimeout$.animate()一起使用?

(function($){
    (function customSwipe(element) {
        element
            .animate({'margin-left':'150px'}, 1000)
            .animate({'margin-left':'50px'}, 1000, function(){
                setTimeout(function(){
                    customSwipe(element);
                }, 2000);
            });
    })($('#animate'));

    $(function(){  //document.ready


    });

})(jQuery);

如果您不需要在动画之间延迟,请删除setTimeout()。

JSFIDDLE of the above code working...

您可能还想查看更复杂的动画。

http://api.jquery.com/jquery.fx.interval/

结论......所有方法都会耗尽相同数量的内存,最终会被释放,不会永远存在,所以不是真正的问题。

您在Chrome TM中看到的是,每次触发动画时,都会请求大量内存,并且操作系统会将该内存“提交”为操作的chrome。一旦操作完成,内存仍然被提交。在某些时候,Chromes垃圾收集器出现并释放内存,您的使用统计数据将下降。所以如果你看足够久,你会看到内存上下移动。

您可以在Chrome命令行的末尾添加--purge-memory-button,以在Chrome TM中提供“清除内存”按钮。这可能会帮助您查看实际等待释放的内存量。

希望这个答案可以帮助你,也许还有其他人。