角度过滤搜索问题

时间:2017-04-24 10:44:41

标签: javascript angularjs angularjs-ng-repeat

好的,所以我不确定该怎么称呼这个问题。

通常你想在id字段上过滤<form method="POST" id="Form<?php echo $rstMilestones->fields['IdCronograma']; ?>0" action=""> <input type="date" style="font-size: 9px; font-style: bold;" name="FechaInicio" value="<?php echo $strFaseInicioSinFormato;?>"> <input type="hidden" name="IdCronograma" value="<?php echo $rstMilestones->fields['IdCronograma']; ?>"> <a href="#botones" id="<?php echo $rstMilestones->fields['IdCronograma']; ?>0" onclick="GuardarMilestone(this)"><img src="images/PC_si.png" alt="Save"></a> <a href="#botones" id="<?php echo $rstMilestones->fields['IdCronograma']; ?>0" onclick="EditarFechaCronograma(this)"><img src="images/PC_no.png" alt="cancel"></a> </form>,但这会产生问题。

比如说你有以下数组:

ng-repeat

现在您进行以下 $scope.objList = [ {id: 1, name:'A'}, {id: 2, name:'B'}, {id: 3, name:'C'}, {id: 4, name:'D'}, {id: 5, name:'E'}, {id: 6, name:'F'}, {id: 7, name:'G'}, {id: 8, name:'H'}, {id: 9, name:'I'}, {id: 10, name:'J'}, {id: 11, name:'K'} ];

ng-repeat

如果您然后将<div ng-repeat="obj in objList | filter:search"> <div> {{obj.id}} {{obj.name}} </div> </div> 设置为:search

您将获得以下结果:

search.id = 1

所以我想我的问题是如何避免这种情况,以便唯一的结果是1 A 10 J 11 K

请注意,我知道在这个例子中我只能搜索1 A键,但上面的例子只是为了说明一点。

你可以在这里找到这个问题的小提琴:

Fiddle

2 个答案:

答案 0 :(得分:2)

您应该添加:true以匹配精确搜索。

 ng-repeat="obj in objList | filter:search:true"

&#13;
&#13;
var myApp = angular.module('myApp',[]);

//myApp.directive('myDirective', function() {});
//myApp.factory('myService', function() {});

function MyCtrl($scope) {
    $scope.name = 'Superhero';
    $scope.search = {};
    $scope.objSelect = [{id: 1, name: 'A'}];
    
    
    $scope.objList = [
    {id: 1, name:'A'},
    {id: 2, name:'B'},
    {id: 3, name:'C'},
    {id: 4, name:'D'},
    {id: 5, name:'E'},
    {id: 6, name:'F'},
    {id: 7, name:'G'},
    {id: 8, name:'H'},
    {id: 9, name:'I'},
    {id: 10, name:'J'},
    {id: 11, name:'K'}
    ];
}
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="myApp" ng-controller="MyCtrl">

<select class="form-control" ng-model="search" ng-options="item.id as item.name for item in objSelect" fix-select-null>
    <option value=""></option>
</select>
    <div ng-repeat="obj in objList | filter:search:true">
        <div>
         {{obj.id}}     {{obj.name}}
        </div>
    </div>

</div>
&#13;
&#13;
&#13;

答案 1 :(得分:0)

