Angular 13 Material DataTable with Pagination, Filtering, Sorting Example

In this step by step Angular and Angular Material 11 tutorial, we will learn how to create datatable in Angular using Angular Material. We will also learn how to create pagination, sorting, and filtering.

Angular material offers a table component, which is a pre-defined UI component for angular based applications. It can save time because it comes with searching, sorting, filtering, and pagination.

In this tutorial, we will create an angular app and add Angular Material so that we can use it to create user-friendly and eye-catching user interfaces. Our table component will be fully responsive and indeed work great in all the devices.

Angular Material 13 Data Table Example

Creating tables with angular material is super easy and can be done injecting MatTableModule service in Angular. W

We are covering up the following topics in this tutorial:

  • Creating an angular table pagination with angular material
  • Creating sort table by column with angular
  • Creating angular material table filter by column
  • Creating angular material pagination with dynamic data

Create Angular Application

First, start with creating an Angular application:

ng new angular-material-data-table-example

Answer some questions asked by Angular CLI:

# ? Would you like to add Angular routing? = No
# ? Which stylesheet format would you like to use? = CSS

Move to project root:

cd angular-material-data-table-example

Disable Strict Angular TypeStrict Errors

The latest version of Angular comes with strict mode, you have to manually disable the strict mode you can set “strict”: false, "noImplicitReturns": false and "strictTemplates": false inside the compilerOptions and angularCompilerOptions in tsconfig.json file.

Add Angular Material 10

Angular Material library can be installed with just one command:

ng add @angular/material

Select the Angular material theme from the given options:

? Choose a prebuilt theme name, or "custom" for a custom theme: Indigo/Pink

❯ Indigo/Pink        [ Preview: https://material.angular.io?theme=indigo-pink ] 
  Deep Purple/Amber  [ Preview: https://material.angular.io?theme=deeppurple-amber ] 
  Pink/Blue Grey     [ Preview: https://material.angular.io?theme=pink-bluegrey ] 
  Purple/Green       [ Preview: https://material.angular.io?theme=purple-green ]

Select Yes and add Typography and Animations packages of Angular Material.

# ? Set up global Angular Material typography styles? Yes
# ? Set up browser animations for Angular Material? Yes

Add code in styles.css file.

@import "~@angular/material/prebuilt-themes/indigo-pink.css";

Create Separate Angular Material Module File

Its always a best practice to import angular material modules in a centralized file. So, create ng-material.module.ts file and place the following code in it.

import { CommonModule } from '@angular/common';
import { NgModule } from '@angular/core';
import { MatTableModule } from '@angular/material/table';
import { MatPaginatorModule } from '@angular/material/paginator';
import { MatSortModule } from '@angular/material/sort';

const materialModules = [
  MatTableModule,
  MatPaginatorModule,
  MatSortModule
];

@NgModule({
  imports: [
    CommonModule,
    ...materialModules
  ],
  exports: [
    ...materialModules
  ],
})

export class NgMaterialModule { }

Next, import and register NgMaterialModule in app.module.ts.

import { BrowserModule } from '@angular/platform-browser';
import { AppComponent } from './app.component';

import { NgModule, CUSTOM_ELEMENTS_SCHEMA } from '@angular/core';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
import { NgMaterialModule } from './ng-material.module';


@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    BrowserModule,
    BrowserAnimationsModule,
    NgMaterialModule,
  ],
  providers: [],
  bootstrap: [AppComponent],
  schemas: [CUSTOM_ELEMENTS_SCHEMA]
})
export class AppModule { }

Create Angular Material Data Table

Showing data rows is a no-brainer, so, mat-table directive helps build the data table in angular with angular material.

Add code in app.component.html file.

<table mat-table [dataSource]="dataSource" class="mat-elevation-z8">  
  <ng-container matColumnDef="position">
    <th mat-header-cell *matHeaderCellDef> No. </th>
    <td mat-cell *matCellDef="let element"> {{element.position}} </td>
  </ng-container>

  <ng-container matColumnDef="name">
    <th mat-header-cell *matHeaderCellDef> Name </th>
    <td mat-cell *matCellDef="let element"> {{element.name}} </td>
  </ng-container>

  <ng-container matColumnDef="email">
    <th mat-header-cell *matHeaderCellDef> Email </th>
    <td mat-cell *matCellDef="let element"> {{element.email}} </td>
  </ng-container>

  <tr mat-header-row *matHeaderRowDef="displayedColumns"></tr>
  <tr mat-row *matRowDef="let row; columns: displayedColumns;"></tr>
</table>

Place code in app.component.ts file.

import { Component, ViewChild } from '@angular/core';
import { MatPaginator } from '@angular/material/paginator';
import { MatTableDataSource } from '@angular/material/table';

export interface UserElement {
  name: string;
  position: number;
  email: string;
}

const ELEMENT_DATA: UserElement[] = [
  { position: 1, name: 'John', email: 'john@gmail.com' },
  { position: 2, name: 'Herry', email: 'herry@gmail.com' },
  { position: 3, name: 'Ann', email: 'ann@gmail.com' },
  { position: 4, name: 'Johnny', email: 'johnny@gmail.com' },
  { position: 5, name: 'Roy', email: 'roy@gmail.com' },
  { position: 6, name: 'Kia', email: 'kia@gmail.com' },
  { position: 7, name: 'Merry', email: 'merry@gmail.com' },
  { position: 8, name: 'William', email: 'william@gmail.com' },
  { position: 9, name: 'Shia', email: 'shia@gmail.com' },
  { position: 10, name: 'Kane', email: 'kane@gmail.com' },
];

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.scss'],
})

