Подтвердить что ты не робот

AngularJs UI typeahead соответствует ведущим персонажам

Функциональность typeahead в пользовательском интерфейсе AngularJs кажется простой и мощной, однако я пытался выяснить, как добиться соответствия для ведущих персонажей. Например, если я ввожу "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 соответствовать только ведущим символам.

Любая помощь или идеи по этому поводу были бы чрезвычайно оценены.

4b9b3361

Ответ 1

В конце дня ваш вопрос не очень специфичен для директивы typeahead, но он больше связан с тем, как работают фильтры AngularJS.

Перед представлением рабочего решения обратите внимание, что директива typeahead использует интенсивную инфраструктуру AngularJS ($ http, promises) и язык выражения. Поэтому важно понять, что states | filter:selected не более чем выражение AngularJS.

Взглянув на вышеприведенное выражение, нам нужно найти способ фильтрации массива для возврата списка совпадающих элементов. Единственная особенность директивы typeahead заключается в том, что существует переменная $viewValue, представляющая значение, введенное пользователем в поле ввода. Поэтому нам просто нужно отфильтровать массив states для возврата элементов, начинающихся с $viewValue.

Существует много способов сделать это, но поскольку вы упоминали о компараторе для фильтров (обратите внимание, что они были введены только в версии 1.1.x AngularJS), вам нужно будет определить функцию компаратора, которая должна решить, если данный элемент должен быть возвращен в списке результатов или нет. Такая функция может выглядеть следующим образом:

$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

Ответ 2

Пользовательский фильтр для получения соответствия, которое должно выполняться над ведущими символами в окне автозапуска типа headhead.

(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" >

Ответ 3

Я только что отредактировал пост, помеченный как ответ, и он работает, когда в списке есть 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();
    }