Detail template in EJ2 TypeScript Grid control

1 Dec 202324 minutes to read

The detail template in the Grid control allows you to display additional information about a specific row in the grid by expanding or collapsing detail content. This feature is useful when you need to show additional data or custom content that is specific to each row in the grid. You can use the detailTemplate property to define an HTML template for the detail row. This template can include any HTML element or EJ2 TypeScript control that you want to display as detail content.

Here’s an example of using the detailTemplate property in the grid control:

import { Grid, DetailRow } from '@syncfusion/ej2-grids';
import { employeeData } from './datasource.ts';

Grid.Inject(DetailRow);

let grid: Grid = new Grid({
    dataSource: employeeData,
    detailTemplate: '#detailtemplate',
    columns: [
        { field: 'FirstName', headerText: 'First Name', width: 140 },
        { field: 'LastName', headerText: 'Last Name', width: 140 },
        { field: 'Title', headerText: 'Title', width: 150 },
        { field: 'Country', headerText: 'Country', width: 150 }
    ],
    height: 315
});
grid.appendTo('#Grid');
<!DOCTYPE html>
<html lang="en">
<head>
    <title>EJ2 Grid</title>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta name="description" content="Typescript Grid Control" />
    <meta name="author" content="Syncfusion" />
    <link href="index.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-base/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-buttons/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-popups/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-navigations/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-dropdowns/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-lists/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-inputs/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-calendars/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-splitbuttons/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-grids/styles/material.css" rel="stylesheet" />
    <script src="https://cdnjs.cloudflare.com/ajax/libs/systemjs/0.19.38/system.js"></script>
    <script src="systemjs.config.js"></script>
<script src="https://cdn.syncfusion.com/ej2/syncfusion-helper.js" type ="text/javascript"></script>
</head>
<body>
  <script id='detailtemplate' type="text/x-template">
    <table class="detailtable" width="100%" >
        <colgroup>
            <col width="35%">
            <col width="35%">
            <col width="30%">
        </colgroup>
        <tbody>
            <tr>
                <td rowspan="4" style="text-align: center;">
                    <img class='photo' src="${EmployeeID}.png" alt="${EmployeeID}" />
                </td>
                <td>
                    <span style="font-weight: 500;">First Name: </span> ${FirstName}
                </td>
                <td>
                    <span style="font-weight: 500;">Postal Code: </span> ${PostalCode}
                </td>
            </tr>
            <tr>                  
                <td>
                    <span style="font-weight: 500;">Last Name: </span> ${LastName}
                </td>
                <td>
                    <span style="font-weight: 500;">City: </span> ${City}
                </td>
            </tr>
            <tr>
                <td>
                    <span style="font-weight: 500;">Title: </span> ${Title}
                </td>
                <td>
                    <span style="font-weight: 500;">Phone: </span> ${HomePhone}
                </td>          
            </tr>
            <tr>
                <td>
                    <span style="font-weight: 500;">City: </span> ${City}
                </td>
                <td>
                     <span style="font-weight: 500;">Country: </span> ${Country}
                </td>
            </tr>  
        </tbody>
    </table>
  </script>  
    <div id='loader'>Loading....</div>
    <div id='container'>
        <div id='Grid'></div>        
    </div>
</body>
</html>

Rendering custom control

The Grid control provides a powerful feature that allows you to render custom controls inside the detail row. This feature is helpful when you need to add additional information or functionality for a specific row in the grid.

To render a custom control inside the detail row, you need to define a template using the detailTemplate property and handle the detailDataBound event. This template can include any HTML element or EJ2 TypeScript control that you want to display as the detail content.

The detailDataBound event is an event that is triggered after a detail row is bound to data. This event provides an object of type DetailDataBoundEventArgs as a parameter.

For example, to render grid inside the detail row, place an HTML div element as the detailTemplate and render the DIV element as grid control in the detailDataBound event.

import { Grid, DetailRow, DetailDataBoundEventArgs } from '@syncfusion/ej2-grids';
import { employeeData, data } from './datasource.ts';

Grid.Inject(DetailRow);

