Color Swatch Picker
A palette of colors to choose one from.
Usage
ColorSwatchPicker is a set of colors you have already decided on: a brand palette, a theme's accents, the finishes a product comes in. Where Color Area and Color Slider let someone reach any color at all, the picker offers a fixed list and nothing else.
Each ColorSwatchPickerItem takes a color and renders a Color Swatch inside a button. The value is the same Color the rest of the family uses, so a picker sits in a larger control without converting anything.
Colors are matched on their 8-digit hex, so the same color written two ways is one entry: an item with color="#ff0000" is selected by a value of hsl(0, 100%, 50%). Give the picker a name with aria-label - it has no visible text of its own.
Inside a Color Picker the value comes from the picker, so a palette drops in as presets with no wiring: see Presets.
Examples
Layouts
layout="grid" is the default: a row of swatches that wraps when it runs out of width. layout="stack" puts them in a single column instead, for a sidebar or a narrow panel. The selection indicator travels either way, and the arrow keys follow the layout.
Shapes
shape applies to the swatch, to the button and to the indicator at once, so the three stay concentric. The corner is a percentage of the button, so it holds its proportions at every size.
Sizing
size uses the same ladder as Color Swatch, 3xs 16px through xl 64px, and sets the button. The swatch inside is 80% of it, which leaves the gap the selected ring sits in. Both are ems off one font size, so the ring, the gap and the swatch scale together rather than the gap staying put as the swatch grows.
Naming colors
A hex string read aloud is a string of digits. colorName replaces the description the swatch builds from the color with the name your palette actually uses, and that name is what the option is announced as.
Translucent swatches
An item below full opacity gets the checkerboard the swatch always draws, so a palette of tints reads as tints rather than as four shades of the same flat blue.
Alongside a picker
Presets and a full picker over one piece of state: pick a common color in a click, or open up the area and sliders for anything else. Selecting a preset moves the area and both sliders, and dragging any of them clears the preset, because no swatch matches any more.
A hex preset is an RGB color, which has no saturation or brightness, so the area is pinned with colorSpace="hsb" rather than left to follow the value's own space.
Disabled
disabled on an item takes it out of the tab order and out of the arrow-key run, and gives it the treatment the whole family shares: a flat muted fill inside a dashed outline, dimmed. On the root it does the same to every swatch.
RTL
Every Appica UI component supports right-to-left layouts out of the box. Set the dir attribute on a container (commonly your <html> element) so CSS logical properties resolve correctly, and wrap your tree in DirectionProvider so direction-aware behavior (roving focus, popup placement, and the like) follows the same direction.
The swatches run from the right, and ←/→ swap so the arrow pointing at the next swatch is the one that reaches it. A stack is unaffected in either direction. The indicator is measured from the rendered layout rather than from an index, so it lands where the swatches actually are. For setup details and caveats, see the RTL guide.
API reference
ColorSwatchPicker
Every other <div> attribute is forwarded to the root. The root carries data-layout and data-disabled; the parts are addressable through data-slot (color-swatch-picker, color-swatch-picker-item, color-swatch-picker-indicator).
ColorSwatchPickerItem
Every other <button> attribute is forwarded to the button, which carries data-value (the color's 8-digit hex) and data-disabled.
The color model - Color, parseColor, formatColor, convertColor and the channel helpers - ships from @appica/ui-react/color and is documented on the Color Area page.
Accessibility
- The palette is a
role="listbox"ofrole="option"buttons witharia-selected, following React Aria's model: a set of colors is a list you choose from, not a set of form fields. - Each option is named by its color -
vivid blue,dark muted green- or bycolorNamewhen you supply one. The swatch inside is hidden from assistive technology so the name is not read twice. - Keyboard: the palette is one tab stop, landing on the selected swatch. ←/→ move between swatches (swapped in RTL), ↑/↓ jump a row in a grid or a step in a stack, and Home/End go to the ends. Selection follows focus, so arrowing through the palette picks as it goes.
- Selection is drawn as a single indicator that slides to the chosen swatch, rather than a border toggled on each one, so what a sighted user sees is one object moving. It honors
prefers-reduced-motion, as does the press animation. - The indicator's position is measured from the rendered layout, so it stays correct when the row wraps, the container resizes, or the direction flips.
- A disabled swatch takes the same flat muted fill and dashed outline the area, the slider and the swatch use, so an unavailable color reads the same wherever it appears.