Data Grid

Display and manipulate tabular data with the Ignite UI for Angular Data Grid. Quickly bind your data with very little coding or configuration. Features include filtering, sorting, paging, templates, movable columns, and the ability to edit and update data. User actions are easy to understand and can be controlled programmatically.

Demo


Dependencies

The grid is exported as an NgModule, thus all you need to do in your application is to import the IgxGridModule inside your AppModule:

// app.module.ts

import { IgxGridModule } from 'igniteui-angular';
// Or
import { IgxGridModule } from 'igniteui-angular/grid';

@NgModule({
    imports: [
        ...
        IgxGridModule.forRoot(),
        ...
    ]
})
export class AppModule {}

Each of the components, directives and helper classes in the IgxGridModule can be imported either through the grid sub-package or through the main bundle in igniteui-angular. While you don't need to import all of them to instantiate and use the grid, you usually will import them (or your editor will auto-import them for you) when declaring types that are part of the grid API.

import { IgxGridComponent } from 'igniteui-angular/grid/';
// Or
import { IgxGridComponent } from 'igniteui-angular'
...

@ViewChild('myGrid', { read: IgxGridComponent })
public grid: IgxGridComponent;

Usage

Now that we have the grid module imported, let’s get started with a basic configuration of the igx-grid that binds to local data:

<igx-grid #grid1 id="grid1" [data]="localData" [autoGenerate]="true"></igx-grid>

The id property is a string value and is the unique identifier of the grid which will be autogenerated if not provided, while data binds the grid, in this case to local data.

The autoGenerate property tells the igx-grid to auto generate the grid's IgxColumnComponent based on the data source fields. It will also try to deduce the appropriate data type for the column if possible. Otherwise, the developer needs to explicitly define the columns and the mapping to the data source fields.

Columns configuration

IgxGridColumnComponent is used to define the grid's columns collection and to enable features per column like filtering, sorting, and paging. Cell, header, and footer templates are also available.

Let's turn the autoGenerate property off and define the columns collection in the markup:

<igx-grid #grid1 [data]="data | async" [autoGenerate]="false" [paging]="true" [perPage]="6" (onColumnInit)="initColumns($event)"
    (onSelection)="selectCell($event)">
    <igx-column field="Name" [sortable]="true" header=" " [filterable]="true"></igx-column>
    <igx-column field="AthleteNumber" [sortable]="true" header="Athlete number"></igx-column>
    <igx-column field="TrackProgress" header="Track progress">
        <ng-template igxCell let-value>
            <igx-linear-bar [stripped]="false" [value]="value" [max]="100"></igx-linear-bar>
        </ng-template>
    </igx-column>
</igx-grid>

Each of the columns of the grid can be templated separately. The column expects ng-template tags decorated with one of the grid module directives.

igxHeader targets the column header providing as a context the column object itself.

...
<igx-column field="Name">
    <ng-template igxHeader let-column>
        {{ column.field | uppercase }}
    </ng-template>
</igx-column>
...

igxCell applies the provided template to all cells in the column. The context object provided in the template consists of the cell value provided implicitly and the cell object itself.

...
<igx-column field="Name">
    <ng-template igxCell let-value>
        {{ value | titlecase }}
    </ng-template>
</igx-column>
...

In the snippet above we "take" a reference to the implicitly provided cell value. This is sufficient if you just want to present some data and maybe apply some custom styling or pipe transforms over the value of the cell. However even more useful is to take the IgxGridCellComponent object itself as shown below:

<igx-grid #grid [data]="data">
    <igx-column dataType="string" field="Name">
        <ng-template igxCell let-cell="cell">
            <!-- Implement row deleting inside the cell template itself -->
            <span tabindex="0" (keydown.delete)="grid.deleteRow(cell.rowIndex)">{{ cell.value | titlecase }}</span>
        </ng-template>
    </igx-column>
    <igx-column dataType="boolean" field="Subscribtion">
        <ng-template igxCell let-cell="cell">
            <!-- Bind the cell value through the ngModel directive and update the data source when the value is changed in the template -->
            <input type="checkbox" [ngModel]="cell.value" (ngModelChange)="cell.update($event)" />
        </ng-template>
    </igx-column>
<igx-grid>