let grid: Grid = new Grid({
    dataSource: employeeData,
    detailTemplate: '#detailtemplate',
    columns: [
        { field: 'FirstName', headerText: 'First Name', width: 140 },
        { field: 'LastName', headerText: 'Last Name', width: 140 },
        { field: 'Title', headerText: 'Title', width: 150 },
        { field: 'Country', headerText: 'Country', width: 150 }
    ],
    detailDataBound: (e: DetailDataBoundEventArgs) => {
        let detail = new Grid({
            dataSource: data.filter((item: Object) => item['EmployeeID'] === e.data['EmployeeID']),
            columns: [
                { field: 'OrderID', headerText: 'Order ID', width: 110 },
                { field: 'CustomerID', headerText: 'Customer Name', width: 140 },
                { field: 'ShipCountry', headerText: 'Ship Country', width: 150 }
            ]
        });
        detail.appendTo(<HTMLElement>e.detailElement.querySelector('.custom-grid'));
    }
});
grid.appendTo('#Grid');
<!DOCTYPE html>
<html lang="en">
<head>
    <title>EJ2 Grid</title>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta name="description" content="Typescript Grid Control" />
    <meta name="author" content="Syncfusion" />
    <link href="index.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-base/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-grids/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-buttons/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-popups/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-navigations/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-dropdowns/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-lists/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-inputs/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-calendars/styles/material.css" rel="stylesheet" /> 
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-splitbuttons/styles/material.css" rel="stylesheet" />  
    <script src="https://cdnjs.cloudflare.com/ajax/libs/systemjs/0.19.38/system.js"></script>
    <script src="systemjs.config.js"></script>
<script src="https://cdn.syncfusion.com/ej2/syncfusion-helper.js" type ="text/javascript"></script>
</head>
<body>
  <script id='detailtemplate' type="text/x-template">
    <div class='custom-grid'></div>
  </script>  
    <div id='loader'>Loading....</div>
    <div id='container'>    
        <div id='Grid'></div>        
    </div>
</body>
</html>

Expand by external button

The Grid provides a feature that allows users to expand the detail row of a grid using an external button. By default, detail rows render in a collapsed state, but this feature enables users to view additional details associated with a particular row.

To achieve expanding the detail row of a grid using an external button, you need to invoke the expand method provided by the detailRowModule object of the Syncfusion Grid library. This method will expand the detail row of a specific grid row.
Here is an example of how to use the expand method to expand a detail row:

import { Grid, DetailRow } from '@syncfusion/ej2-grids';
import { Button } from '@syncfusion/ej2-buttons';
import { employeeData } from './datasource.ts';
import { TextBox } from '@syncfusion/ej2-inputs';

Grid.Inject(DetailRow);

let grid: Grid = new Grid({
    dataSource: employeeData,
    detailTemplate: '#detailtemplate',
    columns: [
        { field: 'FirstName', headerText: 'First Name', width: 140 },
        { field: 'LastName', headerText: 'Last Name', width: 140 },
        { field: 'Title', headerText: 'Title', width: 150 },
        { field: 'Country', headerText: 'Country', width: 150 }
    ],
    height: 260
});
grid.appendTo('#Grid');

let expandButton: Button = new Button();
expandButton.appendTo('#expand');

let textbox: TextBox = new TextBox({
    placeholder: 'Enter the Row Index',
    floatLabelType: 'Auto',
    width: 250
});
textbox.appendTo('#rowindex');

(document.getElementById('expand')as HTMLElement).addEventListener('click', () => {
    grid.detailRowModule.expand(textbox.value); 
});
<!DOCTYPE html>
<html lang="en">
<head>
    <title>EJ2 Grid</title>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta name="description" content="Typescript Grid Control" />
    <meta name="author" content="Syncfusion" />
    <link href="index.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-base/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-grids/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-buttons/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-popups/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-navigations/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-dropdowns/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-lists/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-inputs/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-calendars/styles/material.css" rel="stylesheet" />  
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-splitbuttons/styles/material.css" rel="stylesheet" />
    <script src="https://cdnjs.cloudflare.com/ajax/libs/systemjs/0.19.38/system.js"></script>
    <script src="systemjs.config.js"></script>
<script src="https://cdn.syncfusion.com/ej2/syncfusion-helper.js" type ="text/javascript"></script>
</head>
<body>
  <script id='detailtemplate' type='text/x-template'>
    <table class="detailtable" width="100%" >
        <colgroup>
            <col width="35%">
            <col width="35%">
            <col width="30%">
        </colgroup>
        <tbody>
            <tr>
                <td rowspan="4" style="text-align: center;">
                    <img class='photo' src="${EmployeeID}.png" alt="${EmployeeID}" />
                </td>
                <td>
                    <span style="font-weight: 500;">First Name: </span> ${FirstName}
                </td>
                <td>
                    <span style="font-weight: 500;">Postal Code: </span> ${PostalCode}
                </td>
            </tr>
            <tr>                  
                <td>
                    <span style="font-weight: 500;">Last Name: </span> ${LastName}
                </td>
                <td>
                    <span style="font-weight: 500;">City: </span> ${City}
                </td>
            </tr>
            <tr>
                <td>
                    <span style="font-weight: 500;">Title: </span> ${Title}
                </td>
                <td>
                    <span style="font-weight: 500;">Phone: </span> ${HomePhone}
                </td>          
            </tr>
            <tr>
                <td>
                    <span style="font-weight: 500;">City: </span> ${City}
                </td>
                <td>
                     <span style="font-weight: 500;">Country: </span> ${Country}
                </td>
            </tr>  
        </tbody>
    </table>
  </script>  
    <div id='loader'>Loading....</div>
    <div id='container'>
        <div class="e-float-input" style="width: 250px; display: inline-block ;padding: 0px 30px 0px 0px">
            <input id="rowindex" type="text" />
            <span class="e-float-line"></span>
          </div>
          <button id="expand">Expand</button>     
        <div id='Grid'></div>        
    </div>
