【问题标题】:Angular Reactive Forms - Filtering list with both text search and toggleAngular Reactive Forms - 带有文本搜索和切换的过滤列表
【发布时间】:2021-02-11 20:43:58
【问题描述】:

我有以下设置。搜索输入框效果很好。我现在已经添加了切换开关,我正在尝试了解如何使两者一起工作。

我已经为搜索词创建了一个 BehaviourSubject 和 Observable 组合,然后我正在观察 observable 以触发对象的过滤。

searchString = new BehaviorSubject("");
searchString$ = this.searchString.asObservable();   


this.myForm.controls.searchString.valueChanges.pipe(
  debounceTime(400),
  distinctUntilChanged(),
  tap((val) => this.searchString.next(val))
).subscribe()


this.searchString$.subscribe((searchTerm) => {
  console.log(this.userNames);
  if (this.userNames !== undefined) {
    this.filteredUserNames = this.userNames.filter(
      (userName) =>
        userName.searchTerms
          .toLowerCase()
          .indexOf(searchTerm.toLowerCase()) !== -1
    );
  };

这很好用。现在,我使用 formcontrolname 和 Valuechanges observable 设置了切换

this.myForm.controls.isActive.valueChanges.pipe(
  tap( val => this.userIsActive = val)
).subscribe()

这会切换 userIsActive。在filteredUserNames 我有一个属性isActive: boolean

同时按 searchTerm 和 isActive 状态过滤过滤后的UserNames 对象的最佳方法是什么?

编辑: 用户对象如下所示

{id: 52, firstName: "Administrator", lastName: "Account", employeeId: null, jobTitle: "Learning Administrator", isActive: false …}

filteredUserNames 列表用作模板中的 *ngFor。

<div (click)="selectUser(userName)" 
    *ngFor="let userName of filteredUserNames">
     {{userName.title}}
     etc...
</div

我需要同时使用过滤器 isActive 和 SearchTerm 来过滤列表。因此,如果将非活动切换为 false,则搜索框将仅搜索非活动列表,如果将其切换为 true,则搜索框将搜索整个原始列表。

【问题讨论】:

    标签: angular rxjs angular-reactive-forms


    【解决方案1】:

    也许你可以简化一下:

    const searchTerm = val.searchString.toLowerCase();
    
    const list = val.isActive ? this.userNames : this.userNames.filter(user => 
         user.isDeleted === false
    );
    
    this.filteredUserNames = list.filter((userName) => 
        userName.searchTerms.toLowerCase().includes(searchTerm)
    );
    

    【讨论】:

      【解决方案2】:

      在@Dima S 的回答的帮助下,我使用了完整的表单组值更改,然后根据列表是活动还是非活动创建了替代搜索。

      this.myForm.valueChanges.pipe(
        debounceTime(400),
        distinctUntilChanged(),
        tap( val => 
          {
            if (val.isActive == false) {
              let searchTerm = val.searchString;
              let isInactiveList = this.userNames.filter(user => user.isDeleted == false)
              this.filteredUserNames = isInactiveList.filter((userName) =>
              userName.searchTerms
                .toLowerCase()
                .indexOf(searchTerm.toLowerCase()) !== -1)
            } 
            else if (val.isActive == true) {
              let searchTerm = val.searchString;
              this.filteredUserNames = this.userNames.filter((userName) =>
              userName.searchTerms
                .toLowerCase()
                .indexOf(searchTerm.toLowerCase()) !== -1);
            }
          })
      ).subscribe()
      

      【讨论】:

        【解决方案3】:

        假设您有一个端点,FormGroup 将返回其完整值

        destroy$ = new Subject<any>();
        
        ngOnDestroy() {
            this.destroy$.next();
            this.destroy$.complete();
        }
        
        ngOnInit() {
            this.myForm.valueChanges
                .pipe(
                    // To clear valueChanges
                    takeUntil(this.destroy$),
                    debounceTime(400),
                    distinctUntilChanged(),
                    // This will take a val and switch to an endpoint of a choice
                    switchMap((val) => this.onSearch(val))
                ).subscribe(res => { });
        }
        
        private onSearch() {
            return {{ endPoint }}
        };
        

        如果是本地搜索,则将 switchMap 返回到 tap 并使用表单值的对象进行一些本地过滤

        【讨论】:

        • 我正在尝试理解 ngOnDestroy 以及为什么这里需要它。
        • @Bwizard 在这种特殊情况下与本地主题无关。但无论如何,这是一个好习惯。 distinctUntilChanged() 在此示例中也没有做任何事情,因为对于完整组,比较总是会失败。
        • 嗯,不是。你看,组件在被销毁时有一个状态,但 valueChanges 返回 Subject 而不是t. Thats 只是一个小的性能建议。也有例外,例如 activatedRoutehttp 在返回值时自动完成自身。随意不包括破坏部分。顺便说一句,它对你有用吗?
        • 好吧,我还在想这个。当切换或输入字段更改时,将触发对完整组的原始订阅。如何仅在输入框更改而不是切换切换时应用 debounceTime 和 distinctUntil Changed?
        • 也许我不需要关心这个,因为它与切换无关。 switchMap 文档说它切换到另一个 observable。我不确定我是否看到了另一个 observable。
        猜你喜欢
        • 2017-09-30
        • 1970-01-01
        • 2021-08-14
        • 2015-01-29
        • 2017-04-02
        • 2016-01-04
        • 2019-12-18
        • 2020-07-24
        • 1970-01-01
        相关资源
        最近更新 更多