The column also accepts one last template that will be used when a cell is in edit mode. As with the other column templates, the provided context object is again the cell value and the cell object itself. Of course in order to make the edit-mode template accessible to end users, you need to set the editable property of the IgxColumnComponent to true.

<igx-column dataType="number" editable="true" field="Price">
    <ng-template igxCellEditor let-cell="cell">
        <label for="price">
            Enter the new price tag
        </label>
        <input name="price" type="number" [ngModel]="cell.value" (ngModelChange)="cell.update(convertToNumber($event))" />
    </ng-template>
</igx-column>

Make sure to check the API for the IgxGridCellComponent in order to get accustomed with the provided properties you can use in your templates.

Each of the column templates can be changed programmatically at any point through the IgxColumnComponent object itself. For example in the code below, we have declared two templates for our user data. In our TypeScript code we'll get references to the templates themselves and then based on some condition we will render the appropriate template for the column in our application.

<igx-grid>
    <!-- Column declarations -->
</igx-grid>

<ng-template #normalView let-value>
    <div class="user-details">{{ val }}</div>
    <user-details-component></user-details-component>
</ng-template>

<ng-template #smallView let-value>
    <div class="user-details-small">{{ val }}</div>
</ng-template>
@ViewChild("normalView", { read: TemplateRef })
public normalView: TemplateRef<any>;

@ViewChild("smallView", { read: TemplateRef })
public smallView: TemplateRef<any>;

....

const column = this.grid.getColumnByName("User");
// Return the appropriate template based on some conditiion.
// For example saved user settings, viewport size, etc.
column.bodyTemplate = this.smallView;

Column properties can also be set in code in the initColumns event which is emitted when the columns are initialized in the grid.

public initColumns(column: IgxGridColumn) {
    const column: IgxColumnComponent = column;
    if (column.field === 'ProductName') {
        column.filterable = true;
        column.sortable = true;
        column.editable = true;
    }
}

The code above will make the ProductName column filterable, sortable, and editable and will instantiate the corresponding features UI (like inputs for editing, etc.).

Data binding

Before going any further with the grid we want to change the grid to bind to remote data service, which is the common scenario in large-scale applications. A good practice is to separate all data fetching related logic in a separate data service, so we are going to create a service which will handle the fetching of data from the server.

Let's implement our service in a separate file

// northwind.service.ts

import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { Observable } from 'rxjs/Observable';
import { of } from 'rxjs/observable/of';
import { catchError, map } from 'rxjs/operators';

We're importing the Injectable decorator which is an essential ingredient in every Angular service definition. The HttpClient will provide us with the functionality to communicate with backend services. It returns an Observable of some result to which we will subscribe in our grid component.

Note: Before Angular 5 the HttpClient was located in @angular/http and was named Http.

Since we will receive a JSON response containing an array of records, we may as well help ourselves by specifing what kind of data we're expecting to be returned in the observable by defining an interface with the correct shape. Type checking is always recommended and can save you some headaches down the road.

// northwind.service.ts

export interface NorthwindRecord {
    ProductID: number;
    ProductName: string;
    SupplierID: number;
    CategoryID: number;
    QuantityPerUnit: string;
    UnitPrice: number;
    UnitsInStock: number;
    UnitsOnOrder: number;
    ReorderLevel: number;
    Discontinued: boolean;
    CategoryName: string;
}

The service itself is pretty simple consisting of one method: fetchData that will return an Observable<NorthwindRecord[]>. In cases when the request fails for any reason (server unavailable, network error, etc), the HttpClient will return an error. We'll leverage the catchError operator which intercepts an Observable that failed and passes the error to an error handler. Our error handler will log the error and return a safe value.

// northwind.service.ts

@Injectable()
export class NorthwindService {
    private url = 'http://services.odata.org/V4/Northwind/Northwind.svc/Alphabetical_list_of_products';

    constructor(private http: HttpClient) {}

    public fetchData(): Observable<NorthwindRecord[]> {
        return this.http
            .get(this.url)
            .pipe(
                map(response => response['value']),
                catchError(
                    this.errorHandler('Error loading northwind data', [])
                )
            );
    }

    private errorHandler<T>(message: string, result: T) {
        return (error: any): Observable<any> => {
            console.error(`${message}: ${error.message}`);
            return of(result as T);
        };
    }
}

