【问题标题】:$rootScope.$broadcast not working$rootScope.$broadcast 不工作
【发布时间】:2016-06-09 05:13:56
【问题描述】:

我正在尝试让 $rootScope.$broadcast 刷新我的视图。 该服务是-

var app = angular.module("productsApp", [])
    .service("serviceProvider", function ($http) {
        this.getDatas = function getDatas(data) {
            return $http({
                method: 'POST', url: serviceUrl + '/GetProductsByCategoryOrName', headers: {
                    'Authorization': apiKey
                },
                data: data
            })
        }
        return this
    }).factory("sharedService", function ($rootScope) {

        var mySharedService = {};

        mySharedService.values = [];

        mySharedService.passData = function (newData) {
            mySharedService.values = newData;
            $rootScope.$broadcast('dataPassed', newData);
        }

        return mySharedService;
    });

通过控制器调用-

function searchProductsController($scope, $window, serviceProvider, sharedService) {
    $scope.submit = function () {
        var data = { "query": $scope.searchText, "categoryId": "976759", "pageIndex": 0, "sortDirection": "asc" };
        serviceProvider.getDatas(data).then(function (response) {
            var result = response;
            sharedService.passData(result.data.data);
        });
    }
};

在此控制器sharedService.passData 中,它将新数组传递给服务方法。然后它试图用$rootScope.$broadcast('dataPassed', newData)这一行来广播它的变化@

我不知道为什么它不广播要查看的更改。有没有其他方法可以广播更改?

注意- 我之前的问题How to transfer data between controllers 没有得到任何帮助。

编辑

到目前为止,我已经改变了听众 -

mySharedService.passData = function (newData) {
    $rootScope.$broadcast('dataPassed', newData)
}
$rootScope.$on('dataPassed', function (newData) {
    mySharedService.values = newData;
})

但仍然无法刷新视图。

【问题讨论】:

  • 你的$scpe.$on在哪里?
  • @Artless,我该如何使用它?
  • $broadcast 不会直接在视图上异步数据...您需要使用 $on 在广播事件上设置侦听器,然后您可以在它的回调函数中获取广播数据。并再次重新分配数据以在范围内反映它。
  • @PankajParkar,我尝试了以下两个答案,但没有一个对我有用。恐怕我做错了什么。你能帮帮我吗
  • 以下解决方案应该可以工作..如果你没有做错什么..请添加 plunkr

标签: angularjs angularjs-directive angular-broadcast


【解决方案1】:

你犯了一个很小但很有效的错误。改变你的听众:

$rootScope.$on('dataPassed', function (newData) {
    mySharedService.values = newData;
});

到这里:

$rootScope.$on('dataPassed', function ($event, newData) {
    mySharedService.values = newData;
});

在分派的任何 AngularJS 范围事件上,每个侦听器的第一个参数是一个 $event 对象。

我很惊讶一个老问题,有这么多答案,却没有注意到真正的问题。

