Search results

Immutable Mode in JavaScript (ES5) TreeGrid control

29 Jul 2021 / 3 minutes to read

The immutable mode optimizes the Tree Grid re-rendering performance by using the object reference and deep compare concept. When performing the Tree Grid actions, it will only re-render the modified or newly added rows and prevent the re-rendering of the unchanged rows.

To enable this feature, you have to set the enableImmutableMode property as true.

  • This feature uses the primary key value for data comparison. So, you need to provide the isPrimaryKey column.
Source
Preview
index.js
index.html
Copied to clipboard
ej.treegrid.TreeGrid.Inject(ej.treegrid.Page, ej.treegrid.Edit);

var immutableStart;
var normalStart;
var immutableInit = true;
var init = true;
if(sampleData2.length == 0){
  dataSource();
}
    
    var immutableGrid = new ej.treegrid.TreeGrid(
        {
            dataSource: sampleData2,
            childMapping: 'subtasks',
            height: 350,
            allowPaging: true,
            pageSettings: {pageSize: 50},
            selectionSettings: { type: "Multiple" },
            editSettings: { allowEditing: true, allowAdding: true, allowDeleting: true, mode: 'Cell' },
            treeColumnIndex: 1,
            enableImmutableMode: true,
            beforeDataBound: function() {
                immutableStart = new Date().getTime();
            },
            dataBound: function() {
                var val = immutableInit ? '' : new Date().getTime() - immutableStart;
                document.getElementById('immutableDelete').innerHTML = 'Immutable rendering Time: ' + "<b>" + val + "</b>" + '<b>ms</b>';
                immutableStart = 0; immutableInit = false;
            },
            columns: [
                { field: 'taskID', headerText: 'Task ID', isPrimaryKey: true, width: 70, textAlign: 'Right' },
                { field: 'taskName', headerText: 'Task Name', width: 200, textAlign: 'Left' },
                { field: 'startDate', headerText: 'Start Date', width: 90, textAlign: 'Right', type: 'date', format: 'yMd' },
                { field: 'endDate', headerText: 'End Date', width: 90, textAlign: 'Right', type: 'date', format: 'yMd' },
                { field: 'duration', headerText: 'Duration', width: 80, textAlign: 'Right' },
                { field: 'progress', headerText: 'Progress', width: 80, textAlign: 'Right' },
                { field: 'priority', headerText: 'Priority', width: 90 }
            ]
        });
    immutableGrid.appendTo('#immutable');

    
document.getElementById('delete').addEventListener('click', function(e) {
  normalGrid.selectRows([0, 2, 4]);
  immutableGrid.selectRows([0, 2, 4]);
  normalGrid.deleteRecord();
  immutableGrid.deleteRecord();
});

document.getElementById('addtop').addEventListener('click', function(e) {
  normalGrid.addRecord(sampleData[0], 0, "Top");
  immutableGrid.addRecord(sampleData[0], 0, "Top");
});

document.getElementById('addbottom').addEventListener('click', function(e) {
  normalGrid.addRecord(sampleData[0], 0, "Bottom");
  immutableGrid.addRecord(sampleData[0], 0, "Bottom");
});

document.getElementById('reverse').addEventListener('click', function(e) {
  let aData = (immutableGrid.dataSource).reverse();
  normalGrid.setProperties({ dataSource: aData });
  immutableGrid.setProperties({ dataSource: aData });
});

document.getElementById('paging').addEventListener('click', function(e) {
  let page = normalGrid.pageSettings.currentPage + 1;
  normalGrid.goToPage(page);
  immutableGrid.goToPage(page);
});

var normalGrid = new ej.treegrid.TreeGrid({
            dataSource: sampleData2,
            childMapping: 'subtasks',
            height: 350,
            allowPaging: true,
            pageSettings: {pageSize: 50},
            selectionSettings: { type: "Multiple" },
            editSettings: { allowEditing: true, allowAdding: true, allowDeleting: true, mode: 'Cell' },
            treeColumnIndex: 1,
            beforeDataBound: function() {
                normalStart = new Date().getTime();
            },
            dataBound: function() {
                var val = init ? '' : new Date().getTime() - normalStart;
                document.getElementById('normalDelete').innerHTML = 'Normal rendering Time: ' + "<b>" + val + "</b>" + '<b>ms</b>';
                normalStart = 0; init = false;
            },
            columns: [
                { field: 'taskID', headerText: 'Task ID',  isPrimaryKey: true, width: 70, textAlign: 'Right' },
                { field: 'taskName', headerText: 'Task Name', width: 200, textAlign: 'Left' },
                { field: 'startDate', headerText: 'Start Date', width: 90, textAlign: 'Right', type: 'date', format: 'yMd' },
                { field: 'endDate', headerText: 'End Date', width: 90, textAlign: 'Right', type: 'date', format: 'yMd' },
                { field: 'duration', headerText: 'Duration', width: 80, textAlign: 'Right' },
                { field: 'progress', headerText: 'Progress', width: 80, textAlign: 'Right' },
                { field: 'priority', headerText: 'Priority', width: 90 }
            ]
});
normalGrid.appendTo('#normal');
Copied to clipboard
<!DOCTYPE html><html lang="en"><head>
    <title>EJ2 Tree Grid</title>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta name="description" content="Typescript Tree Grid Control">
    <meta name="author" content="Syncfusion">
    <link href="index.css" rel="stylesheet">
     <!-- Syncfusion Essential JS 2 Styles -->
    <link rel="stylesheet" href="https://cdn.syncfusion.com/ej2/material.css">
    
    
<style>
    .immutablegrid,
    .normalgrid {
        pointer-events: none;
    }
</style><script src="https://cdn.syncfusion.com/ej2/dist/ej2.min.js" type="text/javascript"></script>
<script src="es5-datasource.js" type="text/javascript"></script>
</head>

<body>
   
    <div id="container">
        <table>
            <tbody>
                <tr>
                    <td>
                        <span id="immutableDelete"></span>
                    </td>
                </tr>
                <tr>
                    <td>
                        <span id="normalDelete"></span>
                    </td>
                </tr>
                <tr>
                    <td>
                        <div>
                            <button id="addtop" class="e-control e-btn e-lib e-info">Add row at top</button>
                            <button id="addbottom" class="e-control e-btn e-lib e-info">Add row at bottom</button>
                            <button id="delete" class="e-control e-btn e-lib e-info">Delete 5 rows</button>
                            <button id="reverse" class="e-control e-btn e-lib e-info">Sort Task ID</button>
                            <button id="paging" class="e-control e-btn e-lib e-info">Paging</button>
                        </div>
                    </td>
                </tr>
                <tr>
                    <td>
                        <span><b>Immutable Tree Grid</b></span>
                        <div id="immutable" class="immutablegrid"></div>
                    </td>
                    <td>
                        <span><b>Normal Tree Grid</b></span>
                        <div id="normal" class="normalgrid"></div>
                    </td>
                </tr>
            </tbody>
        </table>
    </div>  

<script>
var ele = document.getElementById('container');
if(ele) {
    ele.style.visibility = "visible";
 }   
        </script>
<script src="index.js" type="text/javascript"></script>
</body></html>

Limitations

The following features are not supported in the immutable mode:

  • Frozen rows and columns
  • Row Template
  • Detail Template
  • Column reorder
  • Virtualization