Make sure to import both the HttpClientModule and our service in the application module and register the service as a provider.

// app.module.ts

import { HttpClientModule } from '@angular/common/http';
...
import { NorthwindService } from './northwind.service';

@NgModule({
    imports: [
        ...
        HttpClientModule
        ...
    ],
    providers: [
        NorthwindService
    ]
})
export class AppModule {}

After implementing the service we will inject it in our component's constructor and use it to retrieve the data. The ngOnInit lifecycle hook is a good place to dispatch the initial request.

Note: In the code below, you may wonder why are we setting the records property to an empty array before subscribing to the service. The Http request is asynchronous, and until it completes, the records property will be undefined which will result in an error when the grid tries to bind to it. You should either initialize it with a default value or use a BehaviorSubject.

// my.component.ts

@Component({
    ...
})
export class MyComponent implements OnInit {

    public records: NorthwindRecord[];

    constructor(private northwindService: NorthwindService) {}

    ngOnInit() {
        this.records = [];
        this.northwindService.fetchData().subscribe((records) => this.records = records);
    }
}

and in the template of the component:

    <igx-grid [data]="records">
        <igx-column field="ProductId"></igx-column>
        <!-- rest of the column definitions -->
        ...
    </igx-grid>

Note: The grid autoGenerate property is best to be avoided when binding to remote data for now. It assumes that the data is available in order to inspect it and generate the appropriate columns. This is usually not the case until the remote service responds, and the grid will throw an error. Making autoGenerate available, when binding to remote service, is on our roadmap for future versions.

Known Limitations

Limitation Description
Column widths set in percentage and px Currently we do not support mixing of column widths with % and px.
When trying to filter a column of type number If a value different than number is entered into the filtering input, NaN is returned due to an incorrect cast.
Grid width does not depend on the column widths The width of all columns does not determine the spanning of the grid itself. It is determined by the parent container dimensions or the defined grid's width.
Grid nested in parent container When grid's width is not set and it is placed in a parent container with defined dimensions, the grid spans to this container.
Grid OnPush ChangeDetectionStrategy The grid operates with ChangeDetectionStrategy.OnPush so whenever some customization appears make sure that the grid is notified about the changes that happens.
Columns have a minimum allowed column width. Depending on the displayDensity option, they are as follows:
"compact": 24px
"cosy": 32px
"comfortable ": 48px
If width less than the minimum allowed is set it will not affect the rendered elements. They will render with the minimum allowed width for the corresponding displayDensity. This may lead to an unexpected behavior with horizontal virtualization and is therefore not supported.

API

Inputs

Below is the list of all inputs that the developers may set to configure the grid look/behavior:

Name Type Description
id string Unique identifier of the Grid. If not provided it will be automatically generated.
data Array The data source for the grid.
autoGenerate boolean Autogenerate grid's columns, default value is false
paging bool Enables the paging feature. Defaults to false.
perPage number Visible items per page, default is 15
filteringLogic FilteringLogic The filtering logic of the grid. Defaults to AND.
filteringExpressionsTree IFilteringExpressionsTree The filtering state of the grid.
sortingExpressions Array The sorting state of the grid.
height string The height of the grid element. You can pass values such as 1000px, 75%, etc.
width string The width of the grid element. You can pass values such as 1000px, 75%, etc.
evenRowCSS string Additional styling classes applied to all even rows in the grid.
oddRowCSS string Additional styling classses applied to all odd rows in the grid.
paginationTemplate TemplateRef You can provide a custom ng-template for the pagination part of the grid.
groupingExpressions Array The group by state of the grid.
groupingExpansionState Array The list of expansion states of the group rows. Contains the expansion state(expanded: boolean) and an unique identifier for the group row (Array) that contains a list of the group row's parents described via their fieldName and value.
groupsExpanded Boolean Determines whether created groups are rendered expanded or collapsed.
groupsRowList QueryList A list of visible group rows.
groupsRecords IGroupByRecord[] All groups in hierarchy reflecting the current groups state.

Outputs

A list of the events emitted by the igx-grid:

