AngularJs 广播事件

AngularJs broadcast event

本文关键字:事件 广播 AngularJs      更新时间:2023-09-26

我想从javascript函数即angular.injector(['ng', 'myModule'](.get("mySharedService"(.prepForBroadcast('hello'(;通过使用上面的行,我可以调用prepForBroadcast((,但我无法在$scope.$on((中捕获事件

注意:我想从javascript函数调用prepForBroadcast((方法。

    <!-- index.html -->
<!DOCTYPE html>
<html>
<head>
  <!-- SPELLS -->
  <!-- load angular via CDN -->
  <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.0.8/angular.min.js"></script>
  <script src="script.js"></script>
  <style>
    .question{
        border:1px solid darkgray;
        padding:10px;
        margin-bottom:10px;
    }
  </style>
</head>
<body>
    <div ng-app="myModule">
        <div id="appID" ng-controller="ControllerZero">
            <input ng-model="message" >
        </div>
        <div ng-controller="ControllerOne">
            <input ng-model="message" >
        </div>
        <div ng-controller="ControllerTwo">
            <input ng-model="message" >
        </div>
        <my-component ng-model="message"></my-component>
    </div>
</body>
<script>
angular.injector(['ng','myModule']).get("mySharedService").prepForBroadcast('hello');
</script>
</html>

脚本.js文件

var myModule = angular.module('myModule', []);
myModule.factory('mySharedService', function($rootScope) {
    var sharedService = {};
    sharedService.message = '';
    sharedService.prepForBroadcast = function(msg) {
        console.log('prepForBroadcast');
        this.message = msg;
        this.broadcastItem();
    };
    sharedService.broadcastItem = function() {
        console.log('broadcastItem');
        $rootScope.$broadcast('handleBroadcast');
    };
    return sharedService;
});
myModule.directive('myComponent', function(mySharedService) {
    return {
        restrict: 'E',
        controller: function($scope, $attrs, mySharedService) {
            $scope.$on('handleBroadcast', function() {
                $scope.message = 'Directive: ' + mySharedService.message;
            });
        },
        replace: true,
        template: '<input>'
    };
});
function ControllerZero($scope, sharedService) {
    $scope.$on('handleBroadcast', function() {
        console.log('handle event');
        $scope.message = sharedService.message;
    });
}
function ControllerOne($scope, sharedService) {
    $scope.$on('handleBroadcast', function() {
        $scope.message = 'ONE: ' + sharedService.message;
    });
}
function ControllerTwo($scope, sharedService) {
    $scope.$on('handleBroadcast', function() {
        $scope.message = 'TWO: ' + sharedService.message;
    });
}

ControllerZero.$inject = ['$scope', 'mySharedService'];
ControllerOne.$inject = ['$scope', 'mySharedService'];
ControllerTwo.$inject = ['$scope', 'mySharedService'];

angular.injector()创建一个新的注入器,并随之创建一个新的$rootScope。事件将在此新$rootScope上广播,而不是在控制器正在侦听的上广播。

您需要检索已与应用程序关联的注入器:

angular.element(domElement).injector();

您还需要手动触发摘要循环以更新数据绑定,例如使用 $apply

例:

angular.element(document).ready(function() {
  var element = angular.element(document.querySelector('.ng-scope'));
  var injector = element.injector();
  var scope = element.scope();
  scope.$apply(function() {
    injector.get('mySharedService').prepForBroadcast('hello');
  });
});

演示:http://plnkr.co/edit/NDKBdzSmvN1xY7alafir?p=preview

从一个控制器发布事件并在其他控制器中侦听它们的另一种方法是使用 angular-PubSub 模块。

PubSub使订阅者仅侦听已发布的事件,这与将事件发送到 Scope 层次结构中的所有作用域的$rootScope.$broadcast不同,与 PubSub 方法相比,效率低下。