bit Bheadless

Grid / TreeGrid

An interactive two-dimensional widget — data tables, spreadsheets-lite, file trees with columns, calendars — with roving cell focus, row selection, sorting and expandable rows.

Implementation: CSS Tailwind

Sortable data grid

The WAI-ARIA Data Grid pattern on a real <table> (As="table" / "thead" / "tbody" / "tr" / "th" / "td"). The grid is a single tab stop: arrow keys move between cells, Home / End jump to the ends of the row, Ctrl + Home / End to the corners, PageUp / PageDown move by PageSize rows. Column headers are cells too — click one or press Enter on it and its OnActivate toggles the sort, which Sort announces as aria-sort.

Planet Type Diameter Moons
Earth Terrestrial 12,756 km 1
Jupiter Gas giant 142,984 km 95
Mars Terrestrial 6,792 km 2
Mercury Terrestrial 4,879 km 0
Neptune Ice giant 49,528 km 16
Saturn Gas giant 120,536 km 146
Uranus Ice giant 51,118 km 28
Venus Terrestrial 12,104 km 0

Multi-row selection

SelectionMode="BitBhGridSelectionMode.Multiple" with @bind-SelectedKeys (every data row needs a Key). Click toggles a row and Shift + click selects a range; Space toggles the focused row, Shift + Space or Shift + Up / Down extend the selection, Ctrl + A selects every row. Rows get aria-selected, so the check boxes are pure CSS; the header box uses OnActivate to select or clear everything.

0 selected · total $0.00
Select all Invoice Customer Status Amount
INV-1042 Acme Corp Paid $1,250.00
INV-1043 Globex Pending $830.50
INV-1044 Initech Overdue $4,200.00
INV-1045 Umbrella Paid $615.75
INV-1046 Hooli Pending $2,980.00
INV-1047 Stark Industries Paid $12,400.00

Row activation

OnRowActivate fires with the row's Key when the user presses Enter on any of its cells or double-clicks it — open a message, navigate to a record, start editing. Here BitBhGridSelectionMode.Single marks the current row, and opening a message marks it as read.

From Subject Received
Ada Lovelace Notes on the Analytical Engine 09:24
Grace Hopper Found a bug (an actual moth) 08:51
Alan Turing Can machines think? Yesterday
Margaret Hamilton Priority displays Mon

Press Enter on a row, or double-click it, to open the message.

TreeGrid

TreeGrid="true" renders role="treegrid". Give each row its Level, HasChildren and ParentKey: rows under a collapsed folder get the hidden attribute and are skipped by the keyboard. On a row's first cell, Right expands it (then moves into the row) and Left collapses it (then jumps to the parent row). The chevron is a BitBhGridRowToggle: a mouse shortcut, hidden from assistive tech, that toggles the row (synced through @bind-ExpandedKeys); indentation comes from the --bit-bh-grid-level variable on each row.

Name Kind Size
📂project Folder 502.1 KB
📂src Folder 23.6 KB
📄app.ts TypeScript 13.9 KB
📄router.ts TypeScript 6.7 KB
📄styles.css Stylesheet 3.1 KB
📄package.json JSON 1.2 KB
📄README.md Markdown 4.4 KB
📄notes.txt Text 1 KB

Selected: (none)

Div-based grid (calendar)

BitBhGrid, BitBhGridRowGroup, BitBhGridRow and BitBhGridCell render <div>s with role="grid" / "rowgroup" / "row" / "gridcell" by default, so any layout works — here each row is a 7-column CSS grid. Arrow keys move by day and week, Home / End go to the start / end of the week, and Enter or a click picks a date through each cell's OnActivate. aria-selected, aria-current and aria-disabled on the cells are plain attributes set by the page.

October 2026
Su
Mo
Tu
We
Th
Fr
Sa
27
28
29
30
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31

Picked: (none)

An unhandled error has occurred. Reload 🗙