Angularjs承诺,不会及时通知绑定的更新进度



我试图提供使用angularjs运行的任务的进度,但在执行deferred.notify()时更新绑定时遇到问题。

以下是我为重现问题(Plunker)而做的一个例子

var app = angular.module('app', [
  'ngAnimate',
  'ui.bootstrap'
]);

(function() {
  'use strict';
  var controllerId = 'testController';
  angular.module('app').controller(controllerId, ['$timeout', '$q', '$scope', testController]);
  function testController($timeout, $q, $scope) {
    $scope.callLongProcess = callLongProcess;
    $scope.value = '-';
    $scope.progress = 0;

    function longProccess() {
      var def = $q.defer();
      $timeout(function() {
        for (var i = 0; i < 200000; i++) {
          if (i % 2 === 0) {
            //WHY THIS LINES DOES NOT UPDATE THE UI WHEN RUNNING
            def.notify(i);
            $scope.$apply();
          }
        }
        def.resolve("success");
      }, 0);
      return def.promise;
    }

    function callLongProcess() {
      longProccess()
        .then(
          function(results) {
            $scope.value = results;
          },
          function(error) {
            $scope.value = error;
          },
          function(progress) {
            $scope.progress = progress;
          })
    }
  }
})();

您在超时函数中陷入了200000次迭代的紧密循环。尽管您已经调用了$scope$应用100000次,循环必须在angular有机会做任何事情之前完成。这是因为$scope$application通过向主浏览器事件循环添加另一个事件异步运行,而不是立即运行。

如果你想更新进度,你必须将"longProcess"函数分解成更小的块,你可以通过回调异步处理这些块。

最新更新