AngularJS将事件/从服务更改为控制器

时间:2015-07-20 04:18:02

标签: angularjs angularjs-service angularjs-controller

我试图在两个控制器之间进行通信。我知道这可以通过引发事件然后使用$ rootScope。$ broadcast来完成,但不适用于大型应用程序。我看过很多博客文章,建议使用服务进行沟通,但无法成功实施。我的实际代码更复杂,但这是要点:

HTML:

<body ng-app="app">
    <div ng-controller="MainCtrl">
        <span>Source: {{count}}</span>
        <button ng-click="updateCount()">Increase Count</button>
    </div>
    <div ng-controller="ListCtrl">
        Destination: {{updatedCount}}
    </div>
</body>

JS:

(function () {

    var app = angular.module("app", []);

    app.factory("ShareDataSvc", function ($log) {

        var currentCount = 0;

        var set = function (val) {
            $log.info('Setting service value to: ' + currentCount);
            currentCount = val;
        }

        var get = function () {
            return currentCount;
        }

        return {
            set: set,
            get: get
        }
    });

    app.controller("MainCtrl", ['$scope', 'ShareDataSvc', function ($scope, ShareDataSvc) {
        $scope.count = ShareDataSvc.get();
        $scope.updateCount = function () {
            $scope.count = $scope.count + 1;
            ShareDataSvc.set($scope.count);
        }
    }]);

    app.controller("ListCtrl", ["$scope", "ShareDataSvc", function ($scope, ShareDataSvc) {
        $scope.updatedCount = ShareDataSvc.get();

        // trigger alert if count updated
        $scope.triggerAlert = function () {
            alert('Count updated!');
        }
    }]);
}());

我试图理解为什么Angular不会更新目标中的计数,即使它是数据绑定的。我的理解是,当在SharedDataSvc中更新计数时,将重新计算updatedCount属性。 我在这做错了什么?最终结果是在每次计数更新时触发警报。

1 个答案:

答案 0 :(得分:0)

您按价值问题遇到旧副本。当你这样做

$scope.updatedCount = ShareDataSvc.get();

更新后的count属性被设置为从get函数返回的值,因此不会看到将来对服务中跟踪的值的更改。你有两个选择来解决这个问题。一种是为每个控制器添加一个监视器来监视服务中的值。不理想。第二种是在服务中跟踪对象属性跟踪值,并将数据绑定到范围。像(注意我只展示有趣的部分):

app.factory("ShareDataSvc", function ($log) {

    var set = function (val) {
        $log.info('Setting service value to: ' + currentCount);
        this.data.count = val;
    }

    return {
        data: {count: 0}
        set: set
    }
});

app.controller("MainCtrl", ['$scope', 'ShareDataSvc', function ($scope, ShareDataSvc) {
    $scope.data = ShareDataSvc.data;
    $scope.updateCount = function () {
        ShareDataSve.data.count++; // and increment function in the service would be better
    }
}]);

app.controller("ListCtrl", ["$scope", "ShareDataSvc", function ($scope, ShareDataSvc) {
    $scope.data = ShareDataSvc.data;

}]);

然后在你的HTML

<body ng-app="app">
    <div ng-controller="MainCtrl">
        <span>Source: {{data.count}}</span>
        <button ng-click="updateCount()">Increase Count</button>
    </div>
    <div ng-controller="ListCtrl">
        Destination: {{data.count}}
    </div>
</body>