Javascript 传递到指令的数据上的筛选器引发异常

Javascript 传递到指令的数据上的筛选器引发异常,javascript,angularjs,angularjs-directive,angularjs-filter,Javascript,Angularjs,Angularjs Directive,Angularjs Filter,我正在使用一个指令来模板化对象列表。根据指令的使用位置,应过滤模板中呈现的对象列表。在一种方法中,代码如下所示: person_list.html 选定的过滤器.js 该指令的使用方式如下: 我想使用的另一种方法是从指令外部筛选列表: person_list.html .目前代码中有相当多的竞争条件(初始化顺序)和其他微妙之处 首先,解决您描述的错误 解析前,承诺的初始值是多少 当第一次评估people | selected:true时,people是一个未解决的承诺。因此,angular

我正在使用一个指令来模板化对象列表。根据指令的使用位置,应过滤模板中呈现的对象列表。在一种方法中,代码如下所示:

person_list.html

选定的过滤器.js

该指令的使用方式如下:

我想使用的另一种方法是从指令外部筛选列表:

person_list.html


  • .

    目前代码中有相当多的竞争条件(初始化顺序)和其他微妙之处

    首先,解决您描述的错误

    解析前,
    承诺的初始值是多少
    当第一次评估
    people | selected:true
    时,
    people
    是一个未解决的承诺。因此,
    angular
    使用值
    undefined
    调用过滤器。这是正确的(TM)行为,因为将有一些过滤器希望捕获未定义的
    ,然后在后台解析值时显示一些默认值。这种情况需要在过滤器中处理:

    app.filter('selected', function(){
      return function(list, criteria){
         if(!angular.isUndefined(list)){
            return list.filter(function(element){
              return !!element.selected === criteria;
            });
         }
      }
    });
    
    app.filter('selected',function(){
    返回函数(列表、条件){
    如果(列表类型!==“未定义”){
    返回列表.过滤器(函数(元素){
    return!!element.selected==条件;
    });
    }否则{
    返回[];
    }
    }
    });
    
    使用angular的
    过滤器
    ,可以更容易地将此过滤器编写为
    人员|过滤器:{'selected':true}
    。我假设您有使用自定义过滤器的理由

    其他问题 指令
    范围
    是先初始化的还是控制器的
    范围
    属性
    people
    ListCtrl
    指令的独立范围中定义:

    app.directive('personList',function(){
    返回{
    限制:'E',
    
    作用域:{people:'=list'},//设置中存在许多问题。建议您在指令中使用完全不同的控制器引用,因为您正在从
    ListCtrl
    向指令传递数据,然后在指令中调用同一控制器并再次检索相同的数据

    一个问题是digest cycle将在从承诺中获得数据之前运行该指令。承诺似乎不会传递给指令。这意味着在首次运行筛选器时未定义指令中的
    人员
    的范围

    要修复过滤器,请执行以下操作:

    app.filter('selected', function(){
      return function(list, criteria){
         if(!angular.isUndefined(list)){
            return list.filter(function(element){
              return !!element.selected === criteria;
            });
         }
      }
    });
    
    不要尝试对指令的属性进行筛选。
    ng repeat
    允许这样做,因为它的指令需要筛选。请将筛选放在模板中的ng repeat上,或筛选指令本身中的数据


    更简单的演示会有所帮助…因此不必费力地浏览多个文件。我更新了Plunker,使其仅使用相关组件。请再看一看。如果您使用
    angular.isUndefined
    可避免摘要问题和承诺问题。请参阅我提供的演示。我使用了与您使用$watch相同的功能,但它在没有itO的情况下仍能正常工作其中一个有趣的问题是在指令的双向绑定中使用
    过滤器
    表达式。您在回答中提出的建议是合理的,但您已经通过建议在
    ng repeat
    上使用过滤器来解决了这个问题。这个示例最终的工作原理基本上无关紧要。:-)仍然必须在通过属性将对对象或变量的引用传递到指令的限制范围内工作。在sourceBTW中有相当多的代码用于使
    ng repeat
    工作-一个非常有用的解决方案是使用
    resolve
    routeProvider
    中进行ajax调用,以确保数据可用在对视图模板进行消化之前,
    resolve
    值得一看……还可以使用依赖项注入将数据传递给控制器。下面是一些方便的视频链接
    app.filter('selected', function(){
      return function(list, criteria){
        return list.filter(function(element){
          return !!element.selected === criteria;
        });
      }
    });
    
    <ul>
      <li ng-repeat="person in people">
      <a class="selected-{{ person.selected }}" ng-click="toggleSelect( person )">{{ person.name }}</a>
      </li>
    </ul>
    
    app.filter('selected', function(){
      return function(list, criteria){
         if(!angular.isUndefined(list)){
            return list.filter(function(element){
              return !!element.selected === criteria;
            });
         }
      }
    });