Shadcn React Table

Search documentation

Search the docs

Column resizing

Set enableColumnResizing: true to add a drag handle on each column's edge. Users drag the handle to widen or narrow a column.

Column resizingDrag the header edge to resize a column.
GitHub
ID
AvaThompsonOwnerEngineeringactive22$45,000Jan 2, 2023
0%
LiamNguyenAdminMarketinginactive25$47,137Jan 13, 2023
9%
NoahSilvaEditorDesignpending28$49,274Jan 24, 2023
18%
EmmaCarterViewerSalesactive31$51,411Feb 4, 2023
27%
OliviaRossiOwnerSupportinactive34$53,548Feb 15, 2023
36%
WilliamWalkerAdminEngineeringpending37$55,685Feb 26, 2023
45%
SophiaPatelEditorMarketingactive40$57,822Mar 9, 2023
54%
JamesMullerViewerDesigninactive43$59,959Mar 20, 2023
63%
IsabellaParkOwnerSalespending46$62,096Mar 31, 2023
72%
LucasReyesAdminSupportactive49$64,233Apr 11, 2023
81%
$4,120,536
Rows per page
1–10 of 48
tsx
const table = useDataTable({
  data,
  columns,
  getRowId: (row) => row.id,
  enableColumnResizing: true,
})

return <DataTable table={table} />

Keyboard

Each resize handle is focusable. With it focused, the arrow keys widen or narrow the column by 10px (50px with Shift) — mirrored in right-to-left tables — Home and End jump to the column's minSize and maxSize, and Enter fits the column to its content (or resets it when auto-size is off). Screen readers hear it as a separator with the column's current width.

Resize mode

The resize mode defaults to "onChange", so columns resize live as the handle moves. Pass TanStack's columnResizeMode: "onEnd" to defer the resize until the handle is released.

tsx
const table = useDataTable({
  data,
  columns,
  enableColumnResizing: true,
  columnResizeMode: "onEnd",
})

Width constraints

Column widths come from size, minSize, and maxSize on the column definition.

tsx
const columns = [
  { accessorKey: "firstName", size: 200, minSize: 120, maxSize: 320 },
]

Set sensible bounds

Define minSize and maxSize so users cannot collapse or stretch a column past a usable width.

Auto-sizing

Double-click a column's resize handle to size it to fit its widest value — header and data, across the full dataset (not just the rows currently on screen). This is on by default whenever enableColumnResizing is set, and respects each column's minSize/maxSize bounds.

Set enableColumnAutosize: false to turn it off; double-clicking the handle then resets the column to its default size instead.

tsx
const table = useDataTable({
  data,
  columns,
  enableColumnResizing: true,
  enableColumnAutosize: true, // default: matches enableColumnResizing
})

You can also trigger it imperatively from the table instance:

tsx
table.autoSizeColumn("firstName")
table.autoSizeAllColumns()
Column auto-sizeFit every column to its content from a toolbar button.
GitHub
ID
AvaThompsonOwnerEngineeringactive22$45,000Jan 2, 2023
0%
LiamNguyenAdminMarketinginactive25$47,137Jan 13, 2023
9%
NoahSilvaEditorDesignpending28$49,274Jan 24, 2023
18%
EmmaCarterViewerSalesactive31$51,411Feb 4, 2023
27%
OliviaRossiOwnerSupportinactive34$53,548Feb 15, 2023
36%
WilliamWalkerAdminEngineeringpending37$55,685Feb 26, 2023
45%
SophiaPatelEditorMarketingactive40$57,822Mar 9, 2023
54%
JamesMullerViewerDesigninactive43$59,959Mar 20, 2023
63%
IsabellaParkOwnerSalespending46$62,096Mar 31, 2023
72%
LucasReyesAdminSupportactive49$64,233Apr 11, 2023
81%
$4,120,536
Rows per page
1–10 of 48

Layout mode and grow

layoutMode decides how the table hands out its width, as in Material React Table:

  • "semantic" (default) — the browser's table layout. Columns with a size keep it and the others share what's left.
  • "grid" — every column keeps its size, and the spare width (the container's width minus the columns' sizes) goes to the growing columns, so the table fills its container. When the columns are wider than the container, nothing grows and the table scrolls.
  • "grid-no-grow" — every column keeps its size and nothing grows; the table is exactly as wide as its columns.

In grid mode every data column grows by default. Set meta.grow on a column to change that: false (or 0) keeps it at its size, and a number sets its share — a column with grow: 2 takes twice the spare width of one with grow: 1. The table's own columns (selection, expand, row numbers, row drag, row pin, row actions) never grow.

tsx
const columns = [
  { accessorKey: "firstName", size: 150 },
  { accessorKey: "email", size: 220, meta: { grow: 2 } },
  { accessorKey: "role", size: 130, meta: { grow: false } },
]

const table = useDataTable({
  data,
  columns,
  layoutMode: "grid",
  enableColumnResizing: true,
})

Resizing works in every mode. In grid mode, resizing a growing column starts from the width it shows, and from then on the column keeps the size you gave it (it has a size in columnSizing, so it stops growing); the other growing columns take up the difference. Resetting the column (column.resetSize()) lets it grow again. A column given a size through initialState.columnSizing does not grow either.

Layout modeSwitch between semantic, grid and grid-no-grow; grow columns by weight.
GitHub
AvaThompsonava.thompson@example.comOwner
LiamNguyenliam.nguyen@example.comAdmin
NoahSilvanoah.silva@example.comEditor
EmmaCarteremma.carter@example.comViewer
OliviaRossiolivia.rossi@example.comOwner
Rows per page
1–5 of 48