Reputation: 61
I often use components to display cell data in an Angular Material Table, including dynamic components created with ngComponentOutlet. When filtering those tables, I can't seem to properly filter injection based dynamic components. Regular, fixed components filter correctly and input based dynamic components filter correctly, also. To demonstrate, the image below shows an unfiltered table.
This second image shows the result of filtering the table with a lowercase 'v' with the table's dataSource.filterPredicate. The fixed component and the input based dynamic component filter correctly, while the injection based dynamic component does not.
Here is the StackBlitz project for anyone who wishes to help.
Upvotes: 1
Views: 99
Reputation: 57986
The filterPredicate should return false, when no search is done, because ''
empty string, will return true with includes
. Also we need to convert to lowercase for case insensitive comparison:
filterDataSource(data: any, filter: string): boolean {
console.log(filter);
const filters = JSON.parse(filter);
let retVal = true;
for (const [key, value] of Object.entries(filters)) {
const dataVal = data[key];
if (!dataVal) {
continue;
}
retVal = value
? dataVal
.toString()
.toLowerCase()
.includes((value as any)!.toLowerCase())
: false;
if (!retVal) {
break;
}
}
return retVal;
}
The cell name has to match with the property name of the data being rendered:
export class Column {
public headerName: string = '';
public cellName: string = '';
public injectComponent: string = '';
public inputComponent: string = '';
}
export const columnArr: Column[] = [
{
headerName: 'Fixed Component',
cellName: 'fixedComponent',
injectComponent: '',
inputComponent: '',
},
{
headerName: 'Dynamic Inject Component',
cellName: 'dynamicComponent', // <- changed here!
injectComponent: 'DemoColumnComponent',
inputComponent: '',
},
{
headerName: 'Dynamic Input Component',
cellName: 'dynamicComponent2', // <- changed here!
injectComponent: '',
inputComponent: 'DemoColumnComponent',
},
];
Notice how a new name dynamicComponent2
is added, it's because there cannot be duplicate columns with the same cell name:
export class DemoData {
fixedComponent: string = '';
dynamicComponent: string = '';
dynamicComponent2: string = '';
}
export const demoDataArr: DemoData[] = [
{
fixedComponent: '1234 First Street',
dynamicComponent: '1234 First Street',
dynamicComponent2: '1234 First Street',
},
{
fixedComponent: '1234 Second Street',
dynamicComponent: '1234 Second Street',
dynamicComponent2: '1234 Second Street',
},
{
fixedComponent: '1234 Third Street',
dynamicComponent: '1234 Third Street',
dynamicComponent2: '1234 Third Street',
},
{
fixedComponent: '1234 First Avenue',
dynamicComponent: '1234 First Avenue',
dynamicComponent2: '1234 First Avenue',
},
{
fixedComponent: '1234 Second Avenue',
dynamicComponent: '1234 Second Avenue',
dynamicComponent2: '1234 Second Avenue',
},
{
fixedComponent: '1234 Third Avenue',
dynamicComponent: '1234 Third Avenue',
dynamicComponent2: '1234 Third Avenue',
},
];
Upvotes: 0