【问题标题】:Need to use $timeout and $apply with requestAnimationFrame需要将 $timeout 和 $apply 与 requestAnimationFrame 一起使用
【发布时间】:2016-03-12 11:59:14
【问题描述】:

我正在尝试使用 requestAnimationFrame 创建一个带有滚动数字的 javascript 动画

为了看到动画滚动,我需要使用 $apply 来刷新视图。这里的问题是当我开始动画时,摘要循环已经在运行,所以我的 $apply 返回一个错误“$apply already in progress”。

我正在寻找一个解决方案,我使用 $timeout of 0 可以完美地工作,但我想知道是否有其他解决方案可以避免使用在性能方面不是很好的超时?

感谢您的帮助!

HTML代码:

<div ng-app="myApp">
  <div ng-controller="myController as ctrl">
    <animated-counter data-from='0' data-to='{{ctrl.limit}}'></animated-counter>
  </div>
</div>

Javascript 代码:

(function(){
'use strict';

angular
    .module('myApp', [])
    .directive('animatedCounter', AnimatedCounter);

    AnimatedCounter.$inject = ['$timeout'];

    function AnimatedCounter($timeout) {
        return {
            restrict: 'E',
            template: '<div>{{num}}%</div>',
            link: function (scope, element, attrs) {
                scope.num = parseInt(attrs.from);
                var max = parseInt(attrs.to);

                //Loop to increment the num
                function animloop() {
                    if (scope.num >= max) { //Stop recursive when max reach
                        return;
                    }
                    requestAnimationFrame(animloop);
                    scope.$apply(function() {
                        scope.num += 1;
                    });
                }

                // $timeout(function() { //if I use $timeout it works perfectly
                    animloop();
                // });
            }
        };
    }


 angular
    .module('myApp')
    .controller('myController', myController);

    function myController() {
       var vm = this;
       vm.limit = 100;
    }
})();

你可以在这里找到一个 CodePen

http://codepen.io/phliem/pen/ZWOjwz?editors=1011

【问题讨论】:

  • 试试这个范围。$evalAsync() (function() { scope.num += 1; });
  • 工作非常感谢!

标签: angularjs timeout requestanimationframe angularjs-digest


【解决方案1】:

如果我像 HadiJZ 所说的那样使用 $evalAsync(),效果会很好!

只需要更换

scope.$apply(function() {
   scope.num += 1;
});

scope.$evalAsync(function() {
   scope.num += 1;
})

这里有一篇好文章http://www.bennadel.com/blog/2605-scope-evalasync-vs-timeout-in-angularjs.htm

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-08-28
    • 2013-08-13
    • 2017-10-25
    • 1970-01-01
    • 2014-05-29
    • 2020-07-10
    • 2018-11-26
    相关资源
    最近更新 更多