简体   繁体   中英

Angular 4 Typescript multi pipe value

I've created a pipe 'filterBy' and I want to use it on my application. Almost everything works good, but I want to use this pipe for 5 properties, and I have no abilities to understand how to do it. I will try to explain you what I mean.

My pipe

import { Injectable, Pipe, PipeTransform } from '@angular/core';

@Pipe({
  name: 'filterBy',
  pure: false
})

@Injectable()
export class FilterBy implements PipeTransform {
  transform( array: Array<any>, filterField: string, filterValue: string, filterField2: string, filterValue2: any): Array<any> {
    if (!array) return [];
    return array.filter(item => item[filterField] === filterValue);
  }
}

products.component.html

<div class="col-sm-1 lessmargins" *ngFor="let product of products | filterBy: 'condition': 'new'"

It works good, but my product have a properties like condition, prices etc. For example I would like to show products with 'condition' : 'new' and 'condition' : 'used' and I don't know how to do it. I tried to run it like that: products.component.html

*ngFor="let product of products | filterBy: {'condition': 'new'} && {'condition' : 'used'}"

But it doesn't work :( is that something wrong with my pipe? Could someone explain me?

Add all the properties you want to filter on to an array and pass that array to the pipe. You can then just loop through the array of properties and check that all match. Below is an example:

A class for your filters:

export class Filter {
    public name: string;
    public value: any;
}

And then just create new filters and push to an array of filters. Use the array in your pipe instead:

<div class="col-sm-12" *ngFor="let product of products | filterBy: filters">
</div>

And then loop the array of filters in your pipe:

import { Injectable, Pipe, PipeTransform } from '@angular/core';
import { Filter } from './filter';

@Pipe({
  name: 'filterBy',
  pure: false,
})
export class FilterBy implements PipeTransform {
  transform( array: Array<any>, filters: Array<Filter>): Array<any> {
    if (!array) return [];
    if (!filters) return array;

    return array.filter(item => matchAll(item, filters));
  }
}

function matchAll(item: any, filters: Array<Filter>): boolean {
  let valid = true;
  for (const filter of filters) {
    if (!hasKey(item, filter.name)
      || item[filter.name] !== filter.value) {
      valid = false;
      break;
    }
  }

  return valid;
}

function hasKey(item: any, keyName: string): boolean {
  return Object.keys(item).indexOf(keyName) !== -1;
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM