‹ components

DataTable

stablev1.0.0·open in canvas

Terminal-grade table: real table semantics, sticky header, aria-sort client sorting, density-token row grid.

Installnpx shadcn add @cids/data-table
Live demo
Markets
Volume7d
SOL$184.26+3.60%$3.18B
JUP$0.8123−1.70%$142.6M
BONK$0.00002314+6.90%$318.4M
JTO$2.448−2.10%$38.2M

Motion · tap to replay

honors reduced-motion

Row hover + sort-header color, 150ms targeted. Nothing animates on data ticks (zero layout shift is the contract).

Brand chip remounts on tap · highlighted tokens are named in this component's doc · spring is budgeted to human feedback only.

import { DataTable, type Column } from "@/design-system";

const cols: Column<Row>[] = [
  { key: "sym", header: "Token", cell: (r) => r.sym, sortable: true, sortValue: (r) => r.sym },
  { key: "px", header: "Price", align: "right", sortable: true, cell: (r) => fmtUsd(r.px), sortValue: (r) => r.px },
];

<DataTable columns={cols} rows={rows} rowKey={(r) => r.sym} caption="Markets" maxHeight="20rem" />

Tokens · live

Resolves in the active theme — flip the toggle above to verify.

Terminal-grade table: real table semantics, sticky header, aria-sort client sorting, density-token row grid.

Anatomy

TOKEN        PRICE ▾   <- sticky thead, sort buttons, aria-sort
-------------------------
JUP        $0.8123      <- row-h/cell-px from density tokens
SOL      $184.26        <- numeric: right + data-md + tabular

Props

PropTypeDefaultNotes
columnsColumn<T>[]--{key, header, cell, align?, sortable?, sortValue?, width?}.
rowsT[]--Data.
rowKey(row) => string--Stable identity (streaming-safe).
captionstring--Visually-hidden table name (required).
maxHeightstring--Scroll container + sticky header.
classNamestring--cn-merged onto the frame.

Virtualization recipe: not shipped by design (no reference system ships it). Past ~200 streaming rows, wrap rows with TanStack Virtual: keep this table for layout/semantics, virtualize <tbody> children, preserve rowKey stability.

Motion

Row hover + sort-header color, 150ms targeted. Nothing animates on data ticks (zero layout shift is the contract).

A11y

Self-contained: copy the folder into any Tailwind+React app, or use the install command above. Docs and this page render the same file on disk — they cannot drift.