AngularJs UIの先行入力機能はシンプルで強力に見えますが、先頭の文字でマッチングを実行する方法を理解しようとしています。たとえば、入力ボックスに「A」と入力すると、名前に「A」が含まれるすべての州ではなく、「A」で始まるすべての州が表示されます。数日探していました。これについて、Angularには「コンパレータ」を持つカスタムフィルタの概念があります。これに関するドキュメントには、コンパレータを実装するための正確な構文を示さない簡単な例があります。
Htmlは次のようになります。
<div>Selected: <span>{{selected}}</span></div>
<div><input type="text" ng-model="selected" typeahead="name for name in states | filter:selected"></div>
基本的なJavaScriptはこのようになります
angular.module('firstChar', ['ui.bootstrap']);
function TypeaheadCtrl($scope) {
$scope.selected = undefined;
$scope.states = ['Alabama', 'Alaska', 'Arizona', 'Arkansas', 'California', 'Colorado', 'Connecticut', 'Delaware', 'Florida', 'Georgia', 'Hawaii', 'Idaho', 'Illinois', 'Indiana', 'Iowa', 'Kansas', 'Kentucky', 'Louisiana', 'Maine', 'Maryland', 'Massachusetts', 'Michigan', 'Minnesota', 'Mississippi', 'Missouri', 'Montana', 'Nebraska', 'Nevada', 'New Hampshire', 'New Jersey', 'New Mexico', 'New York', 'North Dakota', 'North Carolina', 'Ohio', 'Oklahoma', 'Oregon', 'Pennsylvania', 'Rhode Island', 'South Carolina', 'South Dakota', 'Tennessee', 'Texas', 'Utah', 'Vermont', 'Virginia', 'Washington', 'West Virginia', 'Wisconsin', 'Wyoming'];
}
ここにプランカーがあります http://plnkr.co/edit/LT6pAnS8asnpFEd5e6Ri
つまり、簡単に言えば、AngularUIの先行入力を先頭の文字のみに一致させることです。
これに関するどんな助けやアイデアでも大いに感謝されます。
結局のところ、あなたの質問はtypeahead
ディレクティブに固有のものではありませんが、AngularJSフィルターの動作とは関係があります。
実用的なソリューションを提示する前に、typeahead
ディレクティブがAngularJSインフラストラクチャ($ http、promises)と式言語を頻繁に使用することに注意してください。したがって、states | filter:selected
は、AngularJSの式にすぎないことを理解することが重要です。
上記の式を見て、一致する項目のリストを返すために配列をフィルタリングする方法を見つける必要があります。 typeaheadディレクティブの唯一の特別な点は、ユーザーが入力ボックスに入力した値を表す$viewValue
変数があることです。したがって、基本的には、states
配列をフィルタリングして、$viewValue
で始まるアイテムを返す必要があります。
これを行う方法はたくさんありますが、フィルターのコンパレーターについて述べてきたので(それらはAngularJSの1.1.xバージョンでのみ導入されたことに注意してください)、特定のアイテムが必要かどうかを決定するコンパレーター関数を定義する必要があります。結果のリストで返されるかどうか。このような関数は次のようになります。
$scope.startsWith = function(state, viewValue) {
return state.substr(0, viewValue.length).toLowerCase() == viewValue.toLowerCase();
}
使い方を定義するのはとても簡単です:
typeahead="name for name in states | filter:$viewValue:startsWith"
これが作業中のプランクです: http://plnkr.co/edit/WWWEwU4oPxvbN84fmAl0?p=preview
タイプヘッドのオートコンプリートボックスの先頭の文字に対してマッチングを実行するためのカスタムフィルター。
(function() {
// Create global filters using angular.filter() only. Never use local filters inside
// controllers/services. This enhances testing and reusability.
function xpTypeaheadFilter() {
return function(items, props) {
var out = [];
if (angular.isArray(items)) {
items.forEach(function(item) {
var text = props.toLowerCase();
var itemLoverCase =item.toLowerCase();
var substr = itemLoverCase.substr(0, text.length);
if (substr === text ) {
out.Push(item);
}
});
} else {
// Let the output be the input untouched
out = items;
}
console.log("out lem", out.length);
return out;
};
}
// Pass functions into module methods rather than assigning a callback.
// This helps aid with readability and helps reduced the amount of code "wrapped"
// inside Angular.
angular.module('common')
.filter('xpTypeaheadFilter', xpTypeaheadFilter);
})();
<input type="text" ng-model="vesselName" placeholder="Vessel Name" typeahead="vesselName for vesselName in vesselNames | xpTypeaheadFilter:$viewValue | limitTo:8" class="form-control form-textbox" >
回答済みとマークされた投稿を編集しました。リストにIDとタイトルの両方がある場合に機能します。
<input type="text" ng-model="ledgerstatementModel.Supplier" typeahead="supplier as supplier.Name for supplier in supplierList | filter:{Name:$viewValue}:startsWith" class="form-control">
そしてjsで:
$scope.startsWith = function (supplier, viewValue) {
return supplier.substr(0, viewValue.length).toLowerCase() == viewValue.toLowerCase();
}