---
product: "AG Grid"
title: "Loading Rows"
description: "Display skeleton rows while Client-Side Row Model data is loading."
framework: angular
version: "36.2.0"
related:
    - title: "Overview"
      url: "https://www.ag-grid.com/angular-data-grid/overlays-overview/"
    - title: "Provided Overlays"
      url: "https://www.ag-grid.com/angular-data-grid/overlays-provided/"
    - title: "Active Overlay"
      url: "https://www.ag-grid.com/angular-data-grid/overlays-active/"
llms: "https://www.ag-grid.com/llms.txt"
---

# Loading Rows

The Client-Side Row Model can display skeleton rows instead of the loading overlay while row data is loading.

#### Loading Rows

```ts
import { Component } from "@angular/core";
import { AgGridAngular } from "ag-grid-angular";
import "./styles.css";
import {
  ClientSideRowModelModule,
  ColDef,
  ColGroupDef,
  GridApi,
  GridOptions,
  GridReadyEvent,
  LoadingRowsOptions,
  ModuleRegistry,
  enableDevValidations,
} from "ag-grid-community";

if (process.env.NODE_ENV !== "production") {
  enableDevValidations();
}

ModuleRegistry.registerModules([ClientSideRowModelModule]);

interface IAthlete {
  athlete: string;
  country: string;
  sport: string;
  year: number;
  gold: number;
  silver: number;
  bronze: number;
}

@Component({
  selector: "my-app",
  standalone: true,
  imports: [AgGridAngular],
  template: `<div class="example-wrapper">
    <div class="example-header">
      <label>
        <span>loading:</span>
        <input
          type="checkbox"
          id="loading-toggle"
          checked=""
          (change)="onLoadingToggled()"
        />
      </label>
      <label>
        <span>loadingRows.rowCount:</span>
        <input
          type="number"
          id="row-count"
          min="1"
          max="50"
          value="10"
          (change)="onRowCountChanged()"
        />
      </label>
    </div>
    <ag-grid-angular
      style="width: 100%; height: 100%;"
      [rowData]="rowData"
      [loading]="true"
      [loadingRows]="loadingRows"
      [columnDefs]="columnDefs"
      (gridReady)="onGridReady($event)"
    />
  </div> `,
})
export class AppComponent {
  private gridApi!: GridApi<IAthlete>;

  rowData: IAthlete[] | null = [
    {
      athlete: "Michael Phelps",
      country: "United States",
      sport: "Swimming",
      year: 2008,
      gold: 8,
      silver: 0,
      bronze: 0,
    },
    {
      athlete: "Natalie Coughlin",
      country: "United States",
      sport: "Swimming",
      year: 2008,
      gold: 1,
      silver: 2,
      bronze: 3,
    },
    {
      athlete: "Aleksey Nemov",
      country: "Russia",
      sport: "Gymnastics",
      year: 2000,
      gold: 2,
      silver: 1,
      bronze: 3,
    },
    {
      athlete: "Alicia Coutts",
      country: "Australia",
      sport: "Swimming",
      year: 2012,
      gold: 1,
      silver: 3,
      bronze: 1,
    },
    {
      athlete: "Missy Franklin",
      country: "United States",
      sport: "Swimming",
      year: 2012,
      gold: 4,
      silver: 0,
      bronze: 1,
    },
    {
      athlete: "Ryan Lochte",
      country: "United States",
      sport: "Swimming",
      year: 2012,
      gold: 2,
      silver: 2,
      bronze: 1,
    },
    {
      athlete: "Chris Hoy",
      country: "Great Britain",
      sport: "Cycling",
      year: 2008,
      gold: 3,
      silver: 0,
      bronze: 0,
    },
    {
      athlete: "Ian Thorpe",
      country: "Australia",
      sport: "Swimming",
      year: 2000,
      gold: 3,
      silver: 2,
      bronze: 0,
    },
  ];
  loadingRows: boolean | LoadingRowsOptions = { rowCount: 10 };
  columnDefs: ColDef[] = [
    { field: "athlete" },
    { field: "country" },
    { field: "sport" },
    { field: "year" },
    { field: "gold" },
    { field: "silver" },
    { field: "bronze" },
  ];

  onLoadingToggled() {
    const loading =
      document.querySelector<HTMLInputElement>("#loading-toggle")!.checked;
    this.gridApi.setGridOption("loading", loading);
  }

  onRowCountChanged() {
    const rowCount =
      document.querySelector<HTMLInputElement>("#row-count")!.valueAsNumber;
    if (!Number.isInteger(rowCount) || rowCount < 1) {
      return;
    }
    this.gridApi.setGridOption("loadingRows", { rowCount });
  }

  onGridReady(params: GridReadyEvent<IAthlete>) {
    this.gridApi = params.api;
  }
}
```

