Reputation: 815
I have an angular 6 application which has a Mat Table. Data for the table is populated like below. Sorting works for the fields position
and name
, but not weight
and symbol
which are part of the detail
object. I have also tried naming the columns like detail.weight
in displayedColumns
and matColumnDef
but with no luck. Please advise what am I doing wrong ?
const ELEMENT_DATA: PeriodicElement[] = [
{position: 1, name: 'Hydrogen', detail: {weight: 4.0026, symbol: 'He'}},
{position: 2, name: 'Helium', detail: {weight: 4.0026, symbol: 'He'}},
]
displayedColumns: string[] = ['position', 'name', 'weight', 'symbol'];
Template
<ng-container matColumnDef="weight">
<th mat-header-cell *matHeaderCellDef mat-sort-header> Weight </th>
<td mat-cell *matCellDef="let element"> {{element.detail.weight}} </td>
</ng-container>
Here is the stackblitz url for the issue
https://stackblitz.com/edit/angular-kumdeq
Upvotes: 3
Views: 5523
Reputation: 1854
Yes the above code will work but we should use it where ever, we are updating the datasource (not in ngOnInit for dynamic data)
updateMatTable(customerData: Customer[]) {
this.dataSource = new MatTableDataSource<Customer>(customerData);
this.dataSource.sortingDataAccessor = (item, property) => {
switch (property) {
case 'email': return item.address.email;
default: return item[property];
}
}
this.dataSource.paginator = this.paginator;
this.dataSource.sort = this.sort;
}
and call "updateMatTable" method whenever data is refreshed.
Upvotes: 0
Reputation: 2681
Use sortingDataAccessor, which
Allows for sort customization by overriding sortingDataAccessor, which defines how data properties are accessed.
Add this code snippet inside ngOnInit:
this.dataSource.sortingDataAccessor = (item, property) => {
switch (property) {
case 'weight': return item.detail.weight;
case 'symbol': return item.detail.symbol;
default: return item[property];
}
Link: https://stackblitz.com/edit/angular-kumdeq-z4bags
Upvotes: 10