export class AppComponent {
  displayedColumns: string[] = ['position', 'name', 'email'];
  dataSource = new MatTableDataSource(ELEMENT_DATA);
  @ViewChild(MatPaginator) paginator: MatPaginator;

  ngOnInit() {
    this.dataSource.paginator = this.paginator;
  }
}

Add little bit of styling for table, add code in styles.css file.

table {
  width: 100%;
}

Adding Pagination in Angular Table

Adding Pagination in Angular data table is easy, If you remember we have already imported the MatPaginatorModule in NgMaterialModule class.

Add code in app.component.ts to implement pagination module.

import { Component, ViewChild } from '@angular/core';
import { MatPaginator } from '@angular/material/paginator';
import { MatTableDataSource } from '@angular/material/table';

export interface UserElement {
  name: string;
  position: number;
  email: string;
}

const ELEMENT_DATA: UserElement[] = [
  { position: 1, name: 'John', email: 'john@gmail.com' },
  { position: 2, name: 'Herry', email: 'herry@gmail.com' },
  { position: 3, name: 'Ann', email: 'ann@gmail.com' },
  { position: 4, name: 'Johnny', email: 'johnny@gmail.com' },
  { position: 5, name: 'Roy', email: 'roy@gmail.com' },
  { position: 6, name: 'Kia', email: 'kia@gmail.com' },
  { position: 7, name: 'Merry', email: 'merry@gmail.com' },
  { position: 8, name: 'William', email: 'william@gmail.com' },
  { position: 9, name: 'Shia', email: 'shia@gmail.com' },
  { position: 10, name: 'Kane', email: 'kane@gmail.com' },
];

@Component({
  selector: 'app-root',
  styleUrls: ['./app.component.scss'],
  templateUrl: './app.component.html',
})
export class AppComponent {
  displayedColumns: string[] = ['position', 'name', 'email'];
  dataSource = new MatTableDataSource(ELEMENT_DATA);
  @ViewChild(MatPaginator) paginator: MatPaginator;

  ngOnInit() {
    this.dataSource.paginator = this.paginator;
  }
}

Next, include code in app.component.html.

<mat-paginator [pageSizeOptions]="[6, 12, 18]" showFirstLastButtons></mat-paginator>

Integrate Data Sorting in Angular 12 Table

Now, we will implement data sorting feature in Angular app. So to sort the data within data tables, we need to rely on MatSortModule.

We have already imported this service in NgMaterialModule, next place the code inside the app.component.ts file.

import { Component, ViewChild } from '@angular/core';
import { MatPaginator } from '@angular/material/paginator';
import { MatTableDataSource } from '@angular/material/table';
import { MatSort } from '@angular/material/sort';

export interface UserElement {
  name: string;
  position: number;
  email: string;
}

const ELEMENT_DATA: UserElement[] = [
  { position: 1, name: 'John', email: 'john@gmail.com' },
  { position: 2, name: 'Herry', email: 'herry@gmail.com' },
  { position: 3, name: 'Ann', email: 'ann@gmail.com' },
  { position: 4, name: 'Johnny', email: 'johnny@gmail.com' },
  { position: 5, name: 'Roy', email: 'roy@gmail.com' },
  { position: 6, name: 'Kia', email: 'kia@gmail.com' },
  { position: 7, name: 'Merry', email: 'merry@gmail.com' },
  { position: 8, name: 'William', email: 'william@gmail.com' },
  { position: 9, name: 'Shia', email: 'shia@gmail.com' },
  { position: 10, name: 'Kane', email: 'kane@gmail.com' },
];

@Component({
  selector: 'app-root',
  styleUrls: ['./app.component.scss'],
  templateUrl: './app.component.html',
})

export class AppComponent {
  displayedColumns: string[] = ['position', 'name', 'email'];
  dataSource = new MatTableDataSource(ELEMENT_DATA);

  @ViewChild(MatPaginator) paginator: MatPaginator;
  @ViewChild(MatSort) sort: MatSort;

  ngOnInit() {
    this.dataSource.paginator = this.paginator;
    this.dataSource.sort = this.sort;
  }
}

Add the code inside the app.component.html template. The sort object is connected with dataSource, now data sorting in angular has implemented.

<table mat-table [dataSource]="dataSource" matSort class="mat-elevation-z8">
    <ng-container matColumnDef="position">
        <th mat-header-cell *matHeaderCellDef mat-sort-header> No. </th>
        <td mat-cell *matCellDef="let element"> {{element.position}} </td>
    </ng-container>

    <ng-container matColumnDef="name">
        <th mat-header-cell *matHeaderCellDef mat-sort-header> Name </th>
        <td mat-cell *matCellDef="let element"> {{element.name}} </td>
    </ng-container>

    <ng-container matColumnDef="email">
        <th mat-header-cell *matHeaderCellDef mat-sort-header> Email </th>
        <td mat-cell *matCellDef="let element"> {{element.email}} </td>
    </ng-container>

    <tr mat-header-row *matHeaderRowDef="displayedColumns"></tr>
    <tr mat-row *matRowDef="let row; columns: displayedColumns;"></tr>
</table>

<mat-paginator [pageSizeOptions]="[6, 12, 18]" showFirstLastButtons></mat-paginator>

Add CSS in styles.css.

table {
  width: 100%;
}

th.mat-sort-header-sorted {
  color: black;
}

Test Angular DataTable App

Now, Its time to test datatables built with Angular Material UI library.

ng serve --open

Finally, Angular 11 Material DataTable with Pagination, Filtering, Sorting tutorial has been completed.