Table

Virtualized data grid with declarative columns, sorting, selection, pinning and resizing.

c2-table

Attributes

NameTypeDefaultDescription
rowsTableRow[][]The rows to display. An array in the property, JSON in the attribute.
columnsTableColumnConfig[] | undefinedColumn definitions, as an alternative to `c2-table-column` children. Children win when both are present.
row-keystringField used as the identity of a row, for selection and DOM reuse. Falls back to the row index.
selectionTableSelectionModenone`single` selects one row at a time, `multiple` supports ⌘/ctrl-click and shift-click ranges.
checkbox-selectionbooleanfalseAdds a leading checkbox column, pinned to the start.
valuestring[][]Keys of the selected rows: an array in the property, `;`-separated in the attribute.
sortSortModel[][]The sort, in priority order: `SortModel[]` in the property, `field:asc;other:desc` in the `sort` attribute.
multi-sortbooleanfalseLets shift-click add a column to the sort instead of replacing it.
sortablebooleanfalseMakes every column sortable; a column's own `sortable` still wins.
resizablebooleanfalseMakes every column resizable; a column's own `resizable` still wins.
stripebooleanfalseTints odd rows with `--c2-table__row__odd--background`.
virtualTableVirtualModeauto`auto` virtualizes past `virtual-threshold` rows; `always` and `never` force it.
row-heightnumber36Row height in pixels used before the first row has been measured.
overscannumber6Rows rendered above and below the viewport while virtualizing.
virtual-thresholdnumber100Row count past which `virtual="auto"` starts windowing.
block-sizenumber100Number of rows the table asks a `dataSource` for at a time.
loadingbooleanfalseShows the loading state; implied while a `dataSource` resolves its first block.
errorstringShows the error state with this message.
empty-messagestringNo rowsMessage shown when there are no rows.
pagenumber1The page on show, 1-based. Only meaningful while the table is `paginated`; clamped to `pageCount`.
page-sizenumber0Rows per page. `0` leaves paging off; a `c2-pagination` slotted into the `footer` sets it from its own `page-size` when the table has none, which is what makes the nested form work with no configuration. With `rows` the page is sliced in place; with a `dataSource` each page is one request.

Events

NameTypeDescription
page-changeCustomEvent<TablePageChangeEventDetail>Fired after the shown page changes, while `paginated`. `detail.start` and `detail.count` are the slice of the whole dataset now shown — with a `dataSource`, the `getRows` request that follows. A pager slotted in the footer does not fire its own: the table speaks for it.
sort-changeCustomEvent<TableSortChangeEventDetail>Fired after the user clicks a sortable header. `detail.sort` is the new sort model, in priority order.
row-clickCustomEvent<TableRowEventDetail>Fired when a row is clicked, before the selection is applied.
cell-clickCustomEvent<TableCellEventDetail>Fired when a cell is clicked; adds `detail.column` and `detail.value`.
selection-changeCustomEvent<TableSelectionChangeEventDetail>Fired after the user changes the selection. `detail.value` is the array of selected row keys, `detail.rows` the matching rows.
column-resizeCustomEvent<TableColumnResizeEventDetail>Fired when the user releases a column's resize handle.

CSS custom properties

Grouped by the element and state they target. Click a group to collapse it; click a name to copy it.

