4

我使用 Angular 6,我想过滤异步管道的结果,然后在 UI 中呈现它们。

这是我现在的代码

this.results = this.form.get('name').valueChanges.pipe(           
  filter(formdata => formdata.name.length > 0), 
  switchMap( formdata => this.service.getNames(formdata.name)) 
);

和模板

  <div *ngIf='results | async ; let items'>
       <div *ngFor='let item of items'>{{item.id}} {{item.name}} </div>               
  </div> 

从管道中,我得到了一些 ID 和名称。我已经有一个 id 数组。我想过滤管道的 id,而不是渲染已经在数组中的那些。

所以,这就是我尝试做的。

array = [{id:1,name:'one'},{id:2,name:'two'}];//I already have this

新版本的管道过滤器

this.results = this.form.get('name').valueChanges.pipe(           
  filter(formdata => formdata.name.length > 0), 
  switchMap( formdata => this.service.getNames(formdata.name)) ,
  filter(checkIfResultIdInArray())//pseudocode
);

假设那checkIfResultIdInArray是我创建的函数。过滤并返回所有不在array. 所以最终出现在模板中的 ids/names 不是{id:1,name:'one'},{id:2,name:'two'}.

或者也许我可以以某种方式过滤模板?

4

3 回答 3

7

@Davy's answer is what I would do myself. However another option is to use a pipe. This is the way to go if you would like to reuse this functionality.

@Pipe({name:'filterOnId'})
export class FilterOnIdPipe implements PipeTransform {
    transform(list : MyObject[], acceptedIds : number[]){
        return list.filter(item => acceptedIds.indexOf(item.id) > -1);
    }
}

and in the template

<div *ngFor='let item of results | async | filterOnId : acceptedIds'>
    {{item.id}} {{item.name}} 
</div>

Note the following:

You use your custom pipe the same way you use built-in pipes. You must include your pipe in the declarations array of the AppModule If you choose to inject your pipe into a class, you must provide it in the providers array of your NgModule.

于 2018-11-07T15:55:03.587 回答
3

正如评论中所建议的,您可以用AsyncPipe常规数组替换,或更改发出值的值(@Davy 的解决方案很好)。

然而,有一个基于模板的解决方案。我把它放在这里是为了那些不想将组件的逻辑与视图显示合并的人。

零件

result$ = of([1,2,3,4,5,6,7,8]); // for the sake of example

isAcceptedThing(thing){
  return thing%2 != 0 // accept only odd numbers
}

模板

<ul >
  <ng-container *ngFor="let thing of result$ | async">
    <li *ngIf="isAcceptedThing(thing)">
      filtered thing = {{ thing }} 
    </li>
  </ng-container>
</ul>

输出

  • 过滤的东西 = 1
  • 过滤的东西= 3
  • 过滤的东西= 5
  • 过滤的东西= 7
于 2018-11-07T10:16:44.750 回答
1

我想这就是你想要做的:

this.results = this.form.get('name').valueChanges.pipe(           
  filter(formdata => formdata.name.length > 0), 
  switchMap( formdata => this.service.getNames(formdata.name)) ,
  map(names => names.filter(n => checkIfResultIdInArray(n)))
);

通常,在这样的设置中,我还会添加一个 debounceTime 运算符来防止过多的请求。

于 2018-11-07T11:34:27.467 回答