I was following a tutorial by Muhi Masri Load, Add, Update and Delete Table Rows using API Services (Totally recommended tutorial by the way) to make an Editable Dynamic Table.
Use a dataSource that I render every time I filter a date. But I wanted to add an Angular Material Paginator to it, only it doesn't work. I don't quite understand why, I did it as mentioned in the documentation, but still nothing.
The this.dataSource._filterData.length
returns me 1
// The columns
displayedColumns: string[] = ActivityColumns.map((col) => col.key);
columnsSchema: any = ActivityColumns;
// The date
dataSource = new MatTableDataSource<ApidatumDisplay>();
request: ApidatumDisplay[] = []
getDataIsSelected() {
let dailydata = {
startDate: this.selected.startDate.format("YYYY-MM-DD"),
endDate: this.selected.endDate.format("YYYY-MM-DD")
}
const validStartSelected = dailydata.startDate;
const validd = (validStartSelected === dayjs().format("YYYY-MM-DD")) ? this.editDateisNow = true : this.editDateisNow = false;
// Request get this.reportesService.getDailyTracking(dataDaily).pipe(takeUntil(this.unsubscribe$)).subscribe((res) => {
this.request = res.apidata;
this.dataSource.data = this.request;
console.log('length',this.dataSource._filterData.length); // returns 1
this.averageTotal = res.adding_total_activity
this.hourTimeTotal = this.convert(res.adding_total_hours);
this.expectedBudget = 192 * 22;
this.isReload = false;
});
}
HTML
<!--Table of content-->
<section >
<table mat-table [dataSource]="dataSource">
<ng-container [matColumnDef]="col.key" *ngFor="let col of columnsSchema">
<th mat-header-cell *matHeaderCellDef>
<div >
<div >
{{ col.label }}
</div>
</div>
</th>
<td mat-cell *matCellDef="let element">
<div [ngSwitch]="col.type" *ngIf="!element.isEdit">
<div *ngSwitchCase="'isEdit'">
<button mat-button (click)="element.isEdit=
!element.isEdit">
Editar
</button>
</div>
<span *ngSwitchCase="'text'">
{{ element[col.key] }}
</span>
<span *ngSwitchDefault>
{{ element[col.key] }}
</span>
<div *ngSwitchCase="'indicator_hour_daily'">
<img style="height: 12px;" src="https://ymlabqgbnnbvyybcyqjn.supabase.co/storage/v1/object/public/assets-ui/icons/status-{{element.indicator_hour_daily}}.svg" alt="status">
</div>
<div *ngSwitchCase="'indicator_activity_daily'">
<img style="height: 12px;" src="https://ymlabqgbnnbvyybcyqjn.supabase.co/storage/v1/object/public/assets-ui/icons/status-{{element.indicator_activity_daily}}.svg" alt="status">
</div>
</div>
<div [ngSwitch]="col.type" *ngIf="element.isEdit">
<div *ngSwitchCase="'isSelected'"></div>
<div *ngSwitchCase="'isEdit'">
<button mat-button (click)="editRow(element)">Hecho</button>
<button mat-button (click)="cancelEditActivity(element)">Cancelar</button>
</div>
<mat-form-field *ngSwitchCase="col.type ==='activity_daily' ?
col.type : col.type ==='text'">
<input matInput [type]="col.type" [(ngModel)]="element[col.key]" />
</mat-form-field>
<mat-form-field *ngSwitchCase="col.type ==='text' ? col.type :
''">
<input [type]="col.type" matInput [(ngModel)]="element[col.key]" disabled/>
</mat-form-field>
<mat-form-field *ngSwitchCase="'indicator_hour_daily'" ng-disabled="'isEdit'">
<img with="12" height="12" [src]="selectedLanguage">
<mat-select [(value)]="selectedLanguage">
<mat-select-trigger>
{{selectedLanguage}}
</mat-select-trigger>
<mat-option *ngFor="let category of categories" [value]="category.image">
<img with="12" height="12" [src]="category.image"> {{category.viewValue}}
</mat-option>
</mat-select>
</mat-form-field>
<mat-form-field *ngSwitchCase="'indicator_activity_daily'">
<mat-select [(value)]="selectedActivity">
<mat-select-trigger>
<img with="12" height="12" [src]="selectedActivity"> {{selectedActivity}}
</mat-select-trigger>
<mat-option *ngFor="let activity of categories" [value]="activity.image">
<img with="12" height="12" [src]="activity.image"> {{activity.viewValue}}
</mat-option>
</mat-select>
</mat-form-field>
</div>
</td>
</ng-container>
<tr mat-header-row *matHeaderRowDef="displayedColumns"></tr>
<tr mat-row *matRowDef="let row; columns: displayedColumns"></tr>
</table>
<mat-paginator #paginator [length]="dataSource.filteredData.length" [pageIndex]="0" [pageSize]="5" [pageSizeOptions]="[5, 10, 20]">
</mat-paginator>
</section>
</section>
</div>
CodePudding user response:
There's a lot missing in your example so I'm going to explain this end-to-end with a code example. You declare the MatPaginator in your component. Since you are doing a search, you'll want to bind to the length, page size, page index, and handle the (page) event in your mat-paginator tag. Your API results should return the data plus the length. If you're not doing server-side paging, you an disregard that and just set it to the array length of the return results. The "getPagedData" function is where you'll setup your API call and handle the results
It looks like from your example those two things are the missing pieces, so compare with the below code and adjust and it will work for you.
Your HTML template:
<table mat-table [dataSource]="dataSource">
<!-- columns here -->
<tr mat-header-row *matHeaderRowDef="displayedColumns"></tr>
<tr mat-row *matRowDef="let row; columns: displayedColumns;"></tr>
</table>
<mat-paginator
#paginator
(page)="pageChangeEvent($event)"
[length]="totalRecords"
[pageSize]="pageSize"
[pageIndex]="pageIndex"
[length]="totalRecords"
[pageSizeOptions]="[5, 10, 20, 50, 100]"
showFirstLastButtons>
</mat-paginator>
In your component TS:
@ViewChild('paginator', { static: true }) paginator: MatPaginator;
dataSource = new MatTableDataSource<ApidatumDisplay>([]);
displayedColumns: string[] = //... set columns here
totalRecords = 0;
pageSize = 10;
pageIndex = 0;
getPagedData() {
const search = {
// ... set filters here
};
this.searching = true;
this.service.search(search).subscribe({
next: ((results) => {
this.totalRecords = results?.length ? results[0].totalRecords : 0;
this.dataSource.data = results || [];
}),
complete: () => this.searching = false,
error: () => this.searching = false,
});
}
pageChangeEvent(event: PageEvent) {
this.pageIndex = event.pageIndex;
this.pageSize = event.pageSize;
this.getPagedData();
}
CodePudding user response:
To add pagination to the Angular material table i.e., mat-table
we can use mat-paginator
component.
mat-paginator
selector is part of Angular material module called MatPaginator
.
Refer : https://www.angularjswiki.com/material/mat-table-pagination/#pagination-in-mat-table