NameTypeDefaultDescription
--c2-table--backgroundcolor#ffffff
--c2-table--colorcolor#18181b
--c2-table--font-sizefont-size14px
--c2-table--max-heightpixelnoneCaps the height when the host is not sized itself; the body scrolls.
--c2-table--border-topborder1px solid #e4e4e7
--c2-table--border-rightborder1px solid #e4e4e7
--c2-table--border-bottomborder1px solid #e4e4e7
--c2-table--border-leftborder1px solid #e4e4e7
--c2-table--border-top-left-radiusborder-radius8px
--c2-table--border-top-right-radiusborder-radius8px
--c2-table--border-bottom-left-radiusborder-radius8px
--c2-table--border-bottom-right-radiusborder-radius8px
--c2-table--box-shadowbox-shadownone
--c2-table__header--backgroundcolor#fafafa
--c2-table__header--colorcolor#71717a
--c2-table__header--heightpixel36px
--c2-table__header--font-sizefont-size12px
--c2-table__header--font-weightfont-weight600
--c2-table__header--letter-spacingletter-spacing0.02em
--c2-table__header--border-bottomborder1px solid #e4e4e7
--c2-table__header-cell--paddingpadding0 12px
--c2-table__header-cell--gappixel6px
--c2-table__header-cell__hover--backgroundcolor#f4f4f5
--c2-table__header-cell__sorted--colorcolor#18181b
--c2-table__sort-icon--widthpixel14px
--c2-table__sort-icon--heightpixel14px
--c2-table__sort-icon--colorcolor#a1a1aa
--c2-table__sort-icon__active--colorcolorrgb(2, 101, 220)
--c2-table__resizer--widthpixel9pxWidth of the grab area, not of the visible line.
--c2-table__resizer--heightpixel56%Height of the resting divider, as a share of the header.
--c2-table__resizer--line-widthpixel1px
--c2-table__resizer--colorcolor#e4e4e7The divider drawn at a resizable column's edge.
--c2-table__resizer__hover--heightpixel100%
--c2-table__resizer__hover--line-widthpixel2px
--c2-table__resizer__hover--colorcolorrgb(2, 101, 220)
--c2-table__row--heightpixel36pxRow height; virtualization measures it, so keep it uniform.
--c2-table__row--border-bottomborder1px solid #e4e4e7
--c2-table__row__hover--backgroundcolor#fafafa
--c2-table__row__odd--backgroundcolor#fafafaApplies with the `stripe` attribute.
--c2-table__row__selected--backgroundcolor#edf1fe
--c2-table__row__selected--colorcolor#18181b
--c2-table__cell--paddingpadding0 12px
--c2-table__cell--gappixel8px
--c2-table__cell--font-sizefont-size14px
--c2-table__cell--colorcolor#18181b
--c2-table__cell--border-rightbordernoneVertical grid lines; applies to header cells too.
--c2-table__cell__focus--outlineoutline2px solid rgba(2, 101, 220, 0.4)
--c2-table__cell__focus--outline-offsetpixel-2px
--c2-table__pinned-start--box-shadowbox-shadow1px 0 0 0 #e4e4e7Separator on the last column pinned to the start.
--c2-table__pinned-end--box-shadowbox-shadow-1px 0 0 0 #e4e4e7Separator on the first column pinned to the end.
--c2-table__selection-cell--widthpixel44pxWidth of the `checkbox-selection` column.
--c2-table__skeleton--backgroundcolor#f4f4f5Placeholder shown in cells whose `dataSource` block is still loading.
--c2-table__skeleton--border-radiusborder-radius4px
--c2-table__state--colorcolor#71717aColour of the empty and loading messages.
--c2-table__state--paddingpadding32px 12px
--c2-table__state--font-sizefont-size14px
--c2-table__state__error--colorcolorrgb(211, 21, 16)
--c2-table__toolbar--backgroundcolortransparent
--c2-table__toolbar--paddingpadding8px 12px
--c2-table__toolbar--border-bottomborder1px solid #e4e4e7
--c2-table__footer--backgroundcolortransparent
--c2-table__footer--paddingpadding8px 12px
--c2-table__footer--border-topborder1px solid #e4e4e7

c2-table-column

Attributes

NameTypeDefaultDescription
fieldstringKey of the value in the row object; may be a dotted path such as `user.name`.
headerstring | undefinedHeader label. Falls back to the field name.
widthstring1frGrid track for the column: `1fr`, `160px`, `minmax(120px, 1fr)`…
min-widthnumber64Lower bound in pixels while the column is resized.
alignColumnAlignstartHorizontal alignment of the header and the cells.
sortableboolean | undefinedLets the user sort by this column. Defaults to the table's `sortable`.
resizableboolean | undefinedLets the user drag the column's trailing edge. Defaults to the table's `resizable`.
pinnedColumnPin | undefinedFreezes the column against the leading or trailing edge while scrolling horizontally.
hiddenbooleanfalseLeaves the column out of the table without removing the definition.
formatColumnFormattextBuilt-in `Intl` formatting applied when no `renderCell` is set.
format-optionsRecord<string, unknown> | undefinedOptions handed to the `Intl` formatter of `format`, as JSON in the attribute.
currencystring | undefinedCurrency code used by `format="currency"`.
localestring | undefinedBCP 47 locale used by `format`. Defaults to the browser locale.
cell-classstring | undefinedClass set on every cell of this column, so light-DOM CSS can target it through `::part(cell)`.

