2012-07-30 4 views
119

ngRepeatフィルタリングされた結果の参照を取得する方法:AngularJS - 私はそうのようなフィルタでNGリピートディレクティブを使用しています

ng-repeat="item in items | orderBy:'order_prop' | filter:query | limitTo:4" 

を、私は、レンダリング結果を微見ることができます。今私はコントローラでその結果にいくつかのロジックを実行したい。問題は、どのように結果アイテムの参照を取得できますか?

更新:


だけ明確にする:私は自動補完を作成しようとしています、私はこの入力を持っている:

<input id="queryInput" ng-model="query" type="text" size="30" placeholder="Enter query"> 

した後、濾過結果:

<ul> 
    <li ng-repeat="item in items | orderBy:'order_prop' | filter:query | limitTo:4">{{item.name}}</li> 
</ul> 

今すぐ結果をナビゲートしてアイテムの1つを選択したい。

答えて

245

更新日:これまでの方法よりも簡単な方法です。

<input ng-model="query"> 
<div ng-repeat="item in (filteredItems = (items | orderBy:'order_prop' | filter:query | limitTo:4))"> 
    {{item}} 
</div> 

$scope.filteredItemsにアクセスできます。

+0

おかげで、私の更新を参照してください。あなたはそれをどのように実装しますか?私はinitの項目リスト全体を取得します。 –

+0

Ok、それを更新しました。 –

+0

超クール、それに感謝します。私はそれがNGの機能に組み込まれていたほうがいいです –

29

Andy Joslinのソリューションのフィルター版はこちらです。

更新:改ざんの変更。バージョン1.3.0-beta.19(this commit)のフィルタはコンテキストを持たず、thisはグローバルスコープにバインドされます。コンテキストを引数として渡すか、ngRepeat、1.3.0-beta.17 +の新しいエイリアシング構文を使用できます。ビューあなたが$scope.filteredItemsにアクセスすることができます

<!-- pre 1.3.0-beta.19 --> 
<input ng-model="query"> 
<div ng-repeat="item in items | orderBy:'order_prop' | filter:query | limitTo:4 | as:'filteredItems'"> 
{{item}} 
</div> 

<!-- 1.3.0-beta.19+ --> 
<input ng-model="query"> 
<div ng-repeat="item in items | orderBy:'order_prop' | filter:query | limitTo:4 | as:this:'filteredItems'"> 
{{item}} 
</div> 

<!-- 1.3.0-beta.17+ ngRepeat aliasing --> 
<input ng-model="query"> 
<div ng-repeat="item in items | orderBy:'order_prop' | filter:query | limitTo:4 as filteredItems"> 
{{item}} 
</div> 

で次に

// pre 1.3.0-beta.19 
yourModule.filter("as", function($parse) { 
    return function(value, path) { 
    return $parse(path).assign(this, value); 
    }; 
}); 

// 1.3.0-beta.19+ 
yourModule.filter("as", function($parse) { 
    return function(value, context, path) { 
    return $parse(path).assign(context, value); 
    }; 
}); 

+0

ありがとう!フィルタコードの仕組みを説明できますか?私は$ parseに精通していません。角度のあるドキュメントは、フィルタがどのように正確に動作するかを解読するのに役立ちませんでした。 – Magne

+2

@Magne問題ありません!しかし、それは道路にいくつかの痛みや苦しみを救うかもしれないとして、更新をチェックしてください。つまり、あなたの質問に答えるために、 '$ parse'はAngularの[式コンパイラ](https://docs.angularjs.org/api/ng/service/$parse)です。たとえば、文字列 ' some.object.property 'を呼び出して、指定されたコンテキストの前記パスで値を設定または取得できるようにする関数を返します。私はそれをここでは$範囲のフィルター結果を設定するために使用しています。これがあなたの質問に答えることを願っています – kevinjamesus86

10

私はアンディの解決策のやや優れたバージョンを思いついた。彼の解では、ng-repeatは代入を含む式を監視します。各ダイジェストループはその式を評価し、その結果をスコープ変数に代入します。

このソリューションの問題点は、子スコープの場合に割り当て問題が発生する可能性があることです。これは、dot in ng-modelが必要な同じ理由です。

私がこのソリューションについて気に入らないもう1つの点は、フィルタされた配列の定義がビューマークアップのどこかに埋められていることです。あなたのビューやコントローラ内の複数の場所で使用されている場合、混乱する可能性があります。

簡単な解決策は、単に割り当てを作る機能であなたのコントローラで時計を配置することです:パフォーマンスはアンディのソリューションと比較する必要がありますので

$scope.$watch(function() { 
    $scope.filteredItems = $scope.$eval("items | orderBy:'order_prop' | filter:query | limitTo:4"); 
}); 

この関数は、各ダイジェストサイクル中に評価されます。また、関数内に任意の数の代入を追加して、ビューに散らばっているのではなく、すべてを1つの場所に保持することもできます。ビューで

、あなただけの直接フィルタリングされたリストを使用します。

<ul> 
    <li ng-repeat="item in filteredItems">{{item.name}}</li> 
</ul> 

Here's a fiddle where this is shown in a more complicated scenario.

+0

スーパークリーンで、構造を汚染しない、素晴らしい! – kuzyn

+0

この解決法は私にとっては完璧です。私は反復繰り返しの代わりにイオンのコレクションリピートを使用していた理由は、受け入れられた答えは私のためにdidntの仕事を – Lakshay

+0

非常にありがとう...... これはちょうど私を救った。 –

21

はこのような何かを試してみて、NG-繰り返しの問題点は、そのための子スコープを作成することですあなたがアクセスすることはできません

filteritems

コントローラから

<li ng-repeat="doc in $parent.filteritems = (docs | filter:searchitems)" ></li> 
14

更新:

後も1.3.0。コントローラーまたは親のスコープに入れたい場合は、としてという構文を使用することはできません。 たとえば、私は次のコードを持っている場合:

<div>{{labelResults}}</div> 
<li ng-repeat="label in (labels | filter:query | as labelResults)"> 
</div> 

上記の意志ない作品。その周りに行くための 方法はように$親を使用している:

<li ng-repeat="label in ($parent.labelResults = (labels | filter:query))"> 
+0

limitToフィルタがある場合は注意してください。 $ parent.labelResultsに反映されません – Zack

+0

私が 'console.log labelResults'を使うと、私はいつも後でデータを1つ取得します。フィルタが変更されただけではなく、以前の変更の結果でもあります。この問題はありませんでしたか? – Anna

関連する問題