Использование углового материала mat-autocomplete без ReactiveForm

Я пытаюсь использовать <mat-autocomplete> из Angular Material (не AngularJS) без использования реактивной формы. Но все их примеры используют реактивные формы...

Что я пытаюсь сделать:
1. когда что-то набрано в mat-input, сделать вызов Ajax, чтобы получить список пользователей
2. Отобразите список пользователей в автозаполнении (отобразите имя пользователя), но сохраните пользователя в качестве модели
3. Когда модель изменится, вызовите функцию на мой выбор

Пока я делаю эти сумасшедшие вещи (я говорю сумасшедшие, потому что это кажется многим).

<mat-form-field fxLayout>
  <input type="text"
             matInput fxFlex="100"
             [(ngModel)]="listFilterValue"
             (keyup)="memberInputChanged(input.value)"
             (change)="memberChanged()"
             *ngIf="isAutocompleteNeeded()"
             #input
             [matAutocomplete]="auto">
</mat-form-field>

<mat-autocomplete #auto="matAutocomplete" [displayWith]="getMemberAsStr">
       <mat-option *ngFor="let member of members | async" [value]="member">
          {{ getMemberAsStr(member) }}
       </mat-option>
</mat-autocomplete>

На данный момент есть только console.log в моем JS, чтобы увидеть, что называется, с какой ценностью, поэтому я не разделяю это здесь. Я использую правильные атрибуты, правильную логику?

(members свойство в моем компоненте - Rxjs BehaviourSubject)

То, что я делаю сейчас, не работает, потому что listFilterValue никогда не настроен ни на что.

Спасибо за вашу помощь

1 ответ

Вам следует избегать вызова методов в шаблоне, это может привести к сбою вашего браузера, так как они вызываются при каждом обнаружении изменений, см.: * ng Для запуска бесконечного цикла в angular2 Технически это не бесконечный цикл, но вы понимаете, в чем суть:)

Поскольку отсутствие элемента управления формой с автозаполнением не сильно отличается, вы просто заменяете элемент управления формой на переменную, вы можете использовать шаблонно-управляемую форму, если хотите, или вообще не использовать форму. Вот с формой, управляемой шаблоном, хотя:

Демонстрационная версия JSON, используемая в этом примере, выглядит следующим образом:

"value": [
  {
    "id": 409,
    "joke": "some joke here",
    "categories": []
  }
]
<form #f="ngForm">
  <mat-form-field>
    <input matInput [matAutocomplete]="auto" 
           name="joke" #jokeField="ngModel" 
           [(ngModel)]="currentJoke" (ngModelChange)="doFilter()">
  </mat-form-field>

  <mat-autocomplete #auto="matAutocomplete">
    <mat-option *ngFor="let joke of jokes | async" [value]="joke.joke">
        {{joke.joke}}
    </mat-option>
  </mat-autocomplete>
</form>

И ваш TS может выглядеть так:

doFilter() {
  this.jokes = this.service.getData()
    .pipe(
      map(jokes => this.filter(jokes.value)),
  )
}

filter(values) {
  return values.filter(joke => 
    // used 'includes' here for demo, you'd want to probably use 'indexOf'
    joke.joke.toLowerCase().includes(this.currentJoke))
}

StackBlitz Demo

Другие вопросы по тегам