【讨论】:

    【解决方案2】:

    您应该设置一个侦听器来收听广播事件。广播事件不会直接在视图 html 上直接更新您的视图数据。您必须在作用域上使用$on 才能在作用域上绑定事件。在它的回调函数里面。您将受益于获取广播数据并将检索数据重新分配给范围变量以获取更新的绑定。

    代码

    var app = angular.module("productsApp", [])
      .service("serviceProvider", function($http) {
      this.getDatas = function getDatas(data) {
        return $http({
          method: 'POST',
          url: serviceUrl + '/GetProductsByCategoryOrName',
          headers: {
            'Authorization': apiKey
          },
          data: data
        })
      }
      return this;
    }).factory("sharedService", ['$rootScope', function($rootScope) {
    
      var mySharedService = {};
    
      mySharedService.values = [];
    
      mySharedService.passData = function(newData) {
        mySharedService.values = newData;
        $rootScope.$broadcast('dataPassed', newData)
      }
    
      return mySharedService;
    }]);
    
    function GetController($scope, serviceProvider, sharedService, $rootScope) {
      var data = {
        "query": "grocery",
        "categoryId": "976759",
        "pageIndex": 0,
        "sortDirection": "asc"
      };
      serviceProvider.getDatas(data).then(function(response) {
        sharedService.passData(response.data.data);
      });
      //listener should register when controller loads
      $scope.$on('dataPassed', function(event, newData) {
        sharedService.values = newData;
        $scope.products = sharedService.values;
      })
    }
    
    function searchProductsController($scope, $window, serviceProvider, sharedService, $rootScope) {
        $scope.submit = function() {
          var data = {
            "query": $scope.searchText,
            "categoryId": "976759",
            "pageIndex": 0,
            "sortDirection": "asc"
          };
          serviceProvider.getDatas(data).then(function(response) {
            var result = response;
            sharedService.passData(result.data.data);
          });
        }
        //listener should register when controller loads
        $scope.$on('dataPassed', function(event, newData) {
          console.log(newData);
          sharedService.values = newData;
        })
    };
    

    【讨论】:

    • 如何在服务中访问 $scope?
    • 不,你不应该......上面的代码你应该放在控制器中
    • 你能在stackoverflow群聊中查看我的js吗?我仍然没有得到这项工作
    【解决方案3】:

    @Manoz 至于你之前的回答,我已经给你答案了。我也为此更新了 plunker。至于使用$rootscope.,你有2个参数,其中一个是事件,下一个是你正在广播的数据。我在两个答案中都嘲笑了您的 api 调用,以使您更加理解。

    这里是使用$rootscope:http://plnkr.co/edit/MBzDMRll5Z4CjusY5QLN?p=preview的plunker

    <html>
    
       <head>
          <title>Angular JS Controller</title>
          <script src = "http://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular.min.js"></script>
       </head>
    
       <body>
          <h2>AngularJS Sample Application</h2>
    
          <div ng-app = "app" >
    
               <div ng-controller="searchProductsController">
                 <input ng-model="searchText"/>
                    <button ng-click="setPlace(searchText)">Enter Search id</button>
                </div>
                <div ng-controller="GetController">
                  <div ng-repeat="product in products">
                                    <h3>{{product.name}}</h3>
                    </div>
                  </div>
          </div>
    
    
    <script>
             var app = angular.module('app', []);
             app.run(['$rootScope', function($rootScope){
                  $rootScope.test = 123;
                }]);
    
            app.factory("Service", function ($rootScope) {
                function passData(newData) {
                  alert('i am here');
                   $rootScope.$broadcast('dataPassed', newData);
                }
                return {
                    passData: passData
                }
            }).factory("dataService",function($http){//mock for getting values from api
              return{
                getComments:function (roomid){
                       if(roomid==1){
                         var data = [{"name":"alex","place":"kathmandu"},{"name":"god","place":"seattle"}];
                         return data;
                       }
                       if(roomid==2)
                       {
                         var newdata = [{"name":"newname","place":"kathmandu"},{"name":"newname2","place":"seattle"}];
                         return newdata;
                       }
                  }
              }
            });
            app.controller('searchProductsController',function($scope, Service,$http,dataService) {
                $scope.setPlace = function (searchText) {
                    var newdata = dataService.getComments(searchText);
                    Service.passData(newdata);
                }
            })
            .controller('GetController',function($scope, Service,$rootScope) {
              $rootScope.$on('dataPassed', function (event,args) {
                    $scope.products = args;
                })
            })
                  </script>
    
       </body>
    </html>
    

    【讨论】:

      【解决方案4】:

      当您使用 $broadcast 或 $emit 时。你应该有 $scope.$on 来监听那个事件。

      $scope.$on('dataPassed', function(){ //code go here });
      

      编辑:更新问题要求的工作代码

      var app = angular.module("productsApp", [])
          .service("serviceProvider", function ($http) {
              this.getDatas = function getDatas(data) {
                  return $http({
                      method: 'POST', url: serviceUrl + '/GetProductsByCategoryOrName', headers: {
                          'Authorization': apiKey
                      },
                      data: data
                  });
              }
              return this
          }).factory("sharedService", ['$rootScope', function ($rootScope) {
              var mySharedService = {
                  values: [],
                  setValues: function(data){
                      if(data){
                          mySharedService.values.length = 0;
                          data.forEach(function(item){
                              mySharedService.values.push(item);
                          });    
                      }
                  }
              };
              return mySharedService;
          }]);      
      function GetController($scope, serviceProvider, sharedService, $rootScope) {
          var shareData = sharedService;
          $scope.products = sharedService.values;
          $scope.shareData = sharedService;
          var data = { "query": "grocery", "categoryId": "976759", "pageIndex": 0, "sortDirection": "asc" };
          serviceProvider.getDatas(data).then(function (response) {
              sharedService.setValues(response.data.data);
          });
      }
      function searchProductsController($scope, $window, serviceProvider, sharedService, $rootScope) {
          $scope.submit = function () {
              var data = { "query": $scope.searchText, "categoryId": "976759", "pageIndex": 0, "sortDirection": "asc" };
              serviceProvider.getDatas(data).then(function (response) {
                  sharedService.setValues(response.data.data);
              });
          }
      };
      

      【讨论】:

        【解决方案5】:

        你应该听你正在广播的内容:

        $rootScope.$on('dataPassed', function(data){
        console.log(data);
        });
        

        此参考可能会有所帮助:Why do we use $rootScope.$broadcast in AngularJS?

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2018-03-16
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多