AngularJS:在promise之后的指令中失去作用域

AngularJS : Losing scope in directive after promise

本文关键字:指令 失去 作用域 之后 promise AngularJS      更新时间:2023-09-26

我在我的angular应用程序中实际上有一个大问题。

我有一个工厂,它做一个http请求获得假脱机程序,并返回一个承诺。

Spooler.prototype.load = function () {
    var self = this;
    var deferred = $q.defer();
    $http.post('/spooler/' + this.id + '/load')
        .success(function(data) {
            self.statistics = data.statistics;
            deferred.resolve(self);
        })
        .error(function(err, code) {
            deferred.reject(err);
        $log.error(err, code);
    });
    return deferred.promise;
};

当我使用"then()"关键字时,问题发生在我的控制器中,其中的值将传递给如下指令:

$scope.load = function(){
        spooler.load().then(
            function(dataSpooler){
                $scope.spooler = dataSpooler;
                $scope.custom = 4; // example of random var inside then()
            }
            function() {
                $scope.dataFail = 'error error' ;
            }
        );
    }

当我在视图中记录变量custom时,一切都很好,我看到'4'。然而,当我在我的指令中使用这个变量时,问题发生了,如下所示:

<highchart-pie items="custom"></highchart-pie>

下面是指令的代码:

 .directive('highchartPie', function () {
    return {
        restrict: 'E',
        replace: true,
        scope: {
           items : '='
        },
        controller: function ($scope, $element, $attrs) {
        },
        template: '<div style="width:100%;margin: 0 auto;">not working</div>', //
        link: function (scope, element, attrs) { 
                console.log(scope); // i can see the item value 4
                console.log(scope.items); !!! undefined !!!
                link function is actually way bigger and renders the element to the template (useless to be shown)
        }
    }
这是我的结论,当我赋值 时
$scope.custom = 4;

在then()函数中,它不起作用,因为指令可能没有及时接收到值(即使在指令的link函数中,日志看到了它)。

如果我声明$scope。Custom = 4;在then()方法之前的控制器顶部,每个工作都很顺利…

有什么主意吗?提前感谢!:)

第一种方式,

$scope.load = function(){
        return spooler.load().then(
            function(dataSpooler){
                $scope.spooler = dataSpooler;
                $scope.custom = 4; // example of random var inside then()
            }
            function() {
                $scope.dataFail = 'error error' ;
            }
        );
    }

但也许不是最好的方法,

$scope.load = spooler.load;

,

$scope.load().then(
                function(dataSpooler){
                    $scope.spooler = dataSpooler;
                    $scope.custom = 4; // example of random var inside then()
                }
                function() {
                    $scope.dataFail = 'error error' ;
                }
            );

您的console.log在promise被解析之前运行,这就是为什么这些项是未定义的。正如@Razvan Balosin在他的评论中提到的,你必须$watch items数组(这样当你最终获得数据时,Angular就会知道这个变化,你就可以对数据做任何你需要做的事情)

我建议你这样做:

link: function link(scope, element, attrs) {
 scope.$watch('film',function(item){
   // if there is any data in film, render chart
   if(item) {
    console.log("Scope: " , scope);
    console.log("Film:", scope.film); // works now
   }
  })
}

和修改后的柱塞