Data Grid - Row grouping
Group your rows according to some column values.
For when you need to group rows based on repeated column values, and/or custom functions.
In the following example, movies are grouped based on their production company
:
Grouping criteria
Initialize the row grouping
The easiest way to get started with the feature is to provide its model to the initialState
prop:
<DataGridPremium
initialState={{
rowGrouping: {
model: ['company', 'director'],
},
}}
/>
The basic parameters are the columns you want to check for repeating values. This example groups all the movies matching the same company name, followed by a second group matching the director's name.
Controlled row grouping
If you need to control the state of the criteria used for grouping, use the rowGroupingModel
prop.
You can use the onRowGroupingModelChange
prop to listen to changes to the grouping criteria and update the prop accordingly.
Grouping columns
Single grouping column
By default, the data grid will display a single column holding all grouping columns. If you have multiple grouping criteria, this column name will be set to "Group."
Multiple grouping columns
To display a column for each grouping criterion, set the rowGroupingColumnMode
prop to multiple
.
Custom grouping column
To customize the rendering of the grouping column, use the groupingColDef
prop.
You can override the headerName or any property of the GridColDef
interface, except the field
, the type
, and the properties related to inline edition.
By default, when using the object format, the properties will be applied to all Grouping columns. This means that if you have rowGroupingColumnMode
set to multiple
, all the columns will share the same groupingColDef
properties.
If you wish to override properties of specific grouping columns or to apply different overrides based on the current grouping criteria, you can pass a callback function to groupingColDef
, instead of an object with its config.
The callback is called for each grouping column, and it receives the respective column's "fields" as parameter.
Grouping rows with custom cell renderer
By default, when rows are grouped by a column with a custom cell component (GridColDef['renderCell']
), the same custom cell component is used in the grouping column.
You can opt out of this default behavior by returning params.value
in renderCell
for grouping rows instead:
const ratingColDef: GridColDef = {
// ...
renderCell: (params) => {
if (params.rowNode.type === 'group') {
return params.value;
}
return (
// ...
);
},
};
Show values for the leaves
By default, the grouped rows display no value on their grouping columns' cells. Those cells are called "leaves."
If you want to display some value, you can provide a leafField
property to the groupingColDef
.
Hide the descendant count
Use the hideDescendantCount
property of the groupingColDef
to hide the number of descendants of a grouping row.
Hide the grouped columns
By default, the columns used to group the rows remains visible.
For instance if you group by "director"
, you have two columns titled Director:
- The grouped column (the column from which you grouped the rows)
- The grouping column on which you can toggle the groups
To automatically hide the grouped columns, use the useKeepGroupedColumnsHidden
utility hook.
The hook automatically hides the columns when added to the model, and displays them when removed from it.
Below are two examples about how to use columnVisibilityModel
or initialState
with useKeepGroupedColumnsHidden
hook.
You can mix the two examples to support both at the same time.
// Usage with the initial state
const apiRef = useGridApiRef();
const initialState = useKeepGroupedColumnsHidden({
apiRef,
initialState: {
rowGrouping: {
model: ['company'],
},
columns: {
// Other hidden columns
columnVisibilityModel: { gross: false },
},
},
});
return <DataGridPremium {...data} apiRef={apiRef} initialState={initialState} />;
// Usage with the controlled model
const apiRef = useGridApiRef();
const [rowGroupingModel, setRowGroupingModel] = React.useState([
'company',
'director',
]);
const initialState = useKeepGroupedColumnsHidden({
apiRef,
rowGroupingModel,
});
return (
<DataGridPremium
{...data}
apiRef={apiRef}
initialState={initialState}
rowGroupingModel={rowGroupingModel}
/>
);
Disable the row grouping
For all columns
You can disable row grouping by setting the disableRowGrouping
prop to true.
It will disable all the features related to the row grouping, even if a model is provided.
For some columns
In case you need to disable grouping on specific column(s), set the groupable
property on the respective column definition (GridColDef
) to false
.
In the example below, the director
column can not be grouped. And in all example, the title
and gross
columns can not be grouped.
Using groupingValueGetter
for complex grouping value
The grouping value has to be either a string
, a number
, null
, or undefined
.
If your cell value is more complex, pass a groupingValueGetter
property to the column definition to convert it into a valid value.
const columns: GridColDef[] = [
{
field: 'composer',
groupingValueGetter: (params) => params.value.name,
},
// ...
];
Rows with missing groups
If the grouping key of a grouping criteria is null
or undefined
for a row, the data grid will consider that this row does not have a value for this group. and will inline it for those groups.
Group expansion
By default, all groups are initially displayed collapsed. You can change this behavior by setting the defaultGroupingExpansionDepth
prop to expand all the groups up to a given depth when loading the data.
If you want to expand the whole tree, set defaultGroupingExpansionDepth = -1
If you want to expand groups by default according to a more complex logic, use the isGroupExpandedByDefault
prop which is a callback receiving the node as an argument.
When defined, this callback will always have priority over the defaultGroupingExpansionDepth
prop.
isGroupExpandedByDefault={
node => node.groupingField === 'company' && node.groupingKey === '20th Century Fox'
}
Use the setRowChildrenExpansion
method on apiRef
to programmatically set the expansion of a row.
Customize grouping cell indent
To change the default cell indent you can pass the offsetMultiplier
prop to the <GridTreeDataGroupingCell />
component and use it as groupingColDef.renderCell
:
const groupingColDef = {
renderCell: (params) => (
<GridTreeDataGroupingCell {...params} offsetMultiplier={4} />
),
};
<DataGridPremium groupingColDef={groupingColDef} />;
Sorting / Filtering
Single grouping column
When using rowGroupingColumnMode = "single"
, the default behavior is to apply the sortComparator
and filterOperators
of the top-level grouping criteria.
If you are rendering leaves with the leafField
property of groupColDef
, the sorting and filtering will be applied on the leaves based on the sortComparator
and filterOperators
of their original column.
In both cases, you can force the sorting and filtering to be applied on another grouping criteria with the mainGroupingCriteria
property of groupColDef
Multiple grouping columns
When using rowGroupingColumnMode = "multiple"
, the default behavior is to apply the sortComparator
and filterOperators
of the grouping criteria of each grouping column.
If you are rendering leaves on one of those columns with the leafField
property of groupColDef
, the sorting and filtering will be applied on the leaves for this grouping column based on the sortComparator
and filterOperators
of the leave's original column.
If you want to render leaves but apply the sorting and filtering on the grouping criteria of the column, you can force it by setting the mainGroupingCriteria
property groupColDef
to be equal to the grouping criteria.
In the example below:
- the sorting and filtering of the
company
grouping column is applied on thecompany
field - the sorting and filtering of the
director
grouping column is applied on thedirector
field even though it has leaves
Get the rows in a group
You can use the apiRef.current.getRowGroupChildren
method to get the id of all rows contained in a group.
It will not contain the autogenerated rows (i.e. the subgroup rows or the aggregation footers).
const rows: GridRowId[] = apiRef.current.getRowGroupChildren({
groupId: params.id,
// If true, the rows will be in the order displayed on screen
applySorting: true,
// If true, only the rows matching the current filters will be returned
applyFiltering: true,
});
If you want to get the row ids of a group given its grouping criteria, use getGroupRowIdFromPath
const rows = apiRef.current.getRowGroupChildren({
groupId: getGroupRowIdFromPath([{ field: 'company', key: 'Disney Studios' }]),
});
Row group panel 🚧
With this panel, your users will be able to control which columns are used for grouping just by dragging them inside the panel.
Full example
Advanced use cases
See Row grouping recipes for more advanced use cases.
apiRef
The grid exposes a set of methods that enables all of these features using the imperative apiRef
. To know more about how to use it, check the API Object section.
Signature:
addRowGroupingCriteria: (groupingCriteriaField: string, groupingIndex?: number) => void
Signature:
removeRowGroupingCriteria: (groupingCriteriaField: string) => void
Signature:
setRowGroupingCriteriaIndex: (groupingCriteriaField: string, groupingIndex: number) => void