Setup
Everything between installing Abaabil and a themed, accessible control on the screen, in the order you actually hit it.
Install
npm install abaabilPublished as
abaabil@1.1.0. React 19 is the only peer dependency and the package has no runtime dependencies of its own. This site installs it from the registry like anyone else would, so every example on these pages runs against the same published build you get.Pick a tier
This is the single most important idea in the library. Every component ships as three separate entry points, so nothing you don't use gets bundled:
normal
import Button from 'abaabil/button'Structure only. No CSS, no ARIA logic, several entries have no hooks at all. Bring your own styles and behaviour; renders in a Server Component wherever the component allows it.
styled
import Button from 'abaabil/button/styled'Adds the component's CSS. Still hook-free where the normal tier is. This is where a bundler stops being optional (step 06).
a11y
import Button from 'abaabil/button/a11y'Adds the keyboard handling, ARIA attributes and focus management the component needs. The tier most apps should reach for.
For exact numbers: button's a11y tier is 557 B of JS plus 551 B of CSS, gzipped. Every component page on this site prints its own tier, weighed the same way, in its margin.
Import the theme once
// src/main.jsx (or your framework's root entry) import 'abaabil/theme.css';One import, once, at the app root. It sets the cascade layer order and the custom properties (
--color-*,--space-*,--radius-md, ...) every other stylesheet in the library reads from. Skip it and the styled/a11y tiers still render; nothing will be themed, because those custom properties won't exist yet.Theming
:root { --color-primary: #8c2f39; --radius-md: 2px; }Set those two custom properties anywhere and every component reads them live, no rebuild, no prop drilling. The library's own rules live inside
@layer abaabil.components(seeabaabil/theme.css). Cascade layers always lose to any unlayered rule, regardless of selector specificity, so ordinary CSS of yours, written the normal way, with no@layerof its own, wins over the library's styling with no!importantanywhere. This page is themed exactly that way: this site's own CSS (src/globals.css) sits outside every@layer.Server Components
Most entry points carry no
'use client'directive and are built to render in a Server Component tree with zero client JavaScript. Only these need a client boundary:Entry point Boundary abaabil/dialog/a11yclient abaabil/combobox,abaabil/combobox/styled,abaabil/combobox/a11yclient (every tier) abaabil/input/a11yclient abaabil/checkbox/a11yclient abaabil/radio/a11yclient abaabil/select/a11yclient everything else server That includes
button/a11yand every accordion tier, a11y included: none of those need a hook, so none of them carry the directive. Abaabil is designed so most of its entry points can render in a React Server Component tree, but this documentation site itself is a client-rendered single-page app (Vite + React Router), not a server-rendering framework, so it does not and cannot demonstrate that split at runtime. The table above states the library's own boundaries; it is not verified by this site.A bundler is required for styled and a11y
Those two tiers import a
.cssfile. Plain Node has no loader for that extension, so requiring one directly in a Node script throws:Error [ERR_UNKNOWN_FILE_EXTENSION]: Unknown file extension ".css"Next.js, Vite and webpack all resolve CSS imports as part of their normal build, so this is a non-issue in any of them. The
normaltier imports no CSS at all, and works in plain Node.No CSS isn't the same as unstyled
The
normaltier ships no stylesheet of its own, but every tier of a component shares one class name. If any tier's CSS is loaded anywhere on the page, all three tiers pick up that styling, because the class selector doesn't know or care which entry point rendered the element. A page that importsabaabil/button/styledonce styles every plainabaabil/buttonelement on that same page too.Browser support
Chrome 99+, Firefox 98+, Safari 15.4+. Set by
@layerand by Firefox's<dialog>support. CSS anchor positioning is used as progressive enhancement behind@supports, not a hard dependency.