Infinite scroll in React TreeGrid

8 Oct 202513 minutes to read

Infinite scrolling loads large data sets without degrading TreeGrid performance. This feature uses lazy loading, buffer data is fetched only when the scrollbar reaches the end of the scroller.
To enable Infinite scrolling, set the enableInfiniteScrolling property to true and inject the InfiniteScroll module in the TreeGrid.

  • In this feature, TreeGrid does not make a new data request when the same page is revisited.
import { TreeGridComponent, ColumnsDirective, ColumnDirective, Inject, InfiniteScroll } from '@syncfusion/ej2-react-treegrid';
import * as React from 'react';
import { dataSource, virtualData } from './datasource';
function App() {
    dataSource();
    return <TreeGridComponent dataSource={virtualData} childMapping='Crew' enableInfiniteScrolling={true} treeColumnIndex={1} height='291'>
        <ColumnsDirective>
            <ColumnDirective field='TaskID' headerText='Player Jersey' width='120' textAlign='Right'></ColumnDirective>
            <ColumnDirective field='FIELD1' headerText='Player Name' width='120'></ColumnDirective>
            <ColumnDirective field='FIELD2' headerText='Year' width='100' textAlign='Right'></ColumnDirective>
            <ColumnDirective field='FIELD3' headerText='Stint' width='120' textAlign='Right'></ColumnDirective>
            <ColumnDirective field='FIELD4' headerText='TMID' width='120' textAlign='Right'></ColumnDirective>
        </ColumnsDirective>
            <Inject services={[InfiniteScroll]}/>
    </TreeGridComponent>;
}
;
export default App;
import { TreeGridComponent, ColumnsDirective, ColumnDirective, Inject, InfiniteScroll } from '@syncfusion/ej2-react-treegrid';
import * as React from 'react';
import { dataSource, virtualData } from './datasource';

function App() {
    dataSource();
    return <TreeGridComponent dataSource={virtualData} childMapping = 'Crew' enableInfiniteScrolling={true} treeColumnIndex={1} height='291'>
        <ColumnsDirective>
            <ColumnDirective field='TaskID' headerText='Player Jersey' width='120' textAlign='Right'></ColumnDirective>
            <ColumnDirective field='FIELD1' headerText='Player Name' width='120'></ColumnDirective>
            <ColumnDirective field='FIELD2' headerText='Year' width='100' textAlign='Right'></ColumnDirective>
            <ColumnDirective field='FIELD3' headerText='Stint' width='120' textAlign='Right'></ColumnDirective>
            <ColumnDirective field='FIELD4' headerText='TMID' width='120' textAlign='Right'></ColumnDirective>
        </ColumnsDirective>
            <Inject services={[InfiniteScroll]} />
    </TreeGridComponent>
};
export default App;

InitialBlocks

Define the number of pages loaded initially using the infiniteScrollSettings.initialBlocks property. By default, three pages load during initial rendering.
In the demo below, this property is configured to load five pages instead of three.

import { TreeGridComponent, ColumnsDirective, ColumnDirective, Inject, InfiniteScroll } from '@syncfusion/ej2-react-treegrid';
import * as React from 'react';
import { dataSource, virtualData } from './datasource';
function App() {
    const pageSettings = { pageSize: 50 };
    const infiniteOptions = { initialBlocks: 5 };
    dataSource();
    return <TreeGridComponent dataSource={virtualData} childMapping='Crew' height={300} enableInfiniteScrolling={true} infiniteScrollSettings={infiniteOptions} pageSettings={pageSettings} treeColumnIndex={1}>
            <Inject services={[InfiniteScroll]}/>
            <ColumnsDirective>
                <ColumnDirective field='TaskID' headerText='Player Jersey' width='120' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD1' headerText='Player Name' width='120'></ColumnDirective>
                <ColumnDirective field='FIELD2' headerText='Year' width='100' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD3' headerText='Stint' width='120' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD4' headerText='TMID' width='120' textAlign='Right'></ColumnDirective>
            </ColumnsDirective>
            </TreeGridComponent>;
}
;
export default App;
import { TreeGridComponent, ColumnsDirective, ColumnDirective, Inject, InfiniteScroll, InfiniteScrollSettingsModel, PageSettingsModel } from '@syncfusion/ej2-react-treegrid';
import * as React from 'react';
import { dataSource, virtualData } from './datasource';