</body>
</html>

Customize detail template icon

The detail template icon in the Syncfusion Grid is used to expand or collapse the detail content of a row. By default, the icon represents a right arrow for the collapsed state and a down arrow for the expanded state. If you want to customize this icon, you can achieve it by overriding the following CSS styles:

.e-grid .e-icon-grightarrow::before {
          content: '\e300';
}

.e-grid .e-icon-gdownarrow::before {
          content: '\e304';
}

Here is an example of how to customize the detail template icon:

import { Grid, DetailRow } from '@syncfusion/ej2-grids';
import { employeeData } from './datasource.ts';

Grid.Inject(DetailRow);

let grid: Grid = new Grid({
    dataSource: employeeData,
    detailTemplate: '#detailtemplate',
    columns: [
        { field: 'FirstName', headerText: 'First Name', width: 140 },
        { field: 'LastName', headerText: 'Last Name', width: 140 },
        { field: 'Title', headerText: 'Title', width: 150 },
        { field: 'Country', headerText: 'Country', width: 150 }
    ],
    height: 315
});
grid.appendTo('#Grid');
<!DOCTYPE html>
<html lang="en">
<head>
    <title>EJ2 Grid</title>
    <meta charset="utf-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta name="description" content="Typescript Grid Control" />
    <meta name="author" content="Syncfusion" />
    <link href="index.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-base/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-buttons/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-popups/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-navigations/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-dropdowns/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-lists/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-inputs/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-calendars/styles/material.css" rel="stylesheet" /> 
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-splitbuttons/styles/material.css" rel="stylesheet" />
    <link href="https://cdn.syncfusion.com/ej2/25.1.35/ej2-grids/styles/material.css" rel="stylesheet" />
    <script src="https://cdnjs.cloudflare.com/ajax/libs/systemjs/0.19.38/system.js"></script>
    <script src="systemjs.config.js"></script>
    <style>
         .e-grid .e-icon-grightarrow::before {
          content: '\e300';
        }

        .e-grid .e-icon-gdownarrow::before {
          content: '\e304';
        }
    </style>
<script src="https://cdn.syncfusion.com/ej2/syncfusion-helper.js" type ="text/javascript"></script>
</head>
<body>
  <script id='detailtemplate' type="text/x-template">
    <table class="detailtable" width="100%" >
        <colgroup>
            <col width="35%">
            <col width="35%">
            <col width="30%">
        </colgroup>
        <tbody>
            <tr>
                <td rowspan="4" style="text-align: center;">
                    <img class='photo' src="${EmployeeID}.png" alt="${EmployeeID}" />
                </td>
                <td>
                    <span style="font-weight: 500;">First Name: </span> ${FirstName}
                </td>
                <td>
                    <span style="font-weight: 500;">Postal Code: </span> ${PostalCode}
                </td>
            </tr>
            <tr>                  
                <td>
                    <span style="font-weight: 500;">Last Name: </span> ${LastName}
                </td>
                <td>
                    <span style="font-weight: 500;">City: </span> ${City}
                </td>
            </tr>
            <tr>
                <td>
                    <span style="font-weight: 500;">Title: </span> ${Title}
                </td>
                <td>
                    <span style="font-weight: 500;">Phone: </span> ${HomePhone}
                </td>          
            </tr>
            <tr>
                <td>
                    <span style="font-weight: 500;">City: </span> ${City}
                </td>
                <td>
                     <span style="font-weight: 500;">Country: </span> ${Country}
                </td>
            </tr>  
        </tbody>
    </table>
  </script>  
    <div id='loader'>Loading....</div>
    <div id='container'>
        <div id='Grid'></div>        
    </div>
</body>
</html>

Limitations

Detail template is not supported with the following features:

  • Frozen rows and columns
  • Immutable mode
  • Infinite scrolling
  • Virtual scrolling
  • Print
  • Row template
  • Row spanning
  • Column spanning
  • Lazy load grouping
  • State persistence