问题是你使用的是一个非常旧版本的angularjs,它还不支持比较器。你能升级吗?我相信angularjs v1.2.30及以上已经支持比较器,否则我使用函数作为filterFilter的表达式(即obj in objList | filter:myFilterExpression其中myFilterExpression = function (value) : boolean

快速解决方案

至少将angularjs升级到v1.2.30并使用comparator,如下所示:

obj in objList | filter:search:true

使用函数作为表达式

obj in objList | filter:myFilter

$scope.myFilter = function (item) {
    return /* my filter criteria */;
};

如果你无法摆脱angularjs v1.0.1

您可以将decorator应用于angularjs模块中的filterFilter,并使用v1.2.30过滤器逻辑覆盖原始过滤器(顺便说一下,我从angularjs repositorie偷走了)已经有比较器功能。这样您就可以使用快速解决方案而无需升级。

(function() { // begin hack
  angular.module('ng')
    .config(['$provide', function($provide) {
      $provide.decorator('filterFilter', ['$delegate', function($delegate) {
        var filterFilterv1_0_1 = $delegate;

        return filterFilterv1_2_30();
      }]);
    }]);

  function filterFilterv1_2_30() {
    return function(array, expression, comparator) {
      if (!angular.isArray(array)) return array;

      var comparatorType = typeof(comparator),
        predicates = [];

      predicates.check = function(value) {
        for (var j = 0; j < predicates.length; j++) {
          if (!predicates[j](value)) {
            return false;
          }
        }
        return true;
      };

      if (comparatorType !== 'function') {
        if (comparatorType === 'boolean' && comparator) {
          comparator = function(obj, text) {
            return angular.equals(obj, text);
          };
        } else {
          comparator = function(obj, text) {
            if (obj && text && typeof obj === 'object' && typeof text === 'object') {
              for (var objKey in obj) {
                if (objKey.charAt(0) !== '$' && hasOwnProperty.call(obj, objKey) &&
                  comparator(obj[objKey], text[objKey])) {
                  return true;
                }
              }
              return false;
            }
            text = ('' + text).toLowerCase();
            return ('' + obj).toLowerCase().indexOf(text) > -1;
          };
        }
      }

      var search = function(obj, text) {
        if (typeof text === 'string' && text.charAt(0) === '!') {
          return !search(obj, text.substr(1));
        }
        switch (typeof obj) {
          case 'boolean':
          case 'number':
          case 'string':
            return comparator(obj, text);
          case 'object':
            switch (typeof text) {
              case 'object':
                return comparator(obj, text);
              default:
                for (var objKey in obj) {
                  if (objKey.charAt(0) !== '$' && search(obj[objKey], text)) {
                    return true;
                  }
                }
                break;
            }
            return false;
          case 'array':
            for (var i = 0; i < obj.length; i++) {
              if (search(obj[i], text)) {
                return true;
              }
            }
            return false;
          default:
            return false;
        }
      };
      switch (typeof expression) {
        case 'boolean':
        case 'number':
        case 'string':
          // Set up expression object and fall through
          expression = {
            $: expression
          };
          // jshint -W086
        case 'object':
          // jshint +W086
          for (var key in expression) {
            (function(path) {
              if (typeof expression[path] === 'undefined') return;
              predicates.push(function(value) {
                return search(path == '$' ? value : (value && value[path]), expression[path]);
              });
            })(key);
          }
          break;
        case 'function':
          predicates.push(expression);
          break;
        default:
          return array;
      }
      var filtered = [];
      for (var j = 0; j < array.length; j++) {
        var value = array[j];
        if (predicates.check(value)) {
          filtered.push(value);
        }
      }
      return filtered;
    };
  }
})();// end hack

var myApp = angular.module('myApp', []);

//myApp.directive('myDirective', function() {});
//myApp.factory('myService', function() {});

function MyCtrl($scope) {
  $scope.name = 'Superhero';
  $scope.search = {};
  $scope.objSelect = [{
    id: 1,
    name: 'A'
  }];


  $scope.objList = [{
      id: 1,
      name: 'A'
    },
    {
      id: 2,
      name: 'B'
    },
    {
      id: 3,
      name: 'C'
    },
    {
      id: 4,
      name: 'D'
    },
    {
      id: 5,
      name: 'E'
    },
    {
      id: 6,
      name: 'F'
    },
    {
      id: 7,
      name: 'G'
    },
    {
      id: 8,
      name: 'H'
    },
    {
      id: 9,
      name: 'I'
    },
    {
      id: 10,
      name: 'J'
    },
    {
      id: 11,
      name: 'K'
    }
  ];
}
<div ng-app="myApp" ng-controller="MyCtrl">

  <select class="form-control" ng-model="search" ng-options="item.id as item.name for item in objSelect" fix-select-null>
    <option value=""></option>
</select>
  <div ng-repeat="obj in objList | filter:search:true">
    <div>
      {{obj.id}} {{obj.name}}
    </div>
  </div>

</div>

<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.0.1/angular.js"></script>