Skip to content

A primitive is one control you drop into a form or a toolbar — a segmented control, an input with an addon, a tag field.

Primitives

The parts between an element and a section

Not another Button. You already have one — what you do not have is the button group with its borders collapsed, the input with an addon on each end, the field that wires a label to a hint to an error, the segmented control that a screen reader can actually read. Every project rebuilds these, and no base library ships them.

54 primitives in 12 categories28 need nothing but React307 blocks built on top

Recently added

Nothing new in the last 7 days — this is the most recent

    Actions

    View all 3
    Open the full page for this primitive

    Button

    Six variants and four sizes, with the two states everyone forgets: a loading state that keeps its width, and an icon-only size whose type refuses to compile without an accessible name.

    Actions114 lines1 dep
    Open the full page for this primitive

    Button Group

    Buttons joined into one control, with collapsed borders, logical end rounding and a focus ring that paints above its neighbours instead of being clipped by them.

    Actions104 linesNo deps
    Open the full page for this primitive

    Social & Login Buttons

    Google, GitHub, Apple and Microsoft with their real marks drawn as inline SVG — no icon package, no brand-guideline violation, and the "Continue with" wording that works for sign-up and sign-in at once.

    Actions150 lines1 dep

    Form Controls

    View all 7
    Open the full page for this primitive

    Field

    The label, hint, error and aria wiring around one input — including the part that is usually wrong, where the hint has to stay in aria-describedby once an error joins it.

    Form Controls129 lines1 dep
    Open the full page for this primitive

    Input Group

    An input with addons, an inline icon or an action button attached, with the padding reserved for the icon and the focus ring on the whole group rather than its middle third.

    Form Controls120 linesNo deps
    Open the full page for this primitive

    Keyboard Key

    A shortcut written once as "mod+k" and rendered for the keyboard it will be typed on — ⌘ on Apple, Ctrl elsewhere — with the symbols hidden from screen readers behind a spoken name.

    Form Controls149 linesNo deps
    Open the full page for this primitive

    Switch

    An on/off setting that takes effect now, as role="switch" so a screen reader says "on" rather than "checked" — with the label and description in one row, a clickable label, and an off state dark enough to pass 3:1.

    Form Controls106 linesNo deps
    Open the full page for this primitive

    Range Slider

    Two thumbs on one track, built from two native range inputs so the keyboard, touch dragging and announced values come free — with the thumbs prevented from crossing and the min thumb still reachable at the far end.

    Form Controls129 linesNo deps

    Selection

    View all 5
    Open the full page for this primitive

    Combobox

    A select you can type into, with the full ARIA combobox keyboard contract and focus that never leaves the input — which is the single most common defect in hand-built ones.

    Selection235 lines1 dep
    Open the full page for this primitive

    Segmented Control

    Pick exactly one, built as a radio group rather than three buttons, so a screen reader says which is chosen — with a sliding indicator that animates one transform instead of repainting backgrounds.

    Selection164 linesNo deps
    Open the full page for this primitive

    Rating

    Both ratings, which are different components: a radio group for choosing whole stars, and a non-interactive display with fractional fill, because an average of 4.3 drawn as 4.5 is a number the page invented.

    Selection158 lines1 dep
    Open the full page for this primitive

    Emoji Reactions

    A reaction row where each pill is a toggle that says whether you are one of the count, plus a short picker — announced with names, since "👍 3" is read as a shrug by a screen reader.

    Selection153 lines1 dep
    Open the full page for this primitive

    Radio Card Group

    Plans and shipping methods as cards, built on real radio inputs so the arrow keys, "2 of 3" and form submission are the browser's — with selection drawn as a tick, not only a colour.

    Selection135 linesNo deps

    Status & Labels

    View all 4
    Open the full page for this primitive

    Badge

    Six semantic tones across three shapes, kept as separate axes — so a red outline badge is something you can ask for rather than something the variant list forgot.

    Status & Labels91 linesNo deps
    Open the full page for this primitive

    Status Badge

    A dot and a word, with no icon-only mode by design — one in twelve men cannot separate the red state from the green one, so the word is structural rather than optional.

    Status & Labels104 linesNo deps
    Open the full page for this primitive

    Progress Steps

    An ordered list in a nav, not a row of divs — so the count and the position come free, and aria-current names the step you are on. Horizontal and vertical, because four labels do not fit on a phone.

    Navigation & Steps145 lines1 dep
    Open the full page for this primitive

    Tree View

    One tab stop for the whole tree, with the ARIA tree keyboard contract in full — including typeahead and the arrow keys mapped through the reading direction.

    Navigation & Steps235 lines1 dep
    Open the full page for this primitive

    Tabs

    One tab stop for the whole list, arrow keys mapped through the reading direction, and a manual-activation mode so arrowing past five expensive panels does not fire four requests nobody asked for.

    Navigation & Steps181 linesNo deps
    Open the full page for this primitive

    Pagination

    A page window that keeps its width while you page and never draws an ellipsis for a single page — as real links when you pass getHref, so a listing stays crawlable and works without JavaScript.

    Navigation & Steps179 lines1 dep
    Open the full page for this primitive

    Accordion

    Buttons inside real headings, with panels that stay mounted so aria-controls resolves and go inert when shut so Tab cannot walk into invisible content — animated by a grid-row transition, off under reduced motion.

    Navigation & Steps138 lines1 dep

    Overlays & Feedback

    View all 4
    Open the full page for this primitive

    Alert

    An inline message that is not a live region by default — an alert role interrupts a screen reader, which is wrong for a notice that is simply on the page — with a `live` switch for the ones that appear in response to something.

    Overlays & Feedback134 lines1 dep
    Open the full page for this primitive

    Dropdown Menu

    An action menu with the menu keyboard model in full: arrows, Home/End, typeahead, and Escape that returns focus to the trigger rather than dropping it on the page body. Its limits — no collision flip, no portal — are stated in the header.

    Overlays & Feedback222 linesNo deps
    Open the full page for this primitive

    Dialog

    A modal on the native dialog element, which supplies the focus trap, inert background and top layer — plus the parts it does not: scroll lock that survives two dialogs, backdrop click, and an alertdialog that ignores it.

    Overlays & Feedback156 lines1 dep
    Open the full page for this primitive

    Tooltip

    Dismissible with Escape, hoverable, and persistent — the three things WCAG 1.4.13 asks of content on hover — shown on keyboard focus rather than every click, and wired with aria-describedby so it is announced even when it is not drawn.

    Overlays & Feedback128 linesNo deps

    Identity

    View all 2
    Open the full page for this primitive

    Avatar Group

    Overlapping faces with a descending stack order, deterministic colours for initials, and an overflow chip announced as "and 3 more" rather than an ambiguous +3.

    Identity148 linesNo deps
    Open the full page for this primitive

    Featured Icon

    The glyph-in-a-tinted-box that every feature grid and empty state is built from, in five tones and four treatments — decorative by default, because it sits next to a heading that says the same thing.

    Identity124 linesNo deps

    Pickers & Media

    View all 6
    Open the full page for this primitive

    Gradient Picker

    Draggable stops with pointer capture, an angle, and the CSS it produces shown and copyable — with the stop list kept sorted, because an unsorted linear-gradient is not an error, it just renders wrong.

    Pickers & Media238 lines1 dep
    Open the full page for this primitive

    Image Picker

    A drop zone that counts drag events instead of flickering on every child boundary, validates on drop where the accept attribute does nothing, and revokes its object URLs.

    Pickers & Media184 lines1 dep
    Open the full page for this primitive

    Credit Card Input

    Brand detection, per-brand digit grouping and CVC length, a Luhn check that catches a transposed digit before the network declines it, and the autocomplete tokens that make a card actually autofill.

    Pickers & Media279 linesNo deps
    Open the full page for this primitive

    QR Code

    A real, scannable symbol with no dependency — Reed-Solomon over GF(256), block interleaving and all eight masks scored by the standard penalty rules. Byte mode, level M, up to 213 bytes.

    Pickers & Media538 linesNo deps

    Date & Time

    View all 5
    Open the full page for this primitive

    Calendar

    A real `role="grid"` month rather than 42 tab stops — one tab stop, arrows for days, PageUp/PageDown for months, and six rows always, so paging never changes the height of what sits below it.

    Date & Time418 lines1 dep
    Open the full page for this primitive

    Date Picker

    The typing half most pickers drop, attached to the calendar: parses on blur, refuses to guess whether 3/4 is March or April, and leaves what it cannot read in the box instead of clearing it.

    Date & Time688 lines1 dep
    Open the full page for this primitive

    Time Picker

    Slots at a fixed step with the taken ones struck through and the time zone rendered beside the value — the three things a booking needs and a native time input cannot say.

    Date & Time266 lines1 dep
    Open the full page for this primitive

    Relative Time

    A real `<time>` that says "3 hours ago" and cannot mismatch on hydration: both sides render the absolute date first, and the relative wording only arrives in an effect. Ticks at an interval scaled to its own age.

    Date & Time165 linesNo deps
    Open the full page for this primitive

    Duration Input

    Three segments that behave like one field — typing past one advances, Backspace on an empty one goes back, arrows carry 59 minutes into the next hour, and pasting `1:30:00` fills all three.

    Date & Time241 linesNo deps

    AI & Chat

    View all 7
    Open the full page for this primitive

    Message Bubble

    One turn in a thread, with the part every chat UI leaves out: the speaker is in the text rather than implied by which side the bubble sits on, so a screen reader hears a conversation instead of an unattributed monologue.

    AI & Chat178 linesNo deps
    Open the full page for this primitive

    Prompt Input

    The composer, reduced to the four things that are actually hard: Enter that does not fire mid-IME-composition, one submit path for button and keyboard alike, stop as a separate button from send, and a row cap measured from the real line height.

    AI & Chat177 lines1 dep
    Open the full page for this primitive

    Tool Call

    A single tool invocation that opens into its arguments and result — status carried by a glyph and a word rather than a colour, arguments as a definition list, and a duration formatted arithmetically so it cannot drift at hydration.

    AI & Chat202 lines1 dep
    Open the full page for this primitive

    Reasoning Panel

    The "Thought for 12s" disclosure, built on a native details element — so it keeps its state without JavaScript, needs no ARIA at all, and renders on the server in the same pass as the answer above it.

    AI & Chat110 lines1 dep
    Open the full page for this primitive

    Citation Chip

    A numbered source reference whose accessible name is the source rather than the numeral — because eight links all called a digit cannot be told apart in a screen reader link list, which is how many people navigate a page.

    AI & Chat134 linesNo deps
    Open the full page for this primitive

    Typing Indicator

    Three dots that stop moving for anyone who asked their OS for less motion, and a polite live region that says who is typing — so the information was never carried by the animation in the first place.

    AI & Chat98 linesNo deps
    Open the full page for this primitive

    Prompt Suggestions

    The starters that fill an empty thread, as a real list of real buttons rather than the usual grid of clickable divs — reachable by keyboard, skippable in one keystroke, and named for the prompt they actually send.

    AI & Chat121 linesNo deps

    Structure

    View all 1
    Open the full page for this primitive

    Content Divider

    A rule with a label on it, built from two growing flex children — so it needs no background colour behind the text and does not break the moment you put it on a card.

    Structure105 linesNo deps

    Frames & Mocks

    View all 4
    Open the full page for this primitive

    Browser Frame

    Desktop browser chrome that wraps whatever you put inside it — a screenshot, a video, or the live component itself. Three variants, no image asset, and the window controls are grey rather than a copy of one vendor’s.

    Frames & Mocks139 lines1 dep
    Open the full page for this primitive

    Phone & Tablet Frame

    One handset bezel with the cut-out as a prop, so iPhone, Android and tablet are three settings rather than three assets. Status bar and home indicator included, and the clock is a prop so it can never be a hydration mismatch.

    Frames & Mocks145 linesNo deps
    Open the full page for this primitive

    Laptop Frame

    A lid, a hinge and a tapered base, with the taper done by clip-path rather than the border trick that cannot round or carry a background. Degrades to a boxier laptop where clip-path is missing.

    Frames & Mocks68 linesNo deps
    Open the full page for this primitive

    Device Showcase

    The product-hero arrangement: a handset overlapping a laptop, overlapped with a negative inline-start margin so both stay in flow and the group keeps an honest height. Stacks below sm instead of shrinking to nothing.

    Frames & Mocks291 linesNo deps