Skip to main content

Grouped DataGrids

Now that we have looked at the two different hierarchical data grid types, lets dig deeper into each of them

Basic Example

Lets start with a simple example.

Live Editor
Result
Loading...

In this example, we used the nextLevel property to define the next level of the hierarchy. We have a tree structure with two levels of nesting. The first level is the root level, and the second level is the next level. The next level property is an object that contains the children field, which is the name of the field that contains the next level of the hierarchy. In this case, the field is called items.

Dynamic Levels

In some cases, you may not know upfront how many levels of nesting you have. In this case you can use the enableDynamicLevels flag to let the grid know, and it will recursively traverse the data to find the deepest level. This is useful when you have a tree structure, but you don't know how deep it goes. For example, you may have a tree structure of employees, but you don't know how many levels of managers there are. In this case, you can set the enableDynamicLevels flag to true, and the grid will automatically figure out the deepest level.

Live Editor
Result
Loading...

You can compare this declaration to the declaration of the same grid in the previous section:

        nextLevel: {
childrenField: "items",
},
enableDynamicLevels: true,

vs


nextLevel: {
childrenField: "items",
nextLevel: {
childrenField: "items",
},
},

You can see that we have removed the nested nextLevel declaration, and set the enableDynamicLevels flag to true, because we don't know how many levels of nesting there are, and we want the grid to figure it out for us.

Grouped DataGrids Selection

The concept of selection with hierarchical data is a little nuanced. What happens when you select a parent row? do you select all of the children? or just the parent? or none of them? How about when you select a child row? do you select the parent? or just the child? How does this work with filtering on? Lets look at some examples.

enableSelectionCascade

With the enableSelectionCascade flag set to true, the grid will automatically select all of the children when you select a parent row.

Live Editor
Result
Loading...

Notice that when you select a parent row, all of the children are selected as well.

enableSelectionBubble

With the enableSelectionBubble flag set to true, the grid will automatically select the parent row when you select a child row, but it will keep its selection state as indeterminate until all of the children are selected.

Live Editor
Result
Loading...
enableSelectionCascade & enableSelectionBubble

Please note, you can use both of these flags at the same time, or one or the other. They are independent of each other. For the most part, you will probably want to use both of them. You dont have to explicitly set the them to false if you are not using them, because they are false by default.

Grouped DataGrids Sorting

Sorting with grouped data works similar to sorting with ungrouped data, where you can sort by a single column, or multiple columns. The only difference is that when you sort by a column that is part of a hierarchy, the grid will sort the children of that column as well. This is a marked difference from how Nested Data works, where each level has its own columns, and its own sort state. With grouped data, the grid will sort all of the children of a column, regardless of what level they are on. Lets look at an example:

Live Editor
Result
Loading...

You can see that when we sort by the id column, the children of the id column are also sorted. This is because the id column is part of the hierarchy, and the grid will sort all of the children of the id column.

Grouped DataGrids Filtering

Filtering with grouped data works similar to filtering with ungrouped data, where you can filter by a single column, or multiple columns. The only difference is that when you filter by a column that is part of a hierarchy, the grid will filter the children of that column as well. There is an additional caveat, that if a child matches, we show the parent as well (because if we didnt, we wouldnt be able to see the child). Lets look at an example:

Live Editor
Result
Loading...

Notice that when we filter by the id column, the children of the id column are also filtered. This is because the id column is part of the hierarchy, and the grid will filter all of the children of the id column. You can also see that the parent is shown, even though it doesnt match the filter, because it has children that match the filter. This works with the global filter as well. When you search for the term 314414 in either the global filter or the id column filter, you can see that the parent row is shown, even though it doesnt match the filter, because it has children that match the filter. This recursive filter behavior works with other filters as well, such as the date filter, checkbox filter, number filter, mutil-select filter, and the select filter. It will automatically work with your custom filters as well!

Floating Headers

Floating headers are useful to maintain context when scrolling through a large grid. We also have the ability to float any number of rows or columns. This lets you control the part of the viewport that you want to cover via floating headers, and you can also control the opactiy of the floating headers. Lets look at an example:

Live Editor
Result
Loading...

As you can see, when you scroll, the grid will maintain 2 levels of hierarchy in the floating headers. You can also see that the floating headers are transparent, so you can see the grid behind them. You can also control the opacity of the floating headers, and the number of floating headers that you want to show. You can also control the number of floating columns that you want to show. In this case, we only want to show 1 floating column, which is the id column. The rest of the columns will be blank for the floating rows.

Finally, you can control the opacity of the floating headers. This is useful if you want to make the floating headers more transparent, so you can see the grid behind them. Below is the css that we use to make the floating headers more transparent:

.ezgrid-dg-floater,
.ezgrid-dg-left-locked-floater,
.ezgrid-dg-right-locked-floater {
opacity: 0.9;
z-index: 1;
background-color: #f5f5f5;
pointer-events: none;
}
tip

As you can see from the css above, you can make the left locked and right locked floating headers more or less transparent than the main scrolling area. You can use this behavior to make the floating headers only appear in one area if you choose to do so.

Group Row Headers

In addition to floating rows, we can also make the headers span across the entire grid.

Live Editor
Result
Loading...

You can fully customize the group header using the interface below

/**
* For grouped data grids, you can use the groupHeaderRenderer to display a custom header for each group.
* The group header can span the entire width of the grid, or it can be split into left and right locked sections.
* You can use the existing hierarchy column to display the group header, or you can use a custom renderer
* Please see https://flexicious.github.io/react-data-grid/?example=Group_Headers
* and https://flexicious.github.io/react-data-grid/?example=Large_Dynamic_Grid for examples.
*/
export interface GroupHeaderOptions {
/**
* The group header height function. This is used to control the height of the group header.
*/
groupHeaderHeightFunction?: (item: unknown) => number;
/**
* The group header renderer. The group header renderer is used to display a custom header for each group.
*/
groupHeaderRenderer?: (node: RendererProps) => unknown;
/**
* The group header renderer for the left locked section.
*/
groupHeaderRendererLeftLocked?: (node: RendererProps) => unknown;
/**
* The group header renderer for the right locked section.
* */
groupHeaderRendererRightLocked?: (node: RendererProps) => unknown;
/**
* The group header label function. This is used to control the text that is displayed in the group header.
* @param item The item that is being rendered.
* @returns The text that is displayed in the group header.
* */
groupHeaderLabelFunction?: (item: unknown) => string;
/**
* The field that is used to render the group header.
*/
groupHeaderField?: string;
/**
* When grouped headers are used, you can optionally show the group item row itself.
* this is useful when you want to show the group header, but also want to show the group item row which may
* have summary data.
*/
showGroupItemRow?: boolean;
/**
* The flag to turn on group headers.
*/
enableGroupHeaders: boolean;
/**
* If you already have a column that renders hierarchy, you can use that column to render the group header.
* as we do in the following example: https://flexicious.github.io/react-data-grid/?example=Group_Headers
* This is what enables the checkbox as well as the expand/collapse icon in the group header.
*/
useHierarchyColumnForRenderer?: boolean;
}