Events

NameTypeDescription
COLUMN_CHANGE_EVENTCustomEvent
escAccordionConnected, animated panels with shared borders and single or multiple expansion.LayoutAvatarImage, initials or icon for a person, with status dot and badge.Data displayBadgeTinted pill for status text, counts and dots, optionally pinned to a corner of another element.Data displayBreadcrumbNavigation trail of link buttons with separators, a current page and optional collapsing.NavigationButtonThemeable button with slots for text, prefix, suffix and running icons.ButtonsButton GroupAttached buttons with shared borders, optionally a segmented control with single or multiple selection.ButtonsCardGroups related content and actions on a single bordered surface.LayoutChat InputAuto-growing message box with a send button for chat interfaces.ChatChat MessageOne chat bubble with avatar, title, timestamp and message body.ChatCheckboxNative checkbox behaviour in a quiet, themeable box with an opt-in hover layer.InputsCode ViewerSyntax-highlighted code with line numbers, copy button and dark mode, powered by shiki.Data displayColor AreaTwo-dimensional area for picking saturation and value of a colour.InputsColor SelectColour swatch that opens a full picker built from area and slider.InputsColor SliderHorizontal slider for choosing a hue from 0 to 360.InputsCopy ButtonButton that copies text to the clipboard — the element it sits in, another element by id, or a literal string.ButtonsDetailsCollapsible disclosure built on native details and summary.LayoutIcon ButtonRound, hoverable button wrapping a slotted SVG icon.ButtonsKbdKeyboard key label for shortcuts and command hints, with the semantics of the native kbd element.Data displayLabelCaption that names and activates the control referenced by its for attribute, with a required marker.InputsLink ButtonText-styled control for link and navigation actions, rendered as a real anchor or a button.NavigationListVertical list container with single or multiple selection.Data displayList ItemSelectable row with icon slots, used on its own or as the option of list and select.Data displayMenuCommands, links, checkboxes and submenus in a popover anchored to a trigger.NavigationModalDialog built on the native dialog element: focus trap, backdrop, Escape, title, body and footer.FeedbackNavigation MenuSite navigation bar whose triggers open panels of links below the header.NavigationOverlayAnchored popup built on the browser Popover API, positioned with floating-ui.FeedbackPaginationPage navigation in three layouts: numbered pages, a simple page status, or a table-footer row with rows-per-page.NavigationProgressLinear progress bar, indeterminate or filling to a value, with an optional label and count.FeedbackRadioRadio options built on native inputs, grouped into one value with keyboard navigation.InputsSelectDropdown that pairs a themeable trigger with an anchored list of c2-list-item options.InputsSeperatorHorizontal or vertical rule with an optional label, for dividing content and toolbars.LayoutSheetDialog pinned to an edge of the screen, for content that complements the page rather than interrupting it.FeedbackSide NavResponsive navigation drawer beside the page: pushes the content on large screens, slides over it with a backdrop on small ones.NavigationSkeletonPlaceholder block standing in for content that has not arrived, in three shapes and three animations.FeedbackSliderRange input with a themeable track, thumb, step ticks and value bubble.InputsSpinnerCircular progress indicator, indeterminate or showing a value, with optional text.FeedbackSwitchOn/off toggle on a native switch input, with label, description and thumb icons.InputsTableVirtualized data grid with declarative columns, sorting, selection, pinning and resizing.Data displayTabsTab strip that shows one content panel at a time.NavigationText FieldSingle-line input with icon slots, clear button, helper and error text, and a character counter.InputsTextareaMultiline text input with resizing, helper and error text, and a character counter.InputsToastNotification cards and a manager for stacked, queued notifications with independent lifetimes.FeedbackTooltipContextual hint shown when its target is hovered or focused, rendered in the top layer.FeedbackFeather Icons287 open-source Feather icons, one web component each.IconsMat Icon2,234 Material Icons ligatures rendered through a single element.IconsPhosphor Icons1,512 flexible icons in six weights, one web component each.IconsThemingTheme every c2n component from a handful of design tokens with @c2n/theme, or reach for any component variable directly.GuideUsing c2n in an applicationThe workflow behind every c2n app: load the theme once, use c2-* tags directly, and turn every repeated pattern into a small variant or composed component.Guide