在指令模板中使用ng Repeat

时间:2015-01-24 00:03:40

标签: angularjs angularjs-ng-repeat

参考此plnkr了解我现在的工作情况。

angular.module('app', function(){
})
.run(function($rootScope){
  $rootScope.values = [1,2,3,4];
})
.directive('outer', function(){
  return {
    restrict:'E',
    scope:{
      items: '&'
    },
    replace: true,
    template:'<div><inner items="items()"></inner></div>',
    compile: function(){
      return function(){
      };
    }
  };
})
.directive('inner', function(){
  return {
    restrict:'E',
    scope:{
      items: '&'
    },
    replace: true,
    template:'<div ng-repeat="item in items()">{{item}}</div>',
    compile: function(){
      return function(){
      };
    }
  };
});

这显然是一个人为的例子,但它突出了这个问题。我在指令中有一个ng-repeat,它埋藏在几层深处。我可以从外部范围传递一个集合,使其成为ng-repeat就好了。但是,我真正想要做的是让外部指令的使用者能够传递ng-repeat表达式(即,按项目ID跟踪的值中的项目),该表达式可以针对外部作用域而不是集合进行运行

我希望我的内部指令能够利用ng-repeat中内置的逻辑来优化集合更改时的渲染。

我调查的一个选项是制作新版本的ng-repeat,它支持通过表达式直接设置变量,集合和跟踪,但显然更愿意只利用现有的实现。其他选项是为每个实例使用$ compile。两者都可行,但我希望有一种更优雅的方式。

1 个答案:

答案 0 :(得分:0)

我觉得一种干净的方法是基于表达式构建指令模板作为函数中处理的属性值。我有一个工作版本,您可以将表达式作为外部指令HERE上的属性传递。

外部指令清晰易懂。

Test Directive passing expression
<outer outervalues="values" expression="(k,v) in outervalues"></outer>

<br>
Filter passed in expression to inner scope
<outer outervalues="values" expression="(k,v) in outervalues | filter:'bob'"></outer>

<br>
Filter on outer scope
<div ng-init="morevalues = ( values | filter:'bob')"></div>
<div ng-repeat="(k,v) in morevalues">
   <input ng-model="v.name">
</div>

<br>
Directive from filtered outer scope
<outer outervalues="morevalues" expression="(k,v) in outervalues"></outer>

指令如下:

.directive('outer', function(){
  return {
    restrict:'E',
    scope:{
      outervalues: '=outervalues'
    },
    replace: true,
    template: function (elem, attr) {
              return '<div><inner outervalues="outervalues" nestedex="' + attr.expression + '"></inner></div>';
            },
    compile: function(){
      return function(){
      };
    }
  };
})
.directive('inner', function(){
  return {
    restrict:'E',
    scope:{
      outervalues: '=outervalues'
    },
    replace: true,
    template: function (elem, attr) {
              return '<div ng-repeat="' + attr.nestedex + '"><input ng-model="v.name"></div>';
            },
    compile: function(){
      return function(){
      };
    }
  };
});

希望有所帮助。