# yarcl > React component library where the consumer's config file is the design system. Every key in the config becomes a typed prop value and a generated CSS class. No codegen, no provider. ## Why yarcl exists yarcl was created because design systems and component libraries disagree about who owns the contract. Most libraries decide the options: buttons come in `sm`, `md` and `lg`, colors are `primary` and `secondary`. When your design system has different names or values, you either live with the library's choices, pass free-form strings and lose type safety, or maintain a second list of types by hand that drifts from the real values. yarcl inverts that: the consumer's config defines the sizes, colors, variants, spacing and text styles, and the library derives both its TypeScript API and its CSS from that one file. The library ships mechanisms (buttons, inputs, dialogs, menus); the config makes the decisions. Benefits: - **Type-safe design tokens.** ` ``` Importing from `@yarcl/react` also loads the generated CSS and the component styles; there is no stylesheet to import. Editing the config hot-reloads the CSS. All yarcl styles use ordered layers: `yarcl.tokens` (generated variables, modifiers, typography and font faces), `yarcl.base` (components and reference), then `yarcl.recipes` (built-in part styles and extensions). Component rules preserve size props, automatic table text sizing and invalid-state colors; recipes can override both layers. Unlayered consumer CSS overrides normal yarcl declarations regardless of specificity or import order, including after `applyTheme`. Declare external layer order before importing libraries: `@layer reset, yarcl, app;`, or with Tailwind 4 `@layer theme, base, yarcl, components, utilities;`. Keep resets layered below yarcl to preserve focus rings and dialog centering. For Starlight, put `@layer starlight, yarcl;` first in its first custom stylesheet. Use `not-content` around component previews. See https://yarcl.dev/configuration/css-layers/. Add `class="yarcl-root"` to the body, or `className="yarcl-root"` to an app root or section, to opt into theme-driven page styles. It uses `neutrals.bg`, `neutrals.text`, the `typography.fonts.body` font role, and size, weight, line height and letter spacing from `defaults.textStyle`. `applyTheme` updates them at runtime. It inherits `color-scheme`, preserving an ancestor's forced light or dark mode; you can also set `style={{ colorScheme: 'dark' }}` on the root itself. Page background and typography stay consumer-owned without this class. Keep layout and margins in your own CSS. ## How the build plugin and tsconfig work together The library imports a placeholder module, `@yarcl/config`. Two pieces of wiring point it at your config file, one for runtime and one for types: - **Build plugin** (`yarcl()` from `@yarcl/react/vite`, `/webpack`, `/rspack`, `/rollup` or `/esbuild`): - aliases `@yarcl/config` to your config file, so components read your values at runtime - loads the config at build time and generates the virtual stylesheet (`@yarcl/react/styles.css`): CSS variables and one class per key - emits `yarcl.tokens.css` in the build output directory by default, containing `:root` variables, `color-scheme` and `.yarcl-type-{key}` text-style classes; set `emitTokens: false` or `emitTokens: ''` to disable, or use a string for a custom output-relative filename - with Vite, also writes this file to `build.outDir` on dev-server startup and updates it when the config or its local imports change, so a separate backend can serve it during development - regenerates the CSS when the config or its imports change - verifies that TypeScript resolves `@yarcl/config` to the same file and reports a clear error when it does not - option `config`: path to the config file, relative to the project root; default `'src/yarcl.config.ts'`. If the file doesn't exist, it falls back to the library defaults. - **tsconfig `paths`**: makes TypeScript resolve `@yarcl/config` to the same file, so prop types are the keys of your config. The second entry is a fallback to the library defaults. - Both must point at the same file. The plugin stops startup if they differ. Re-run `npx @yarcl/react init` to repair the mapping. - With Vite's React template, the app's compiler options live in `tsconfig.app.json`: put `paths` there, not in the root `tsconfig.json` that only has `references`. `paths` resolve relative to the tsconfig file; no `baseUrl` needed. - Tests that run through a build tool need the matching plugin too. With Vitest, add the Vite adapter or reuse the Vite config with `mergeConfig`. ## Configuring - Token props (`size`, `color`, `radius`, `variant`, `gap`, `padding`, `shadow`, `textStyle`, `density`) accept only keys of the project's config. Read the project's `src/yarcl.config.ts` before picking values; don't assume `md` or `primary` exist. - `Type '"md"' is not assignable to ...` means that key isn't in the config: use an existing key or add it. - To add a size, color, variant, spacing step or text style, add a key to its config group. It becomes a valid prop and a rendered style with no other changes. - Open groups (any keys): `colors`, `sizes`, `radii`, `variants`, `spacing`, `shadows`, `density`, `modalSizes`, `typography.styles`. Groups with required keys: `neutrals`, `zIndex`, `motion`, `timing`, `borders`. - Colors are `{ light, dark }` pairs; dark mode follows `color-scheme`. Readable text colors are computed. - `typography.fonts` is optional. Without it, the `body` and `heading` roles use the `sans` family when present, and the `mono` role uses the `mono` family when present. Each otherwise uses the first configured family. - `Button` and `IconButton` render native anchors when given `href`, preserving link semantics and anchor attributes for router navigation. Without `href`, they render native buttons. Link forms do not accept button-only props such as `disabled`, `loading`, or `type`. - `Text` without an explicit text style follows a table cell's density font size, so `muted` and `truncate` work alongside plain cell text. Pass `inherit` to use the surrounding font in any container. An explicit `textStyle` retains its configured style. - `Input` accepts `startContent` and `endContent` for text, icons or buttons inside its shared border. `className` and `style` target the outer control; native form attributes and refs target the input. Mark decorative icons `aria-hidden` and label icon buttons. Padding belongs to the editable input; slot content controls its own spacing. Direct buttons attach with square inner corners and the input's outer corners. Supplied actions keep their own disabled state and focus rings. - `Button` and `Badge` accept `startIcon` and `endIcon` for decorative icons beside their labels. The icon size comes from the selected size's `iconSize`, and spacing follows that size's padding. `Button` hides these icons while loading. - `Button autoHeight` grows to fit multiline content, retaining the selected size's minimum height and token spacing. Compose it with an `Avatar` and a `Stack` of name and email for an account menu trigger. - `Badge` truncates long labels with an ellipsis within its container, preserving icons and remove buttons. Use `wrap` for multiline labels. - `Pagination layout="compact"` shows a live page summary and previous/next buttons at the inline end, filling its available width. The default `layout="numbered"` shows numbered pages with ellipses. `summaryLabel(page, count)` customizes the compact text; no pages displays page 0. Both layouts share configured button styling and retain focus on unavailable boundary controls. - `SplitButton` executes the selected option through `onAction(value)`. Its separate arrow menu changes `value` through `onValueChange` without executing. Options have `value`, `label`, optional decorative `icon` and `disabled`. Both segments follow `components.SplitButton`; menu items follow `components.Menu`. Native attributes and refs target the outer group. - `Menu.RadioGroup` takes a controlled `value` and `onValueChange`; `Menu.RadioItem value="..."` renders `menuitemradio`, `aria-checked`, and a check indicator. Name the group with `aria-label` or `aria-labelledby`. Selecting a radio closes the menu and restores trigger focus. - Single `Combobox` initializes its text from the selected value and follows value and label changes, including arriving options. Typed searches survive option updates until selection, blur or dismissal; changing the selected value resets the search. Controlled `inputValue` takes precedence. - `FileDropzone` defaults to a single-file picker with Replace and Remove controls. Use `value` and `onChange(file | null)` for a controlled cover image, `preview` for a selected image thumbnail, and `previewUrl` plus `previewName` for an existing remote image. `multiple` keeps the file list and `onFilesChange` array callback. In multi-file mode use `files` plus `onFilesChange` for a controlled list, `defaultFiles` for an initial list, and `files={[]}` for upload-on-select. `inputRef` exposes the native file input for an external button to call `.click()`; the root `ref` remains a div. The input resets after selection so the same file can be picked again. Local `labels` customize picker and drop copy. See https://yarcl.dev/components/forms/file-dropzone/. - Wrap sanitized HTML or an editor surface in `.yarcl-prose` to style headings, paragraphs, lists, quotes, code, links, tables, images and rules. It follows `typography.headings`; `typography.prose` optionally selects body and code text styles and spacing keys. Each text style always emits a `-letter-spacing` variable, defaulting to `normal`, and heading levels emit `--yarcl-h1-*` through `--yarcl-h6-*` variables. - Built-in text lives in the required `labels` catalog. Spread `defaults.labels` to translate selected entries; keys are fixed and message formatters receive names or numeric counts. `useLabels()` reads the active typed catalog and re-renders after `applyTheme({ ...currentConfig, labels: translatedCatalog })`; `resetTheme()` restores build-time copy. Explicit instance label/message props win, including empty strings and null ReactNode messages. Dialog/Drawer use `closeLabel`, Alert and toast entries use `dismissLabel`, and FileDropzone accepts a partial `labels` object. DatePicker's `locale` separately controls calendar/date formatting. Visible shortcut modifier labels may be translated while `aria-keyshortcuts` keeps standard tokens. See https://yarcl.dev/configuration/labels/. - Built-in part styles go in `components..slots`, checked by `defineConfig`. Supported components: Table (root frame, header cells, row, cell), Card (root, optional Header/Body/Footer), Dialog/Drawer (root, header/body/footer), Tabs (list/trigger), Menu and shared Listbox (panel/item). Listbox is config-only and styles Select plus single/multiple Combobox. Use token keys for radius, padding, shadow, density and textStyle; background is surface|tint|none; border is solid|dashed|dotted|double|none; borderWidth references borders. Properties are restricted per part, with unknown tokens/parts/properties rejected even through variables. `componentSlots` and `ComponentSlotConfig` are exported from `/define`. Part elements expose stable `data-part` values; Table.header means th, Table.root means its outer frame, and Table.cell defaults also apply to header cells. Use compound table parts for styles, rather than raw tr/th/td. Card.Header/Body/Footer are optional divs with native props and React 19 refs, and add no implicit structure. Explicit root props override slots; slots override component/global defaults. Explicit Table.density overrides cell-slot density; cell padding/textStyle override density spacing/font size; header styles override shared cell styles. Dialog/Drawer header textStyle styles the title too. Active option and selected/striped/hovered row backgrounds keep interaction cues; Tabs.trigger cannot configure borders, preserving its underline. applyTheme swaps generated part CSS while preserving content; resetTheme restores it. Slot rules use yarcl.recipes before consumer recipes and are omitted from token-only CSS. There is no per-instance slots prop; use scoped data-part CSS and compound className props (Table.wrapClassName scopes its frame). Portaled panels are outside trigger ancestors. Guide: https://yarcl.dev/configuration/component-slots/. - Global defaults go in `defaults`; per-component defaults in `components`, e.g. `components: { Button: { radius: 'square' }, Tooltip: { padding: 'sm', textStyle: 'caption' } }`. Props override both. - Components with variants may set `components..variants` to a nonempty map of the same recipes as shared `variants`. Its keys replace shared keys for that component's typed `variant` prop. Other components retain shared fallbacks. `ComponentVariant<'Button'>` is the scoped key type; `Variant` remains shared. Set the component's `variant` default when its map omits the inherited default key; ToggleGroup and Pagination also need a `selectedVariant` default when the local map omits the shared selected key. Label stays plain until given a variant. ButtonGroup uses Button recipes; ToggleGroup, Pagination and AvatarGroup apply their own recipes to children. Explicit ButtonGroup and AvatarGroup child variants win. Local classes are `yarcl-{Component}-variant-{key}`; shared classes remain `yarcl-variant-{key}`. Runtime themes must retain keys the app uses. See https://yarcl.dev/configuration/variants/. - Sized components may set `allowedSizes` to a non-empty subset of global size keys; the component's `size` prop is narrowed to that list. Omit it to allow every global size. `sizeOverrides` partially overrides `height`, `paddingX`, `fontSize` or `iconSize` for a component without restricting its prop type. - Component spacing, typography and radii come from config tokens. `Alert`, `Tooltip` and `Toast` accept token-backed `gap`, `padding`, `textStyle` and `radius` where applicable; `Table` accepts `radius` for its frame. - Style with props and config, not inline styles. Custom CSS can use the generated variables, e.g. `var(--yarcl-color-brand)`, `var(--yarcl-space-md)`. - Imports: components and `toast` from `@yarcl/react`; config helpers from `/define` and `/defaults`; build plugins from `/vite`, `/webpack`, `/rspack`, `/rollup` or `/esbuild`; bundled themes from `@yarcl/react/themes`; `applyTheme` from `@yarcl/react/css`. - "Failed to resolve import @yarcl/config" means the build plugin is missing. Type errors on `@yarcl/config` mean the tsconfig `paths` entry is missing or points at a different file. ## Component recipes - Use `defineConfig(baseConfig, (yarcl) => ({ recipes: { ... } }))` to define custom styles. The callback's `yarcl.colors.success`, `yarcl.spacing.sm`, `yarcl.radii.md`, and other groups autocomplete the actual config keys and return serializable CSS variable references. - Every recipe has `slots.root`; extra slots are named by the consumer. `variants` maps axes to choices to slot styles. `defaults` selects omitted choices. `compounds` supplies `{ when, slots }` for combinations. Slot names, default choices and compound references are checked at compile time. - `createComponent('Action', Button)` adds the config recipe's typed visual props to an existing component, preserves its behavior and refs, and merges root classes. Recipe axes cannot replace inherited props. - `createComponent('Status', 'div', ({ rootProps, slots }) => ...)` builds custom markup. Spread `rootProps` onto the root and apply `slots.label`, etc. to declared elements. Only declared recipe names, slots and choices are valid. Recipes do not supply accessibility behavior for arbitrary markup. - `useRecipe(name, props)` supports custom behavior and state. Remove your behavior props before spreading its `rootProps`; configured recipe props are consumed automatically. `ExtendedComponentProps<'Status', 'div'>` combines native props with inferred visual props. - Style objects use normal CSS property names, token references, literal CSS strings and `var(--external)` expressions. Support `&:hover`, nested `@media` and `@supports`, and custom properties. Dimensional numbers receive px; unitless and custom-property numbers do not. - `tokens(baseConfig)` and `defineRecipes(...)` from `/define` support separate recipe modules. Do not import the final config or React entry point inside config definitions. Keep token definitions independent to avoid circular imports. - The existing plugin generates recipe CSS. Runtime themes must preserve recipe names, slots, choices and referenced tokens. `applyTheme` updates recipe CSS and defaults; `resetTheme` restores them. Token-only CSS assets exclude component recipes. - Full guide: https://yarcl.dev/configuration/component-recipes/ ## Working in a yarcl project - Start by reading `src/yarcl.config.ts` (or the file passed to the build plugin): it lists every valid size, color, variant, spacing step and text style. - Props and JSDoc for every component ship as declarations: `node_modules/@yarcl/react/dist/components/.d.ts`. - To type your own components with the same tokens: `import type { Size, ComponentSize, Color, Variant, Radius, Spacing, TextStyle } from '@yarcl/react'`. `Size` is every global size; `ComponentSize<'Button'>` respects that component's `allowedSizes`. - Config values at runtime: `config` from `@yarcl/react`, or `useConfig()` inside components (follows runtime theme switches). - Icons are plain `` children, sized from the size's `iconSize`. `IconButton` requires `aria-label`. - The plugin warns at build time when a color's text fails WCAG AA contrast; adjust the color or set its `on` (text color) explicitly. - `radius="size"` picks the radius named like the control's size; set `defaults.radius: 'size'` to make that the default. ## Theming - **Dark mode**: every color is a `{ light, dark }` pair rendered with `light-dark()`. It follows the OS by default; set `color-scheme: light` or `dark` on any element to force a mode. No JavaScript needed. - **Bundled themes** in `@yarcl/react/themes`: `brutalist`, `bloom`, `compact`, `editorial`, `cyberpunk`, `vermeer`, `artDeco`, `circuit` and `studio`, plus the library defaults (`@yarcl/react/defaults`). Cyberpunk has neon pink and cyan, monospace type and luminous panels; Vermeer has blue and ochre with full serif typography; Art Deco has geometric type and gold double frames; Circuit has cyan and navy surfaces with monospace labels; Studio has bold type, large controls and cobalt with citrus accents. All include light and dark modes. - **One theme per build**: make the config file the theme, `export { editorial as default } from '@yarcl/react/themes';`, or spread it and override: `defineConfig({ ...bloom, colors: { ...bloom.colors, brand: { light: '#4f46e5', dark: '#a5b4fc' } } })`. - **Several themes from one codebase** (white-label builds): keep one config file per theme and pick it in `vite.config.ts`, e.g. ``yarcl({ config: `src/themes/${process.env.THEME ?? 'default'}.ts` })``. - **Runtime switching**: `applyTheme(themes.bloom)` from `@yarcl/react/css` swaps the CSS and the defaults without a rebuild; `resetTheme()` returns to the build-time config. Prop types still come from the build-time config, so a runtime theme must define every key the app uses. - **Theme contract**: themes are interchangeable when they share keys. Check a theme with `satisfies ThemeContract` (from `@yarcl/react/themes`), or your own type listing the keys your app uses; a missing key is a type error. - **Beyond colors**: fonts (`typography.fontFaces`), text styles, radii, shadows, spacing, density, the focus ring, motion and per-component defaults (e.g. pill buttons) are all part of a theme. - Try themes live in the [theme playground](https://yarcl.dev/theme-playground/). ## Components - Buttons: `Button`, `IconButton`, `ButtonGroup`, `ToggleGroup` - Forms: `Field`, `Label`, `Input`, `Textarea`, `NumberInput`, `ColorPicker`, `Select`, `Combobox` (search, free text, async, `multiple` with chips), `DatePicker` (single and range, date-fns locales), `Checkbox`, `RadioGroup` + `Radio`, `Switch`, `Slider` (marks and colored segments) - Typography: `Text` (`whiteSpace="pre-wrap"` preserves line breaks, `wrap="anywhere"` wraps long words), `Heading` (`level` for semantics, `textStyle` for look), `Link` - Layout: `AppLayout`, `Stack`, `Inline`, `Card`, `Divider` - Overlays: `Dialog`, `Drawer`, `Popover`, `Menu`, `Tooltip`, `HoverCard`, `CommandPalette`, `toast` + one `` - Data display: `Tabs`, `Table`, `Accordion`, `Pagination`, `Breadcrumb` - `useTableColumns(definitions, options)` infers literal column IDs. Definitions require id, label and positive finite pixel width; resizable: true requires finite 0 < minWidth < maxWidth with the initial width inside those bounds. Render model.visibleColumns in Table.Columns, header cells and every body row, and pass model.tableStyle to Table for fixed layout and exact summed widths. Table.HeaderCell.resize={model.getResizeProps(id)} adds an independent keyboard/pointer separator beside any sort button; only resizable IDs are accepted. Left/Right respect RTL, PageUp/PageDown use largeStep, Home/End reach limits; native handlers can cancel with preventDefault. Table.ColumnVisibility takes model.columns, label and onVisibilityChange={model.setVisible}; hideable: false keeps required columns visible, and the last visible column cannot be hidden. widths/defaultWidths/onWidthsChange and visibility/defaultVisibility/onVisibilityChange independently control accepted state; callbacks receive the next complete map, and controlled UI waits for accepted props. setWidth/setVisible are typed by column IDs. Hidden columns retain widths; newly added IDs use their definition. React 19 refs target native th, colgroup, fieldset and span handles. Measured virtual rows invalidate widths and update spacer spans after visibility changes; sticky headers and selection continue to work. External removal of a focused column restores focus to its table frame. Widths are layout data; appearance uses existing Table, Checkbox and config tokens. Guide: https://yarcl.dev/components/data/table-columns/. - `Table.VirtualBody` supports measured variable heights with positive `estimateRowHeight` and required `getItemKey` returning stable unique IDs. Render one `Table.Row` or `tr` per item; custom row components must spread props onto their `tr`. `ResizeObserver` refreshes visible heights, and table width, density and theme changes invalidate cached heights. Focused rows stay mounted for keyboard traversal. Pass `rowHeight` instead for explicitly equal-height rows, including padding and borders. `overscan` must be a nonnegative integer; `scrollRef` optionally selects an ancestor scroll container. Unvisited rows use the estimate, so scrollbar accuracy improves as rows are visited. Use `Table.Body` when every row must be present. - Feedback: `Badge`, `Alert`, `Spinner`, `Skeleton`, `Progress`, `AudioPlayer` (playback, seeking, optional input level meter) - `DesignReference` from `@yarcl/react/reference` renders the whole design system from the config. Conventions: - Wrap form controls in `Field` for the label, helper text and error wiring; don't set the control's `id`. - Stateful components are controlled or uncontrolled with `value` / `defaultValue` / `onValueChange` (`open` / `onOpenChange` for overlays). - Structured widgets are compound: `Tabs.List` / `Tabs.Trigger` / `Tabs.Panel`, `Menu.Trigger` / `Menu.Item`, `Accordion.Item`, `Breadcrumb.Item`, `Table.Row`, `Popover.Content`. - `Select` and `Combobox` take their options as data (`options={[{ value, label }]}`), not children; `CommandPalette` takes `commands`. - Hover delays and toast duration come from the `timing` config group; the matching props override them per instance. - Every component passes through native attributes, `className` and `style`. ## Docs - [Installation](https://yarcl.dev/getting-started/installation/) - [Quick start](https://yarcl.dev/getting-started/quick-start/) - [The config file](https://yarcl.dev/configuration/config-file/): every group and what `defineConfig` checks - [Colors](https://yarcl.dev/configuration/colors-and-theming/) - [Sizes and radii](https://yarcl.dev/configuration/sizes-and-radii/) - [Variants](https://yarcl.dev/configuration/variants/) - [Typography](https://yarcl.dev/configuration/typography/) - [Extending components](https://yarcl.dev/configuration/component-recipes/): recipes, typed tokens, custom slots, behavior and themes - [Component parts](https://yarcl.dev/configuration/component-slots/): typed built-in slot styling and stable data-part attributes - [Defaults](https://yarcl.dev/configuration/component-defaults/) - [Generated CSS](https://yarcl.dev/configuration/generated-css/): CSS variables and classes - [Build plugins](https://yarcl.dev/configuration/build-plugins/): Vite, webpack, Rspack, Rollup and esbuild setup, options, fallback and watching - [TypeScript](https://yarcl.dev/configuration/typescript/): how prop types come from your config - [Creating a theme](https://yarcl.dev/theming/creating-a-theme/) - [Switching themes](https://yarcl.dev/theming/switching-themes/): build-time, per-build and runtime - [Bundled themes](https://yarcl.dev/theming/bundled-themes/) - [Components](https://yarcl.dev/components/): every component with examples and props tables - [API reference](https://yarcl.dev/reference/api/) - [Source](https://github.com/eugenioenko/yarcl) - `AppLayout` builds a viewport-height application frame with a top navbar, desktop sidebar, optional footer and independently scrolling main content. Required `navigation`, `navigationLabel`, `desktopBreakpoint` (a key of `config.breakpoints`) and `sidebarWidth` (a key of `config.widths`) avoid assumptions about consumer key names. Example: `}>Projects} navbar={Acme} footer={Support}>Projects`. Below the viewport breakpoint, a burger opens a left modal drawer with native focus management, Escape, close button and backdrop dismissal. Ordinary link clicks also close it; modified clicks, downloads and new-tab links keep it open. `collapsed` supplies an icon rail context on desktop only. `navigationOpen`, `defaultNavigationOpen` and `onNavigationOpenChange` control the mobile drawer; switching to desktop requests closing it. Navigation mounts on the client once, retaining component state and DOM across mode changes and drawer dismissal. Main content renders on the server. Use `mainProps` for native main attributes, ref and scroll handlers; `mainAs="section"` when embedding inside another main landmark. Override root `style.height` for a contained workspace. `padding` resolves through `components.AppLayout.padding` then global defaults. Widths and breakpoint queries update with runtime themes. See https://yarcl.dev/components/layout/app-layout/. - `NavSection title="Workspace"` names a navigation group. `collapsed` hides the heading visually and makes descendant `NavItem` links icon rails. Items can override it with `collapsed={false}`. `NavItem collapsed` keeps its text accessible and shows a right-side tooltip on hover or keyboard focus. Provide icons for collapsed items; links without icons remain expanded. Native anchor props, refs and router handlers are preserved. Section `gap` and `textStyle` resolve through `components.NavSection`, then global defaults. See https://yarcl.dev/components/navigation/nav-section/. ## Responsive props Use ``, ``, or ``. Both breakpoint names and spacing values are typed from the consumer config. Exported `Responsive` accepts a scalar or readonly optional breakpoint map. Existing scalar props work unchanged. Supported: Stack gap/align/justify; Inline gap/align/justify/wrap; Grid gap/columns; Card padding; Alert and EmptyState gap/padding; NavSection gap; AppLayout padding; Tooltip, HoverCard and Popover.Content padding; toast(options) gap/padding. Component config defaults stay scalar. `base` applies before matching viewport thresholds and is reserved as a breakpoint name. Declare config.breakpoints in ascending threshold order; that order determines cascading overrides, regardless of prop key order. Thresholds are inclusive min-width queries. Sparse maps retain the last matching value. Missing base spacing uses component defaults, then global defaults. Inline falls back to center alignment and wrap=true; Grid columns fall back to one. A responsive Card padding map explicitly overrides root slot padding at every viewport, falling back to component/global padding below its first threshold; other slots keep their settings. Grid minItemWidth overrides the entire columns map; raw tracks use inline custom properties as before, while spacing uses token classes. CSS handles responsiveness and SSR without viewport hooks or remounting children. applyTheme regenerates queries and values from the active config. Keep referenced token and breakpoint keys available across applied themes. Unlayered consumer CSS and recipe precedence still apply. Breakpoints use viewport width, not container width. Full guide: https://yarcl.dev/configuration/responsive-props/. ## TreeView `TreeView` renders a named hierarchy from items, each with a unique id, noninteractive label, optional textValue, decorative icon, disabled, selectable and nested children. Supply aria-label or aria-labelledby. Default single selection uses value/defaultValue as an ID or null; selectionMode="multiple" uses ID arrays; selectionMode="none" omits selection. onValueChange reports selection; focus movement does not select. expanded/defaultExpanded are parent ID arrays, with onExpandedChange. Const item arrays infer identifier unions. size/radius/color use consumer keys and components.TreeView defaults, including allowedSizes and sizeOverrides. Native attributes and React 19 refs reach the root div. Up/Down navigate visible nodes without wrapping; Right expands/enters a parent; Left collapses/returns to a parent; Home/End reach the edges. Expansion arrows mirror in RTL. Enter/Space select or toggle multiple selection; in none mode they toggle expansion. Type-ahead searches textValue or labels using timing.typeaheadTimeout; repeated characters cycle matches; * expands enabled siblings. Disabled nodes remain discoverable but cannot select/expand; a disabled root leaves the tab order. A single roving tab stop restores focus after ancestor collapse or focused-item removal. Nonselectable folders expand without selection. Collapsed children stay mounted and hidden. Tree labels should not contain links or controls; use NavItem for ordinary page navigation. See https://yarcl.dev/components/navigation/tree-view/. ## SplitPane Import `SplitPane` from `@yarcl/react`. Pass `primary`, `secondary` and required `primaryLabel`; optional `secondaryLabel` names the other region. `orientation` describes pane arrangement: horizontal means a vertical separator, vertical means a horizontal separator. `value` / `defaultValue` are the first pane's percentage, with `onValueChange` and `onValueCommit`. Defaults are 50 percent with min 10, max 90, step 1 and largeStep 10. Limits must satisfy 0 <= min < max <= 100, and steps must be positive and finite. Arrow keys follow the layout axis and RTL, Home/End reach bounds, PageUp/PageDown make larger adjustments, Enter minimizes/restores. Zero-size panes are hidden while mounted; focus returns to the separator if a focused pane collapses. Disabled prevents resizing and removes the separator's tab stop. Panes have their own tab stops so text-only content can be scrolled by keyboard. Nest split panes for more regions; give vertical layouts a definite height. Size, radius and color use config keys and runtime component defaults. Only caller layout percentages use inline custom properties. Native root attributes, events and ref are supported. Docs: /components/layout/split-pane/. ## Stepper Import `Stepper` and `StepperItem` from `@yarcl/react`. Pass a named ordered list through `items`, with an `id` unique within that stepper, noninteractive `label` / `description`, optional `completed` and `disabled`. Const item arrays infer valid IDs for `value`, `defaultValue` and `onValueChange`. Uncontrolled current stage defaults to the first enabled item; explicit null means no current stage. Completion is independent of selection and order. Controlled values report requests and wait for props to update. Interactive stages use native buttons and one roving tab stop; arrow keys follow orientation and RTL, Home/End reach enabled edges, and Enter/Space activate. Arrow focus does not select. Disabled stages are skipped. `readOnly` renders static ordered progress with no buttons; current uses aria-current="step", and completion text comes from labels.stepCompleted. Native attributes/ref reach the ol. Size, radius, color and responsive gap use consumer config keys and runtime component defaults, with no inline token styles. Docs: /components/navigation/stepper/. Stepper stages are connected by a timeline in horizontal and vertical orientation, mirrored in RTL. Completed stages color their outgoing connector; the last stage has no outgoing connector. Use the existing typed radius prop for circular or normal rounded indicators. Defaults and bundled themes set components.Stepper.radius to the circular rounded token; consumer configs can use any radius key. Vertical descriptions wrap alongside top-aligned indicators. See /components/navigation/stepper/. ## ColorPicker Import ColorPicker and ColorPickerValue from @yarcl/react. Supply an opaque hex value or defaultValue with three or six digits; values and callbacks normalize to lowercase six-digit hex. The native chooser and optional named presets select immediately. Hex text is a draft until Enter or blur; invalid text and Escape restore the accepted color. The first Enter commits without submitting; the next submits. Controlled previews and form data wait for accepted props. Name submits a single accepted color through a hidden input, so partial drafts never enter FormData. Uncontrolled state and drafts reset with the associated form, including explicit form attributes. Disabled prevents all interaction and submission; readOnly retains a focusable text value while disabling the chooser and presets. Use Field for labeling, helper and error wiring, or supply aria-label/aria-labelledby. Native attributes, ref and handlers target the text input; className/style target the outer control. Picker and preset group names come from labels.chooseColor and labels.colorPresets and have instance overrides. Size, radius and color are typed design token keys; chosen colors and preset swatches are application data. Docs: /components/forms/color-picker/.