2013-03-25 9 views
113

W Angular mam w zakresie obiekt, który zwraca wiele obiektów. Każdy z nich ma identyfikator (ten jest przechowywany w pliku płaskiego więc nie DB, i wydaje się nie być w stanie użytkownik ng-resource)W trybie Angular muszę wyszukiwać obiekty w tablicy

W moim kontrolera:

$scope.fish = [ 
    {category:'freshwater', id:'1', name: 'trout', more:'false'}, 
    {category:'freshwater', id:'2', name:'bass', more:'false'} 
]; 

Moim zdaniem mam dodatkowych informacji na temat Ryby domyślnie ukryte, ale po kliknięciu prostej zakładki więcej pokażę funkcję showdetails(fish.fish_id). Moja funkcja będzie wyglądać następująco:

$scope.showdetails = function(fish_id) { 
    var fish = $scope.fish.get({id: fish_id}); 
    fish.more = true; 
} 

obecnie w widoku tym więcej szczegółów pojawi. Jednak po przeszukaniu dokumentacji nie mogę znaleźć sposobu na wyszukanie tablicy fish.

Jak mogę wysłać zapytanie do tablicy? A w konsoli, jak mogę wywołać debugger, aby mieć obiekt $scope do grania?

Odpowiedz

95

Wiem, że to może ci trochę pomóc.

Oto coś, co próbowałem zasymulować.

kasie jsFiddle;)

http://jsfiddle.net/migontech/gbW8Z/5/

Utworzono filtr, który można również wykorzystać w 'ng-repeat'

app.filter('getById', function() { 
    return function(input, id) { 
    var i=0, len=input.length; 
    for (; i<len; i++) { 
     if (+input[i].id == +id) { 
     return input[i]; 
     } 
    } 
    return null; 
    } 
}); 

wykorzystanie w kontrolerze:

app.controller('SomeController', ['$scope', '$filter', function($scope, $filter) { 
    $scope.fish = [{category:'freshwater', id:'1', name: 'trout', more:'false'}, {category:'freshwater', id:'2', name:'bass', more:'false'}] 

    $scope.showdetails = function(fish_id){ 
     var found = $filter('getById')($scope.fish, fish_id); 
     console.log(found); 
     $scope.selected = JSON.stringify(found); 
    } 
}]); 

Jeśli są jakieś pytania, daj mi znać.

+0

Jako Im nowe do kanciasty i javascript, ja nie dostaję sens '+' w "if (+ input [i] == .id + id) {" oświadczenie Czy możesz podzielić się swoimi przemyśleniami? – Harshavardhan

+0

Idealne rozwiązanie !! –

+1

Myślę, że "+ input [i] .id == + id" zapewnia porównywanie liczb. Więc możesz przekazać 1 lub "1" do filtru $ i będzie zachowywał się dokładnie tak samo. Używam identyfikatorów alfanumerycznych, więc zmieniłem go na "input [i] .id === id" –

13

Brudny i łatwe rozwiązanie mogłoby wyglądać

$scope.showdetails = function(fish_id) { 
    angular.forEach($scope.fish, function(fish, key) { 
     fish.more = fish.id == fish_id; 
    }); 
}; 
+5

Dlaczego to jest rozwiązanie _dirty_? – Trialcoder

+5

Domyślam się, że może istnieć miliard rejestrów ryb i po prostu przeglądamy je jeden po drugim. – RedactedProfile

+6

Będzie więcej rekordów w innych językach. Mam na myśli, że w C++ jest mnóstwo ryb. (Och, zamknij się ... Pójdę i zagłosuję ... !!) –

210

Można użyć istniejącej usługi $ filtra. I uaktualniony skrzypce powyżej http://jsfiddle.net/gbW8Z/12/

$scope.showdetails = function(fish_id) { 
    var found = $filter('filter')($scope.fish, {id: fish_id}, true); 
    if (found.length) { 
     $scope.selected = JSON.stringify(found[0]); 
    } else { 
     $scope.selected = 'Not found'; 
    } 
} 

Kątowymi dokumentacji jest tutaj http://docs.angularjs.org/api/ng.filter:filter

+4

Oczywiście - o wiele łatwiej niż przepisywanie ponownie. –

+2

Bardzo pomocne - Kiedy uczę się kątowego, zdaję sobie sprawę, że najpierw muszę przestać myśleć o funkcjach jQuery (próbowałem zrobić to za $ .grep) - raczej używanie tej usługi filtrującej było właśnie tym, czego potrzebowałem! – Bobby

+2

Lepsza odpowiedź, ponieważ nie wymaga pisania własnych filtrów. – stevenw00

22

Aby dodać użytkownika @ migontech odpowiedź, a także jego adres swoim komentarzu, że można „prawdopodobnie uczynić go bardziej rodzajowe”, oto sposób to zrobić to. Poniższy pozwoli Ci wyszukać dowolnym miejscu:

.filter('getByProperty', function() { 
    return function(propertyName, propertyValue, collection) { 
     var i=0, len=collection.length; 
     for (; i<len; i++) { 
      if (collection[i][propertyName] == +propertyValue) { 
       return collection[i]; 
      } 
     } 
     return null; 
    } 
}); 

Wezwanie do filtrowania by następnie stać:

var found = $filter('getByProperty')('id', fish_id, $scope.fish); 

Uwaga, usunąłem jednoargumentowy (+), operatora, aby umożliwić meczów smyczkowych opartej ...

+0

biorąc pod uwagę dokumentację stwierdza, że ​​jest to jedyny przypadek użycia dla ng-init, powiedziałbym, że jest to zdecydowanie Angularny sposób to zrobić. – bluehallu

+0

Bardzo łatwy do zrozumienia przykład i bardzo pomocna – rainabba

7

Twoje rozwiązania są poprawne, ale niepotrzebne skomplikowane.Możesz użyć funkcji czystego javascript filtru. Jest to model:

 $scope.fishes = [{category:'freshwater', id:'1', name: 'trout', more:'false'}, {category:'freshwater', id:'2', name:'bass', more:'false'}]; 

A to czynność:

 $scope.showdetails = function(fish_id){ 
     var found = $scope.fishes.filter({id : fish_id}); 
     return found; 
    }; 

Można również użyć wyrażenie:

 $scope.showdetails = function(fish_id){ 
     var found = $scope.fishes.filter(function(fish){ return fish.id === fish_id }); 
     return found; 
    }; 

Więcej o tej funkcji: LINK

4

zobaczyłem ten wątku, ale chciałem wyszukać identyfikatory, które nie pasowały do ​​mojego wyszukiwania. Kod do tego:

found = $filter('filter')($scope.fish, {id: '!fish_id'}, false); 
+0

To działało dla mnie. Prosta, łatwa, łatwa do przetestowania. Dzięki! –

Powiązane problemy