DataGroup
<DataGroup> is a vertical stack of Collapsible groups, each owning its own DataTable. Use for case-list grouped by collector, team-queue grouped by stage — anywhere groups carry meaning and the user benefits from collapsing by default.
When to use
- Case lists grouped by owner (“Mine”, “Team”).
- Queues grouped by stage / status / region.
- Any list where group membership is the primary scan axis and 5+ groups would be too much for
Tabs.
Don’t use DataGroup for: a single homogeneous list (use DataTable directly), 2–5 mutually-exclusive views (Tabs or SegmentedControl), or grouping that the user would re-pick frequently (use a Filter chip instead).
Default
Open and closed groups; click the header to toggle. The chevron rotates with the open state.
| Name | Stage | Amount |
|---|---|---|
| Acme Corp | Negotiation | $24,000 |
| Globex | Discovery | $8,500 |
| Initech | Closed-Won | $42,000 |
<DataGroup<Case> columns={columns} groups={[ { id: 'mine', label: 'Mine', count: 3, rows: minRows }, { id: 'team', label: 'Team', count: 2, defaultOpen: false, rows: teamRows }, ]}/>API
DataGroup
| Prop | Type | Default | Description |
|---|---|---|---|
groups * | DataGroupGroup<T>[] | — | One section per group. Each: { id, label, count?, description?, rows, defaultOpen? }. |
columns * | DataTableColumn<T>[] | — | Forwarded to every group's DataTable. |
rowId | (row: T) => string | — | Stable row id. Required when selection is enabled. |
onRowClick | (row: T) => void | — | Whole-row click. Forwarded to every DataTable. |
groupEmptyState | ReactNode | — | Rendered when a group has zero rows. Pass <EmptyState variant="filtered" />. |
className | string | — | Forwarded. |
DataGroupGroup<T>
| Prop | Type | Default | Description |
|---|---|---|---|
id * | string | — | Unique within the group list. |
label * | ReactNode | — | Section header label. |
count | number | — | Trailing tabular-num count next to the label. |
description | ReactNode | — | Optional muted description. |
rows * | T[] | — | Rows for this group. |
defaultOpen | boolean | true | Initial open state. |
Design guidelines
✓ Do
- Order groups by user importance (Mine first, then Team, then Archive). Don't alphabetize.
- Default-open groups the user expects to act on; default-closed the rest.
- Pass count prop — the user wants to see "47 in Team" without expanding it.
✗ Don't
- Use DataGroup for one group only. That's a DataTable.
- Mix column shapes across groups. Every group renders the same columns.
- Replace Tabs with DataGroup when the user only ever wants one view at a time. Tabs is correct there.
Accessibility
- Each section is a Radix
Collapsible— trigger is<button aria-expanded aria-controls>, content hasrole="region". - Inner
DataTablekeeps its own role + sort + selection a11y. - Keyboard: Tab reaches each trigger; Enter / Space toggles.
Related
DataTable— Single-list base.Collapsible— Underlying primitive.Tabs— When the user wants one group at a time.