Angular ng-select несколько значений в директиве * ngFor - PullRequest
0 голосов
/ 15 апреля 2020

У меня есть несколько раскрывающихся списков ng-select (пользовательский поиск на стороне сервера), созданных директивой * ngFor, с возможностью выбора нескольких элементов из каждого раскрывающегося списка.

Проблема, однако, в том, что каждый раз, когда я что-то ищу и выбираю значение, это значение будет выбираться и для всех других выпадающих списков ng-select. Также мне нужно сделать значения параметров, возвращаемые API на основе на основе переменной итерации

Stackblitz: https://stackblitz.com/edit/angular-vml2j8

фильтр .component. html:

<div *ngFor="let filter of filters;index as i">
    <ng-select [items]="filterValues | async"
             [typeahead]="filterValuesInput"
             [multiple]="true"
             (open)="ngSelectOpened(filter.name)"
             [loading]="filterValuesLoading"
             bindLabel="name"
             [(ngModel)]="selectedFilterValues[pref.name]">
    </ng-select>
</div>

filter.component.ts

filterValues: Observable<FilterValues[]>;
filterValuesLoading = false;
filterValuesInput = new Subject<string>();
selectedFilterValues];

ngSelectOpened(filterName) {
    this.filterValues = concat(
      of([]), // default items
      this.filterValuesInput.pipe(
        distinctUntilChanged(),
        tap(() => this.filterValuesLoading = true),
        switchMap(term => this.dataService.getData(term).pipe(
          catchError(() => of([])), // empty list on error
          tap(() => this.filterValuesLoading = false)
        ))
      )
    );
}

Как настроить работу ng-select на основе текущая итерация?

1 Ответ

0 голосов
/ 15 апреля 2020

Может быть, не самый элегантный, но, кажется, работает. Ранее ваши selectedPersons были разделены между всеми списками.

Изменено Html:

<div *ngFor="let pref of filters">
  <ng-select [items]="people$ | async"
            bindLabel="name"
            [addTag]="true"
            [multiple]="true"
            [hideSelected]="true"
            [trackByFn]="trackByFn"
            [minTermLength]="2"
            (open)="ngSelectOpened(pref.name)"
            [loading]="peopleLoading"
            typeToSearchText="Please enter 2 or more characters"
            [typeahead]="peopleInput$"
            [(ngModel)]="pref.selected">
  </ng-select>
  <br>
</div>

Изменено ts (2 списка):

import { Component } from '@angular/core';
import { DataService, Person } from '../data.service';
import { concat, Observable, of, Subject } from 'rxjs';
import { catchError, debounceTime, distinctUntilChanged, switchMap, tap } from 'rxjs/operators';
@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: [ './app.component.css' ]
})
export class AppComponent  {
  people$: Observable<Person[]>;
    peopleLoading = false;
    peopleInput$ = new Subject<string>();
    selectedPersons: Person[] = <any>[{ name: 'Karyn Wright' }, { name: 'Other' }];
    filters = [
        {id: 1, name: "Filter1", selected: [...this.selectedPersons]},
        {id: 2, name: "Filter2", selected: [...this.selectedPersons]}/*,
        {id: 3, name: "Filter3"}*/
    ]

    constructor(private dataService: DataService) {
    }


    ngSelectOpened(filterName) {
      this.loadPeople(filterName);
    }

    private loadPeople(filterName) {
        this.people$ = concat(
            of([]), // default items
            this.peopleInput$.pipe(
                distinctUntilChanged(),
                tap(() => this.peopleLoading = true),
                switchMap(term => this.dataService.getPeople(term).pipe(
                    catchError(() => of([])), // empty list on error
                    tap(() => this.peopleLoading = false)
                ))
            )
        );
    }
}

...