[Live example: Loading Rows](https://www.ag-grid.com/examples/loading-rows/client-side-loading-rows/angular/)

> **Note**
>
> For loading rows managed by a server-side datasource, see [Server-Side Row Model Loading Rows](https://www.ag-grid.com/angular-data-grid/server-side-model-loading-rows/).

## Enabling Loading Rows

Set `loadingRows=true` to use skeleton rows when `loading=true`. Ten rows are displayed by default. Alternatively, provide `LoadingRowsOptions` with `rowCount` to configure the number displayed.

```ts
<ag-grid-angular
    [loading]="loading"
    [loadingRows]="loadingRows"
    /* other grid options ... */ />

this.loading = true;
this.loadingRows = {
    rowCount: 10,
};
```

| Property | Type | Required | Default | Description |
| --- | --- | --- | --- | --- |
| `loading` | `boolean` |  |  |  |
| `loadingRows` | `boolean \| LoadingRowsOptions` |  |  |  |

Loading rows are visual placeholders and are not included in Client-Side Row Model operations such as sorting, filtering, grouping or selection. When loading finishes, set `loading=false` to display the row data.

Both options can be updated at runtime. Update `loadingRows` to change the row count while loading, or set it to `false` to switch back to the overlay without ending the loading state.

## Custom Loading Cells

Set `loadingCellRenderer` and `loadingCellRendererParams` on a column definition to customise that column, or on `defaultColDef` to customise every loading cell. See [Loading Cell Component](https://www.ag-grid.com/angular-data-grid/component-loading-cell-renderer/) for component interfaces, parameters and dynamic component selection.

The following example uses a custom loading component for the Athlete column while the other columns retain the default skeleton effect.

#### Custom Loading Cells

```ts
import { Component } from "@angular/core";
import { AgGridAngular } from "ag-grid-angular";
import "./styles.css";
import {
  ClientSideRowModelModule,
  ColDef,
  ColGroupDef,
  GridApi,
  GridOptions,
  GridReadyEvent,
  LoadingRowsOptions,
  ModuleRegistry,
  enableDevValidations,
} from "ag-grid-community";

if (process.env.NODE_ENV !== "production") {
  enableDevValidations();
}

ModuleRegistry.registerModules([ClientSideRowModelModule]);
import { CustomLoadingCellRenderer } from "./custom-loading-cell-renderer.component";

interface IAthlete {
  athlete: string;
  country: string;
  sport: string;
  year: number;
  gold: number;
  silver: number;
  bronze: number;
}

@Component({
  selector: "my-app",
  standalone: true,
  imports: [AgGridAngular, CustomLoadingCellRenderer],
  template: `<div class="example-wrapper">
    <div class="example-header">
      <label>
        <span>loading:</span>
        <input
          type="checkbox"
          id="loading-toggle"
          checked=""
          (change)="onLoadingToggled()"
        />
      </label>
    </div>
    <ag-grid-angular
      style="width: 100%; height: 100%;"
      [rowData]="rowData"
      [loading]="true"
      [loadingRows]="loadingRows"
      [columnDefs]="columnDefs"
      (gridReady)="onGridReady($event)"
    />
  </div> `,
})
export class AppComponent {
  private gridApi!: GridApi<IAthlete>;

  rowData: IAthlete[] | null = [
    {
      athlete: "Michael Phelps",
      country: "United States",
      sport: "Swimming",
      year: 2008,
      gold: 8,
      silver: 0,
      bronze: 0,
    },
    {
      athlete: "Natalie Coughlin",
      country: "United States",
      sport: "Swimming",
      year: 2008,
      gold: 1,
      silver: 2,
      bronze: 3,
    },
    {
      athlete: "Aleksey Nemov",
      country: "Russia",
      sport: "Gymnastics",
      year: 2000,
      gold: 2,
      silver: 1,
      bronze: 3,
    },
    {
      athlete: "Alicia Coutts",
      country: "Australia",
      sport: "Swimming",
      year: 2012,
      gold: 1,
      silver: 3,
      bronze: 1,
    },
    {
      athlete: "Missy Franklin",
      country: "United States",
      sport: "Swimming",
      year: 2012,
      gold: 4,
      silver: 0,
      bronze: 1,
    },
    {
      athlete: "Ryan Lochte",
      country: "United States",
      sport: "Swimming",
      year: 2012,
      gold: 2,
      silver: 2,
      bronze: 1,
    },
    {
      athlete: "Chris Hoy",
      country: "Great Britain",
      sport: "Cycling",
      year: 2008,
      gold: 3,
      silver: 0,
      bronze: 0,
    },
    {
      athlete: "Ian Thorpe",
      country: "Australia",
      sport: "Swimming",
      year: 2000,
      gold: 3,
      silver: 2,
      bronze: 0,
    },
  ];
  loadingRows: boolean | LoadingRowsOptions = { rowCount: 10 };
  columnDefs: ColDef[] = [
    {
      field: "athlete",
      loadingCellRenderer: CustomLoadingCellRenderer,
      loadingCellRendererParams: {
        loadingMessage: "Loading athletes...",
      },
    },
    { field: "country" },
    { field: "sport" },
    { field: "year" },
    { field: "gold" },
    { field: "silver" },
    { field: "bronze" },
  ];

  onLoadingToggled() {
    const loading =
      document.querySelector<HTMLInputElement>("#loading-toggle")!.checked;
    this.gridApi.setGridOption("loading", loading);
  }

  onGridReady(params: GridReadyEvent<IAthlete>) {
    this.gridApi = params.api;
  }
}
```

[Live example: Custom Loading Cells](https://www.ag-grid.com/examples/loading-rows/custom-loading-cells/angular/)