Name Description
Event emitters Notify for a change
onEditDone Emitted when a cell value changes. Returns { currentValue: any, newValue: any }
onCellClick Emitted when a cell is clicked. Returns the cell object.
onSelection Emitted when a cell is selected. Returns the cell object.
onColumnInit Emitted when the grid columns are initialized. Returns the column object.
onSortingDone Emitted when sorting is performed through the UI. Returns the sorting expression.
onFilteringDone Emitted when filtering is performed through the UI. Returns the filtering expressions tree of the column for which the filtering was performed.
onPagingDone Emitted when paging is performed. Returns an object consisting of the previous and the new page.
onRowAdded Emitted when a row is being added to the grid through the API. Returns the data for the new row object.
onRowDeleted Emitted when a row is deleted through the grid API. Returns the row object being removed.
onColumnPinning Emitted when a column is pinned through the grid API. The index that the column is inserted at may be changed through the insertAtIndex property.
onColumnResized Emitted when a column is resized. Returns the column object, previous and new column width.
onContextMenu Emitted when a cell is right clicked. Returns the cell object.
onDoubleClick Emitted when a cell is double clicked. Returns the cell object.
onGroupingDone Emitted when a a new column is grouped or ungrouped. Returns the ISortingExpression related to the grouping operation.

Defining handlers for these event emitters is done using declarative event binding:

<igx-grid #grid1 [data]="data | async" [autoGenerate]="false"
    (onColumnInit)="initColumns($event)" (onSelection)="selectCell($event)"></igx-grid>

Methods

Here is a list of all public methods exposed by igx-grid:

Signature Description
getColumnByName(name: string) Returns the column object with field property equal to name or undefined if no such column exists.
getCellByColumn(rowIndex: number, columnField: string) Returns the cell object in column with columnField and row with rowIndex or undefined.
getCellByKey(rowSelector: any, columnField: string) Returns cell object only if primary key is specified in the grid, rowSelector match any rowID and columnField exists in the grid, else returns undefined.
getRowByIndex(index: number) Returns row object if the specified rowIndex exist and is currently in the display area of the grid.
getRowByKey(keyValue: any) Returns row object only if primary key is specified in the grid and the specified keyValue exist as a rowID in the grid.
addRow(data: any) Creates a new row object and adds the data record to the end of the data source.
deleteRow(rowSelector: any) Removes the row object and the corresponding data record from the data source only if primary key is specified in the grid. The method accept rowSelector as a parameter, which is the rowID.
updateRow(value: any, rowSelector: any) Updates the row object, which is specified by rowSelector parameter /rowSelector parameter correspond to rowID/ and the data source record with the passed value. This method will apply requested update only if primary key is specified in the grid.
updateCell(value: any, rowSelector: any, column: string) Updates the cell object and the record field in the data source. The method accept 3 parameters - value - the new value which is to be set, and the other two params rowSelector and column identify the cell which is going to be updated. rowSelector corresponds to rowID and column to column field. This method will apply requested update only if primary key is specified in the grid.
filter(name: string, value: any, conditionOrExpressionTree?: IFilteringOperation, ignoreCase?: boolean) Filters a single column. A filtering operation is used as parameter. Check the available filtering conditions.
filter(name: string, value: any, conditionOrExpressionTree?: IFilteringExpressionsTree, ignoreCase?: boolean) Filters a single column. A filtering expressions tree is used as parameter.
filterGlobal(value: any, condition?, ignoreCase?) Filters all the columns in the grid with the same condition.
clearFilter(name?: string) If name is provided, clears the filtering state of the corresponding column, otherwise clears the filtering state of all columns.
sort(expression: ISortingExpression) Sorts a single column.
sort(expressions: Array) Sorts the grid columns based on the provided array of sorting expressions.
clearSort(name?: string) If name is provided, clears the sorting state of the corresponding column, otherwise clears the sorting state of all columns.
enableSummaries(fieldName: string, customSummary?: any) Enable summaries for the specified column and apply your customSummary. If you do not provide the customSummary, then the default summary for the column data type will be applied.
enableSummaries(expressions: Array) Enable summaries for the columns and apply your customSummary if it is provided.
disableSummaries(fieldName: string) Disable summaries for the specified column.
disableSummaries(columns: string[]) Disable summaries for the listed columns.
clearSummaryCache() Delete all cached summaries and force recalculation.
previousPage() Goes to the previous page if paging is enabled and the current page is not the first.
nextPage() Goes to the next page if paging is enabled and current page is not the last.
paginate(page: number) Goes to the specified page if paging is enabled. Page indices are 0 based.
markForCheck() Manually triggers a change detection cycle for the grid and its children.
pinColumn(name: string): boolean Pins a column by field name. Returns whether the operation is successful.
unpinColumn(name: string): boolean Unpins a column by field name. Returns whether the operation is successful.
groupBy(expression: ISortingExpression) Groups by a new column based on the provided expression or modifies an existing one.
groupBy(expressions: Array) Groups columns based on the provided array of sorting expressions.
clearGrouping() Clears all grouping in the grid.
clearGrouping(fieldName: string) Clear grouping from a particular column.
isExpandedGroup(group: IGroupByRecord ) Returns if a group is expanded or not.
toggleGroup(group: IGroupByRecord) Toggles the expansion state of a group.
getGroup(field: string, value: any) Gets a group record by its composite key.
toggleAllGroupRows() Toggles the expansion state of all group rows recursively.

