从重复访问单个子控制器?

时间:2014-06-22 21:02:04

标签: angularjs

解释的最佳方式是这个例子:

<table ng-controller="groupOfPeopleController">
    <tr ng-repeat "person in peoples">
       <td>{{person.name}}</td>
       <td><button ng-click="load_data(person.id)">Load Data</button>
       <td><div class="personData" ng-controller="personDataController"></div></td>
    </tr>
</table>

我要做的是用它自己的数据填充div.personData。所以我在groupOfPeopleController中有一个名为load_data(id)的函数:

// groupOfPeopleController
$scope.load_data = function(id){
    $rootScope.$broadcast('load_data'id);
}

我想专门传递给子元素控制器personData。

// personDataController
$scope.$on('load_data',function(e,id){
   // hopefully affect only the div inside the current loop...
});

问题是,它附加到personData的每个循环。因此,单击一个人会影响每一行,因为它们都连接到同一个控制器。

我如何制作personData的单独实例?广播的方式是错误的吗?

2 个答案:

答案 0 :(得分:1)

请勿使用广播。是的,事件是好的,但在这种情况下不是。 并且循环中的项目正在更新,因为循环中的每个项都接收对同一个控制器的引用而不是它的实例。

正确的做法是使用指令。

将模板更改为:

<tr ng-repeat="person in peoples" data-person="person"></tr>

并使用类似这样的指令:

app.directive('person', function(){
    var templateStr = '<td>{{person.name}}</td>' +
        '<td><button ng-click="load_data(person.id)">Load Data</button>' +
        '<td><div class="personData">{{person.anyDataYouWantToDisplay}}</div></td>';
    var linkFn = function(scope){
       scope.load_data = function(id){
           // load person data and do something about it
       };
       // do other magic here as it is the controller for your individual person
    };
    return {
        restrict: 'A',
        scope: {
            person: '='
        }
        link: linkFn,
        template: templateStr
    };
});

希望有所帮助。

答案 1 :(得分:1)

不要从$ rootScope广播,它会将事件名称向下调度到所有子范围(及其子项递归)。

你能做什么,只是来自当前范围,而不是所有范围。请参阅此plunker

主要技巧是您需要子范围ng-repeat创建,因此您将关键字“this”传递给获取当前范围的函数,然后从那里广播事件。

元素:

<button ng-click="load_data(this, person.id)">Load Data</button>

groupOfPeopleController:

$scope.load_data = function(childScope, id){
  childScope.$broadcast('load_data', id);
}

但是,我建议不要使用此方法。为什么要播放任何广播/ $ on?您可以简单地将personDataController移动到tr的整个内容,并直接从ng-click调用loadData函数,如this plunker中所示。它可以为您节省一些麻烦和烦恼。