I am trying to filter Array data based on multiple columns using only one Pipe. Right now, It filters first column value. Please check my below code and help me to sort this out.
My Code:
@Pipe({ name: "dataFilter", pure: false })
export class DataFilterPipe implements PipeTransform {
transform(value: Array<any>, filter: any[]) {
if (!filter) {
return value;
} else if (value) {
return value.filter(item => {
for (var i = 0; i < filter.length; i++) {
if (filter[i][1] == undefined) {
return true;
} else if ((typeof item[filter[i][0]] === 'string' || item[filter[i][0]] instanceof String) &&
(item[filter[i][0]].toLowerCase().indexOf(filter[i][1]) !== -1)) {
return true;
}
return false;
}
});
}
}
}
I am passing data like dataFilter : [['column1',value1],['column2',value2],['column3',value3]].
Here is a solution using the object passed as multiple columns filter. I found it more convenient then passing a 2D array:
@Pipe({ name: 'filter' }) export class FilterPipe implements PipeTransform { transform(items: Array<any>, filter: {[key: string]: any }): Array<any> { return items.filter(item => { const notMatchingField = Object.keys(filter) .find(key => item[key] !== filter[key]); return !notMatchingField; // true if matches all fields }); } } Having an array of objects with multiple columns:
this.people = [ {name: 'John', age: 27, sex: 'male'}, {name: 'Lara', age: 21, sex: 'female'}, {name: 'Rick', age: 29, sex: 'male'}, {name: 'Eva', age: 27, sex: 'female'}, {name: 'Mike', age: 27, sex: 'male'} ]; And a filter:
this.peopleFilter = {age: 27, sex: 'male'}; Use it like:
<div *ngFor="let person of people | filter: peopleFilter;"></div> As a result, two people are matching our criteria: John and Mike.
Here is the working plunker: Multiple columns filter pipe demo.
Here is what I did with Angular 8:
Goal: Search on multiple properties say "Property1" and "Property2" from a list of items for a given keyword:
app.module.ts:
......
import { MyFilterPipe } from './shared/pipes/my-filter.pipe';
@NgModule({
declarations: [
...
MyFilterPipe
],
imports: [
...
],
providers: [],
bootstrap: [AppComponent]
})
export class AppModule { }
Pipe: content-filter.pipe.ts
import { Pipe, PipeTransform } from '@angular/core';
@Pipe({
name: 'myFilter'
})
export class MyFilterPipe implements PipeTransform {
transform(items: any[], keyword: any, properties: string[]): any[] {
if (!items) return [];
if (!keyword) return items;
debugger;
return items.filter(item => {
var itemFound: Boolean;
for (let i = 0; i < properties.length; i++) {
if (item[properties[i]].toLowerCase().indexOf(keyword.toLowerCase()) !== -1) {
itemFound = true;
break;
}
}
return itemFound;
});
}
}
component:
<input type="search" class="form-control filter-list-input" placeholder="Filter"
aria-label="Filter" name="search" [(ngModel)]="searchText" >
<div *ngFor="let itemof myItems | myFilter:searchText:['Property1', 'Property2']; let i = index">...
</div>
component.ts:
export class MyListComponent implements OnInit {
...
searchText: string;
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With