IgxColumnComponent

Inputs

Inputs available on the IgxGridColumnComponent to define columns:

Name Type Description
field string Column field name
header string Column header text
sortable boolean Set column to be sorted or not
editable boolean Set column values to be editable
filterable boolean Set column values to be filterable
hasSummary boolean Sets whether or not the specific column has summaries enabled.
summaries IgxSummaryOperand Set custom summary for the specific column
hidden boolean Visibility of the column
movable boolean Column moving
resizable boolean Set column to be resizable
width string Columns width
minWidth string Columns minimal width
maxWidth string Columns miximum width
headerClasses string Additional CSS classes applied to the header element.
cellClasses string Additional CSS classes applied to the cells in this column.
formatter Function A function used to "template" the values of the cells without the need to pass a cell template the column.
index string Column index
filteringIgnoreCase boolean Ignore capitalization of strings when filtering is applied. Defaults to true.
sortingIgnoreCase boolean Ignore capitalization of strings when sorting is applied. Defaults to true.
dataType DataType One of string, number, boolean or Date. When filtering is enabled the filter UI conditions are based on the dataType of the column. Defaults to string if it is not provided. With autoGenerate enabled the grid will try to resolve the correct data type for each column based on the data source.
pinned boolean Set column to be pinned or not
groupable boolean Determines whether the column may be grouped via the UI.

Methods

Here is a list of all public methods exposed by IgxGridColumnComponent:

Signature Description
pin(): boolean Pins the column. Returns if the operation is successful.
unpin(): boolean Unpins the column. Returns if the operation is successful.

Getters/Setters

Name Type Getter Setter Description
bodyTemplate TemplateRef Yes Yes Get/Set a reference to a template which will be applied to the cells in the column.
headerTemplate TemplateRef Yes Yes Get/Set a reference to a template which will be applied to the column header.
footerTemplate TemplateRef Yes Yes Get/Set a reference to a template which will be applied to the column footer.
inlineEditorTemplate TemplateRef Yes Yes Get/Set a reference to a template which will be applied as a cell enters edit mode.

Filtering Conditions

Five filtering operand classes are available:

  • IgxFilteringOperand is a base filtering operand, which can be inherited when defining custom filtering conditions.
  • IgxBooleanFilteringOperand defines all default filtering conditions for boolean type.
  • IgxDateFilteringOperand defines all default filtering conditions for Date type.
  • IgxNumberFilteringOperand defines all default filtering conditions for numeric type.
  • IgxStringFilteringOperand defines all default filtering conditions for string type.
import {
    IgxBooleanFilteringOperand,
    IgxDateFilteringOperand,
    IgxFilteringOperand,
    IgxNumberFilteringOperand,
    IgxStringFilteringOperand,
} from 'igniteui-angular';
public filter(term) {
    this.grid.filter("ProductName", term, IgxStringFilteringOperand.instance().condition("contains"));
}

String types

