Skip to content

Commit

Permalink
[DataGrid] Dynamic virtualization range (#12353)
Browse files Browse the repository at this point in the history
Signed-off-by: Rom Grk <romgrk@users.noreply.github.com>
Co-authored-by: Andrew Cherniavskii <andrew.cherniavskii@gmail.com>
  • Loading branch information
romgrk and cherniavskii committed Mar 20, 2024
1 parent 6fc1da5 commit 1418ac2
Show file tree
Hide file tree
Showing 50 changed files with 428 additions and 345 deletions.
11 changes: 10 additions & 1 deletion docs/data/data-grid/column-dimensions/ColumnAutosizingAsync.js
Original file line number Diff line number Diff line change
Expand Up @@ -60,11 +60,14 @@ export default function ColumnAutosizingAsync() {
setIsLoading(true);
getFakeData(100)
.then((data) => {
return ReactDOM.flushSync(() => {
ReactDOM.flushSync(() => {
setIsLoading(false);
apiRef.current.updateRows(data.rows);
});
})
// `sleep`/`setTimeout` is required because `.updateRows` is an
// async function throttled to avoid choking on frequent changes.
.then(() => sleep(0))
.then(() =>
apiRef.current.autosizeColumns({
includeHeaders: true,
Expand Down Expand Up @@ -103,3 +106,9 @@ export default function ColumnAutosizingAsync() {
</div>
);
}

function sleep(ms) {
return new Promise((resolve) => {
setTimeout(resolve, ms);
});
}
11 changes: 10 additions & 1 deletion docs/data/data-grid/column-dimensions/ColumnAutosizingAsync.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -60,11 +60,14 @@ export default function ColumnAutosizingAsync() {
setIsLoading(true);
getFakeData(100)
.then((data) => {
return ReactDOM.flushSync(() => {
ReactDOM.flushSync(() => {
setIsLoading(false);
apiRef.current.updateRows(data.rows);
});
})
// `sleep`/`setTimeout` is required because `.updateRows` is an
// async function throttled to avoid choking on frequent changes.
.then(() => sleep(0))
.then(() =>
apiRef.current.autosizeColumns({
includeHeaders: true,
Expand Down Expand Up @@ -103,3 +106,9 @@ export default function ColumnAutosizingAsync() {
</div>
);
}

function sleep(ms: number) {
return new Promise((resolve) => {
setTimeout(resolve, ms);
});
}
1 change: 0 additions & 1 deletion docs/data/data-grid/demo/FullFeaturedDemo.js
Original file line number Diff line number Diff line change
Expand Up @@ -301,7 +301,6 @@ export default function FullFeaturedDemo() {
loading={loading}
checkboxSelection
disableRowSelectionOnClick
rowThreshold={0}
initialState={{
...data.initialState,
pinnedColumns: { left: [GRID_CHECKBOX_SELECTION_FIELD, 'desk'] },
Expand Down
1 change: 0 additions & 1 deletion docs/data/data-grid/demo/FullFeaturedDemo.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -341,7 +341,6 @@ export default function FullFeaturedDemo() {
loading={loading}
checkboxSelection
disableRowSelectionOnClick
rowThreshold={0}
initialState={{
...data.initialState,
pinnedColumns: { left: [GRID_CHECKBOX_SELECTION_FIELD, 'desk'] },
Expand Down
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/BasicDetailPanels.js
Original file line number Diff line number Diff line change
Expand Up @@ -175,7 +175,6 @@ export default function BasicDetailPanels() {
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
Expand Down
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/BasicDetailPanels.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -177,7 +177,6 @@ export default function BasicDetailPanels() {
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/ControlMasterDetail.js
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,6 @@ export default function ControlMasterDetail() {
<DataGridPro
rows={rows}
columns={columns}
rowThreshold={0}
getDetailPanelContent={({ row }) => (
<Box sx={{ p: 2 }}>{`Order #${row.id}`}</Box>
)}
Expand Down
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/ControlMasterDetail.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,6 @@ export default function ControlMasterDetail() {
<DataGridPro
rows={rows}
columns={columns}
rowThreshold={0}
getDetailPanelContent={({ row }) => (
<Box sx={{ p: 2 }}>{`Order #${row.id}`}</Box>
)}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,6 @@ export default function CustomizeDetailPanelToggle() {
<DataGridPro
rows={rows}
columns={columns}
rowThreshold={0}
getDetailPanelContent={getDetailPanelContent}
getDetailPanelHeight={getDetailPanelHeight}
/>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@ export default function CustomizeDetailPanelToggle() {
<DataGridPro
rows={rows}
columns={columns}
rowThreshold={0}
getDetailPanelContent={getDetailPanelContent}
getDetailPanelHeight={getDetailPanelHeight}
/>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
<DataGridPro
rows={rows}
columns={columns}
rowThreshold={0}
getDetailPanelContent={getDetailPanelContent}
getDetailPanelHeight={getDetailPanelHeight}
/>
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/DetailPanelAutoHeight.js
Original file line number Diff line number Diff line change
Expand Up @@ -228,7 +228,6 @@ export default function DetailPanelAutoHeight() {
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -234,7 +234,6 @@ export default function DetailPanelAutoHeight() {
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/FormDetailPanel.js
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,6 @@ export default function FormDetailPanel() {
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
Expand Down
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/FormDetailPanel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -139,7 +139,6 @@ export default function FormDetailPanel() {
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
/>
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/FullWidthDetailPanel.js
Original file line number Diff line number Diff line change
Expand Up @@ -201,7 +201,6 @@ export default function FullWidthDetailPanel() {
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
pinnedColumns={{ left: [GRID_DETAIL_PANEL_TOGGLE_FIELD] }}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
Expand Down
1 change: 0 additions & 1 deletion docs/data/data-grid/master-detail/FullWidthDetailPanel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -205,7 +205,6 @@ export default function FullWidthDetailPanel() {
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
pinnedColumns={{ left: [GRID_DETAIL_PANEL_TOGGLE_FIELD] }}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
<DataGridPro
columns={columns}
rows={rows}
rowThreshold={0}
pinnedColumns={{ left: [GRID_DETAIL_PANEL_TOGGLE_FIELD] }}
getDetailPanelHeight={getDetailPanelHeight}
getDetailPanelContent={getDetailPanelContent}
Expand Down
9 changes: 0 additions & 9 deletions docs/data/data-grid/master-detail/master-detail.md
Original file line number Diff line number Diff line change
Expand Up @@ -49,15 +49,6 @@ const getDetailPanelContent = React.useCallback(() => { ... }, []);
<DataGridPro getDetailPanelContent={getDetailPanelContent} />
```

Depending on the height of the detail panel, you may see a blank space when scrolling.
This is caused by the data grid using a lazy approach to update the rendered rows.
Set `rowThreshold` to 0 to force new rows to be rendered more often to fill the blank space.
Note that this may reduce the performance.

```tsx
<DataGridPro rowThreshold={0} />
```

:::

## Infer height from the content
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ export default function ColumnVirtualizationGrid() {

return (
<div style={{ height: 400, width: '100%' }}>
<DataGrid {...data} columnBuffer={2} columnThreshold={2} />
<DataGrid {...data} columnBufferPx={100} />
</div>
);
}
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ export default function ColumnVirtualizationGrid() {

return (
<div style={{ height: 400, width: '100%' }}>
<DataGrid {...data} columnBuffer={2} columnThreshold={2} />
<DataGrid {...data} columnBufferPx={100} />
</div>
);
}
Original file line number Diff line number Diff line change
@@ -1 +1 @@
<DataGrid {...data} columnBuffer={2} columnThreshold={2} />
<DataGrid {...data} columnBufferPx={100} />
6 changes: 3 additions & 3 deletions docs/data/data-grid/virtualization/virtualization.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ _\*unlimited: Browsers set a limit on the number of pixels a scroll container ca

Row virtualization is the insertion and removal of rows as the data grid scrolls vertically.

The grid renders twice as many rows as are visible. It isn't configurable yet.
The grid renders some additional rows above and below the visible rows. You can use `rowBufferPx` prop to hint to the Data Grid the area to render, but this value may not be respected in certain situations, for example during high-speed scrolling.
Row virtualization is limited to 100 rows in the `DataGrid` component.

## Column virtualization
Expand All @@ -23,11 +23,11 @@ Column virtualization is the insertion and removal of columns as the data grid s
- Overscanning more allows the built-in search feature of the browser to find more matching cells.
- Overscanning too much can negatively impact performance.

By default, 2 columns are rendered outside of the viewport. You can change this option with the `columnBuffer` prop. The following demo renders 1,000 columns in total:
By default, columns coming under 150 pixels region are rendered outside of the viewport. You can change this option with the `columnBufferPx` prop. As for `rowBufferPx`, the value may be ignored in some situations. The following demo renders 1,000 columns in total:

{{"demo": "ColumnVirtualizationGrid.js", "bg": "inline"}}

You can disable column virtualization by setting the column buffer to a higher number than the number of rendered columns, for example with `columnBuffer={columns.length}` or `columnBuffer={Number.MAX_SAFE_INTEGER}`.
You can disable column virtualization by calling `apiRef.current.unstable_setColumnVirtualization(false)`, or by setting the column buffer to the number of total columns.

## Disable virtualization

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -114,9 +114,10 @@ As a result, the following changes have been made:
- Pinned row and column sections are now contained in the virtual scroller.
- The cell inner wrapper `.MuiDataGrid-cellContent` has been removed.

<!-- ### Renamed props
## Renamed props

- -->
- The props `rowBuffer` and `columnBuffer` were renamed to `rowBufferPx` and `columnBufferPx`.
Their value is now a pixel value rather than a number of items. Their default value is now `150`.

### Removed props

Expand All @@ -143,6 +144,8 @@ As a result, the following changes have been made:
};
```

- The props `rowThreshold` and `columnThreshold` have been removed.
If you had the `rowThreshold` prop set to `0` to force new rows to be rendered more often – this is no longer necessary.
- ✅ Some feature flags were removed from the `experimentalFeatures` prop. These features are now stable and enabled by default:
- [`columnGrouping`](/x/react-data-grid/column-groups/)
- [`clipboardPaste`](/x/react-data-grid/clipboard/#clipboard-paste)
Expand Down
6 changes: 2 additions & 4 deletions docs/pages/x/api/data-grid/data-grid-premium.json
Original file line number Diff line number Diff line change
Expand Up @@ -36,9 +36,8 @@
"checkboxSelectionVisibleOnly": { "type": { "name": "bool" }, "default": "false" },
"classes": { "type": { "name": "object" }, "additionalInfo": { "cssApi": true } },
"clipboardCopyCellDelimiter": { "type": { "name": "string" }, "default": "'\\t'" },
"columnBuffer": { "type": { "name": "number" }, "default": "3" },
"columnBufferPx": { "type": { "name": "number" }, "default": "150" },
"columnHeaderHeight": { "type": { "name": "number" }, "default": "56" },
"columnThreshold": { "type": { "name": "number" }, "default": "3" },
"columnVisibilityModel": { "type": { "name": "object" } },
"defaultGroupingExpansionDepth": { "type": { "name": "number" }, "default": "0" },
"density": {
Expand Down Expand Up @@ -553,7 +552,7 @@
"returned": "Promise<R> | R"
}
},
"rowBuffer": { "type": { "name": "number" }, "default": "3" },
"rowBufferPx": { "type": { "name": "number" }, "default": "150" },
"rowCount": { "type": { "name": "number" } },
"rowGroupingColumnMode": {
"type": { "name": "enum", "description": "'multiple'<br>&#124;&nbsp;'single'" },
Expand All @@ -578,7 +577,6 @@
"type": { "name": "enum", "description": "'border'<br>&#124;&nbsp;'margin'" },
"default": "\"margin\""
},
"rowThreshold": { "type": { "name": "number" }, "default": "3" },
"scrollbarSize": { "type": { "name": "number" } },
"scrollEndThreshold": { "type": { "name": "number" }, "default": "80" },
"showCellVerticalBorder": { "type": { "name": "bool" }, "default": "false" },
Expand Down
6 changes: 2 additions & 4 deletions docs/pages/x/api/data-grid/data-grid-pro.json
Original file line number Diff line number Diff line change
Expand Up @@ -25,9 +25,8 @@
"checkboxSelectionVisibleOnly": { "type": { "name": "bool" }, "default": "false" },
"classes": { "type": { "name": "object" }, "additionalInfo": { "cssApi": true } },
"clipboardCopyCellDelimiter": { "type": { "name": "string" }, "default": "'\\t'" },
"columnBuffer": { "type": { "name": "number" }, "default": "3" },
"columnBufferPx": { "type": { "name": "number" }, "default": "150" },
"columnHeaderHeight": { "type": { "name": "number" }, "default": "56" },
"columnThreshold": { "type": { "name": "number" }, "default": "3" },
"columnVisibilityModel": { "type": { "name": "object" } },
"defaultGroupingExpansionDepth": { "type": { "name": "number" }, "default": "0" },
"density": {
Expand Down Expand Up @@ -496,7 +495,7 @@
"returned": "Promise<R> | R"
}
},
"rowBuffer": { "type": { "name": "number" }, "default": "3" },
"rowBufferPx": { "type": { "name": "number" }, "default": "150" },
"rowCount": { "type": { "name": "number" } },
"rowHeight": { "type": { "name": "number" }, "default": "52" },
"rowModesModel": { "type": { "name": "object" } },
Expand All @@ -516,7 +515,6 @@
"type": { "name": "enum", "description": "'border'<br>&#124;&nbsp;'margin'" },
"default": "\"margin\""
},
"rowThreshold": { "type": { "name": "number" }, "default": "3" },
"scrollbarSize": { "type": { "name": "number" } },
"scrollEndThreshold": { "type": { "name": "number" }, "default": "80" },
"showCellVerticalBorder": { "type": { "name": "bool" }, "default": "false" },
Expand Down
6 changes: 2 additions & 4 deletions docs/pages/x/api/data-grid/data-grid.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,8 @@
"checkboxSelection": { "type": { "name": "bool" }, "default": "false" },
"classes": { "type": { "name": "object" }, "additionalInfo": { "cssApi": true } },
"clipboardCopyCellDelimiter": { "type": { "name": "string" }, "default": "'\\t'" },
"columnBuffer": { "type": { "name": "number" }, "default": "3" },
"columnBufferPx": { "type": { "name": "number" }, "default": "150" },
"columnHeaderHeight": { "type": { "name": "number" }, "default": "56" },
"columnThreshold": { "type": { "name": "number" }, "default": "3" },
"columnVisibilityModel": { "type": { "name": "object" } },
"density": {
"type": {
Expand Down Expand Up @@ -413,7 +412,7 @@
"returned": "Promise<R> | R"
}
},
"rowBuffer": { "type": { "name": "number" }, "default": "3" },
"rowBufferPx": { "type": { "name": "number" }, "default": "150" },
"rowCount": { "type": { "name": "number" } },
"rowHeight": { "type": { "name": "number" }, "default": "52" },
"rowModesModel": { "type": { "name": "object" } },
Expand All @@ -429,7 +428,6 @@
"type": { "name": "enum", "description": "'border'<br>&#124;&nbsp;'margin'" },
"default": "\"margin\""
},
"rowThreshold": { "type": { "name": "number" }, "default": "3" },
"scrollbarSize": { "type": { "name": "number" } },
"showCellVerticalBorder": { "type": { "name": "bool" }, "default": "false" },
"showColumnVerticalBorder": { "type": { "name": "bool" }, "default": "false" },
Expand Down

0 comments on commit 1418ac2

Please sign in to comment.