function App() {
  const pageSettings: PageSettingsModel = { pageSize: 50 };
  const infiniteOptions: InfiniteScrollSettingsModel = { initialBlocks: 5 };
    dataSource();
    return <TreeGridComponent dataSource={virtualData} childMapping = 'Crew' height={300} enableInfiniteScrolling={true} infiniteScrollSettings={ infiniteOptions } pageSettings={ pageSettings } treeColumnIndex={1}>
            <Inject services={[InfiniteScroll]} />
            <ColumnsDirective>
                <ColumnDirective field='TaskID' headerText='Player Jersey' width='120' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD1' headerText='Player Name' width='120'></ColumnDirective>
                <ColumnDirective field='FIELD2' headerText='Year' width='100' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD3' headerText='Stint' width='120' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD4' headerText='TMID' width='120' textAlign='Right'></ColumnDirective>
            </ColumnsDirective>
            </TreeGridComponent>
};
export default App;

Cache Mode

Cache mode stores loaded row objects in the TreeGrid instance and reuses them to create row elements when scrolling back to previously visited pages. This mode maintains row elements based on the infiniteScrollSettings.maxBlocks value; after the limit is exceeded, older row elements are removed from the DOM to accommodate new rows.
To enable cache mode in Infinite scrolling, set the infiniteScrollSettings.enableCache property to true.

import { TreeGridComponent, ColumnsDirective, ColumnDirective, Inject, InfiniteScroll } from '@syncfusion/ej2-react-treegrid';
import * as React from 'react';
import { dataSource, virtualData } from './datasource';
function App() {
    const pageSettings = { pageSize: 50 };
    const infiniteOptions = { enableCache: true };
    dataSource();
    return <TreeGridComponent dataSource={virtualData} childMapping='Crew' height={300} enableInfiniteScrolling={true} infiniteScrollSettings={infiniteOptions} pageSettings={pageSettings} treeColumnIndex={1}>
            <Inject services={[InfiniteScroll]}/>
            <ColumnsDirective>
                <ColumnDirective field='TaskID' headerText='Player Jersey' width='120' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD1' headerText='Player Name' width='120'></ColumnDirective>
                <ColumnDirective field='FIELD2' headerText='Year' width='100' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD3' headerText='Stint' width='120' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD4' headerText='TMID' width='120' textAlign='Right'></ColumnDirective>
            </ColumnsDirective>
          </TreeGridComponent>;
}
;
export default App;
import { TreeGridComponent, ColumnsDirective, ColumnDirective, Inject, InfiniteScroll, InfiniteScrollSettingsModel, PageSettingsModel } from '@syncfusion/ej2-react-treegrid';
import * as React from 'react';
import { dataSource, virtualData } from './datasource';

function App() {
  const pageSettings: PageSettingsModel = { pageSize: 50 };
  const infiniteOptions: InfiniteScrollSettingsModel = { enableCache: true };
    dataSource();
    return <TreeGridComponent dataSource={virtualData} childMapping = 'Crew' height={300} enableInfiniteScrolling={true} infiniteScrollSettings={ infiniteOptions } pageSettings={ pageSettings } treeColumnIndex={1}>
            <Inject services={[InfiniteScroll]} />
            <ColumnsDirective>
                <ColumnDirective field='TaskID' headerText='Player Jersey' width='120' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD1' headerText='Player Name' width='120'></ColumnDirective>
                <ColumnDirective field='FIELD2' headerText='Year' width='100' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD3' headerText='Stint' width='120' textAlign='Right'></ColumnDirective>
                <ColumnDirective field='FIELD4' headerText='TMID' width='120' textAlign='Right'></ColumnDirective>
            </ColumnsDirective>
          </TreeGridComponent>
};
export default App;

Limitations for Infinite Scrolling

  • Due to browser element height limitations, the maximum number of records loaded by the TreeGrid is constrained by browser capabilities.
  • The total height of initially loaded rows must exceed the viewport height.
  • Cell selection is not persisted in cache mode.
  • Infinite scrolling is not compatible with batch editing, cell editing, and detail template.
  • Aggregates and total group items reflect only the current view items. To compute across all items regardless of view, refer to the corresponding aggregate documentation.
  • Programmatic selection using the selectRows and selectRow methods is not supported with Infinite scrolling.
  • Infinite scrolling does not support rendering records in a collapsed state. All records must be fully expanded at initial rendering.

Refer to the React TreeGrid feature tour page for feature highlights. Explore the React TreeGrid example to learn how to present and manipulate data.