Name Signature Description
contains (target: string, searchVal: string, ignoreCase?: boolean) Returns true if the target contains the searchVal.
startsWith (target: string, searchVal: string, ignoreCase?: boolean) Returns true if the target starts with the searchVal.
endsWith (target: string, searchVal: string, ignoreCase?: boolean) Returns true if the target ends with the searchVal.
doesNotContain (target: string, searchVal: string, ignoreCase?: boolean) Returns true if searchVal is not in target.
equals (target: string, searchVal: string, ignoreCase?: boolean) Returns true if searchVal matches target.
doesNotEqual (target: string, searchVal: string, ignoreCase?: boolean) Returns true if searchVal does not match target.
null (target: any) Returns true if target is null.
notNull (target: any) Returns true if target is not null.
empty (target: any) Returns true if target is either null, undefined or a string of length 0.
notEmpty (target: any) Returns true if target is not null, undefined or a string of length 0.

Number types

Name Signature Description
equals (target: number, searchVal: number) Returns true if target equals searchVal.
doesNotEqual (target: number, searchVal: number) Returns true if target is not equal to searchVal.
doesNotEqual (target: number, searchVal: number) Returns true if target is greater than searchVal.
lessThan (target: number, searchVal: number) Returns true if target is less than searchVal.
greaterThanOrEqualTo (target: number, searchVal: number) Returns true if target is greater than or equal to searchVal.
lessThanOrEqualTo (target: number, searchVal: number) Returns true if target is less than or equal to searchVal.
null (target: any) Returns true if target is null.
notNull (target: any) Returns true if target is not null.
empty (target: any) Returns true if target is either null, undefined or NaN.
notEmpty (target: any) Returns true if target is not null, undefined or NaN.

Boolean types

Name Signature Description
all (target: boolean) Returns all rows.
true (target: boolean) Returns if target is truthy.
false (target: boolean) Returns true if target is falsy.
null (target: any) Returns true if target is null.
notNull (target: any) Returns true if target is not null.
empty (target: any) Returns true if target is either null or undefined.
notEmpty (target: any) Returns true if target is not null or undefined.

Date types

Name Signature Description
equals (target: Date, searchVal: Date) Returns true if target equals searchVal.
doesNotEqual (target: Date, searchVal: Date) Returns true if target does not equal searchVal.
before (target: Date, searchVal: Date) Returns true if target is earlier than searchVal.
after (target: Date, searchVal: Date) Returns true if target is after searchVal.
today (target: Date) Returns true if target is the current date.
yesterday (target: Date) Returns true if target is the day before the current date.
thisMonth (target: Date) Returns true if target is contained in the current month.
lastMonth (target: Date) Returns true if target is contained in the month before the current month.
nextMonth (target: Date) Returns true if target is contained in the month following the current month.
thisYear (target: Date) Returns true if target is contained in the current year.
lastYear (target: Date) Returns true if target is contained in the year before the current year.
nextYear (target: Date) Returns true if target is contained in the year following the current year.
null (target: any) Returns true if target is null.
notNull (target: any) Returns true if target is not null.
empty (target: any) Returns true if target is either null or undefined.
notEmpty (target: any) Returns true if target is not null or undefined.

IgxGridRowComponent

Getters/Setters

Name Type Getter Setter Description
rowData Array Yes No The data passed to the row component.
index number Yes No The index of the row.
cells QueryList Yes No The rendered cells in the row component.
grid IgxGridComponent Yes No A reference to the grid containing the row.
nativeElement HTMLElement Yes No The native DOM element representing the row. Could be null in certain environments.

Methods

Signature Description
update(value: any) Updates the specified row object and the data source record with the passed value. This method emits onEditDone event.
delete() Removes the specified row from the grid's data source. This method emits onRowDeleted event.

IgxGridCellComponent

Getters/Setters

Name Type Getter Setter Description
column IgxColumnComponent Yes No The column to which the cell belongs.
row IgxGridRowComponent Yes No The row to which the cell belongs.
value any Yes No The value in the cell.
rowIndex number Yes No The index of the row this cell belongs to.
columnIndex number Yes No The index of the column this cell belongs to.
grid IgxGridComponent Yes No The grid component itself.
inEditMode boolean Yes Yes Gets/Sets the cell in edit mode.
nativeElement HTMLElement Yes No The native DOM element representing the cell. Could be null in certain environments.

Methods

Name Return Type Description
update(val: any) void Emits the onEditDone event and updates the appropriate record in the data source.

Additional Resources

Our community is active and always welcoming to new ideas.