2013-03-16 22 views
20

Vì vậy, nếu tôi có một mảng:Có thể lọc angular.js bằng cách ngăn chặn trong một mảng khác không?

$scope.letters = 
[{"id":"a"}, 
{"id":"b"}, 
{"id":"c"}]; 

Và một mảng

$scope.filterBy = ["b","c","d"]; 

Và tôi muốn có một số ng-repeat để lọc $ scope.letters bởi chỉ mục xuất hiện trong $ filterBy.

Tôi muốn để có thể làm gì đó để tác động của:

<span ng-repeat="{{letter in letters|filter: letter.id in filterBy }} > {{letter.id}} </span> 

Và có nó in b, c

Tôi biết đây là một ví dụ thực sự ngu ngốc, nhưng là có một cách để lọc một biểu thức angular.js dựa trên nội dung của một đối tượng mảng khác?

Trả lời

29

Bạn nên thử một cái gì đó như thế:

JS:

angular.module('Test', []); 

function Ctrl($scope) { 
    $scope.letters = [ 
    {id: 'a'}, 
    {id: 'b'}, 
    {id: 'c'} 
    ]; 

    $scope.filterBy = ['b', 'c', 'd']; 

    $scope.filteredLetters = function() { 
    return $scope.letters.filter(function (letter) { 
     return $scope.filterBy.indexOf(letter.id) !== -1; 
    }); 
    }; 
} 

Ctrl.$inject = ['$scope']; 

HTML:

<div ng-repeat='letter in filteredLetters(letters)'>{{letter.id}}</div> 

Bạn có thể thử live example.

+6

filterLetters() sẽ được gọi là chu trình tiêu hóa _every_. Vì vậy, nếu bạn có trong lĩnh vực đầu vào bằng cách sử dụng ng-mô hình trong quan điểm của bạn, đó có nghĩa là tất cả các phím tắt. Sẽ tốt hơn nếu lưu trữ kết quả của bộ lọc trên thuộc tính $ scope mới. Sử dụng $ watch() es để cập nhật kết quả lọc nếu thay đổi 'letters' hoặc' filterBy'. –

+0

Điểm tốt. Cảm ơn về lời khuyên. – ValeriiVasin

+0

Trong khi nó sẽ hoạt động (miễn là ứng dụng của bạn rất đơn giản), tôi sẽ không khuyên bạn sử dụng phương pháp này - như @MarkRajcok đề cập, nó được gọi là mỗi chu kỳ tiêu hóa có nghĩa là hiệu suất là khủng khiếp và tôi đã nhận được lỗi từ góc tương tự như "Lỗi: [$ rootScope: infdig] 10 $ digest() lặp lại đạt được. Hủy bỏ! " –

35

Cập nhật

Dưới đây là một mô-đun góc (dựa trên câu trả lời @InviS) để dễ dàng thực hiện các bộ lọc này bên trong ứng dụng góc của bạn: filters-inArrayFilter


Dưới đây là các bộ lọc góc tiếp cận dựa trên @InviS answer:

Bộ lọc phải như sau:

.filter('inArray', function($filter){ 
    return function(list, arrayFilter, element){ 
     if(arrayFilter){ 
      return $filter("filter")(list, function(listItem){ 
       return arrayFilter.indexOf(listItem[element]) != -1; 
      }); 
     } 
    }; 
}); 

nơi danh sách là danh sách bạn đang lọc (param này được thiết lập theo mặc định bởi góc), arrayFilter là mảng bạn đang sử dụng như bộ lọc, và yếu tố là tên của thuộc tính để lọc trong danh sách của bạn.

Để sử dụng bộ lọc này bạn sử dụng ng-repeat của bạn như:

<div ng-repeat='letter in letters | inArray:filterBy:"id"'>{{letter.id}}</div> 

nơi inArray là bộ lọc, filterBy(đối số đầu tiên của bộ lọc này) là của bạn mảng để so khớp và "id"(đối số thứ hai) là elem ent của danh sách bạn muốn khớp với mảng.

Bạn có thể thử điều này live example bằng cách sử dụng phương pháp tiếp cận bộ lọc góc.

+0

Nếu tôi phải lọc nhiều cột thì sao? 'Chaining' sẽ làm gì? – dreamer

+0

@dreamer Bạn có ý nghĩa gì bởi nhiều cột? – Cyberdelphos

+0

@Cyberdelphos bạn sẽ lọc như thế nào nếu khóa đối tượng là một số? sử dụng $ index? – alphapilgrim

6

Khá cũ nhưng tôi cần nó và tôi đã phải thay đổi nó một chút. Đây là bộ lọc của tôi "notInArray"

app.filter('notInArray', function($filter){ 
return function(list, arrayFilter, element){ 
    if(arrayFilter){ 
     return $filter("filter")(list, function(listItem){ 
      for (var i = 0; i < arrayFilter.length; i++) { 
       if (arrayFilter[i][element] == listItem[element]) 
        return false; 
      } 
      return true; 
     }); 
    } 
}; 

});

<md-chips ng-model="filter.SelectedValues" md-autocomplete-snap 
      md-require-match="true"> 
     <md-autocomplete 
      md-search-text="searchFilterChip" 
      md-items="val in filter.Values | notInArray:filter.SelectedValues:'Id'" 
      md-item-text="val.Name" 
      md-no-cache="true" 
      md-min-length="0"> 
     <span md-highlight-text="searchFilterChip">{{val.Name}}</span> 
     </md-autocomplete> 
     <md-chip-template> 
     {{$chip.Name}} 
     </md-chip-template> 
    </md-chips> 

Tôi cho rằng điều này có thể được cải thiện nhưng không cần thiết trong trường hợp của tôi.

Hy vọng rằng sẽ giúp ai đó!

+0

thankyou usefull – Magico

Các vấn đề liên quan