# Color picker

A field or a swatch that opens a panel to choose a color: by dragging in a square and along strips, by typing its code, or by picking a saved swatch.

Block: `smbk-color-picker`. Status: experimental. Figma: the Figma file, https://www.figma.com/community/file/1688324308358870630. Desktop and mobile: differ by presentation only.

## Options

| Axis | Values | Default | Meaning |
|---|---|---|---|
| `type` | `field`, `swatch` | `field` | Field shows the color and its code with a caret, as a select does; Swatch shows the color alone, for toolbars and tight rows. |
| `size` | `md`, `sm` | `md` | The input’s two heights. Field holds a 20 or 16 px swatch; Swatch is a 40 or 32 px square holding a 24 or 16 px one. |
| `error` | on / off | off | The color is not one the form can take. Draws the input’s danger border on the trigger. |
| `open` | on / off | off | The panel is showing. Set by the component while it is open; the caret turns up. |

Parts: `smbk-color-picker__trigger`, `smbk-color-picker__swatch`, `smbk-color-picker__value`, `smbk-color-picker__name`, `smbk-color-picker__caret`, `smbk-color-picker__panel`, `smbk-color-picker__area`, `smbk-color-picker__slider`, `smbk-color-picker__code`, `smbk-color-picker__format`, `smbk-color-picker__field`, `smbk-color-picker__eyedropper`, `smbk-color-picker__swatches`, `smbk-color-picker__divider`

## Markup

```html
<span class="smbk-color-picker smbk-color-picker--type-field smbk-color-picker--size-md">
  <div class="smbk-popover__anchor">
    <button
      type="button"
      id="color-picker-1-opener"
      class="smbk-input smbk-input--size-md smbk-select__well smbk-color-picker__trigger"
      aria-label="Brand color, #3B5CE3, dark vibrant blue"
      aria-haspopup="dialog"
      aria-expanded="false"
      aria-controls="color-picker-1-panel"
    >
      <span class="smbk-input__leading-content">
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-sm smbk-color-swatch--shape-square smbk-color-picker__swatch"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(59, 92, 227, 1)"></span></span>
      </span>
      <span class="smbk-select__value smbk-color-picker__value" aria-hidden="true">#3B5CE3</span>
      <span
        id="color-picker-2-value"
        class="smbk-color-picker__name"
      >#3B5CE3, dark vibrant blue</span>
      <i
        class="ph ph-caret-down smbk-icon smbk-icon--size-md smbk-input__icon smbk-select__icon smbk-color-picker__caret"
        aria-hidden="true"
      ></i>
    </button>
    <div class="smbk-popover__layer">
      <div
        id="color-picker-1-panel"
        role="dialog"
        aria-label="Color picker"
        class="smbk-popover smbk-popover--align-start smbk-popover--side-below smbk-color-picker__panel"
        tabindex="-1"
        data-scrollbar=""
        hidden=""
      >
        <div
          id="react-aria-color-picker-3"
          role="group"
          style="position:relative;touch-action:none;forced-color-adjust:none;background:linear-gradient(to top, black, transparent), linear-gradient(to right, hsla(228.21, 0%, 100%, 1), transparent), hsla(228.21, 100%, 50%, 1)"
          class="smbk-color-area smbk-color-picker__area"
        >
          <div
            style="position:absolute;left:74.01%;top:10.98%;transform:translate(-50%, -50%);touch-action:none;forced-color-adjust:none;background-color:hsla(228.21, 75%, 56.08%, 1)"
            role="presentation"
            class="smbk-color-thumb smbk-color-area__thumb"
          ><input id="react-aria-color-picker-4" aria-label="Color picker" style="border:0;clip:rect(0 0 0 0);clip-path:inset(50%);height:100%;margin:-1px;overflow:hidden;padding:0;position:absolute;width:100%;white-space:nowrap;opacity:0.0001;pointer-events:none" type="range" min="0" max="100" step="1" aria-roledescription="2D slider" aria-valuetext="Saturation: 74%, Brightness: 89%, Hue: 228.21°, dark vibrant blue" aria-orientation="horizontal" value="74.01"/><input id="react-aria-color-picker-5" aria-label="Color picker" style="border:0;clip:rect(0 0 0 0);clip-path:inset(50%);height:100%;margin:-1px;overflow:hidden;padding:0;position:absolute;width:100%;white-space:nowrap;opacity:0.0001;pointer-events:none" type="range" min="0" max="100" step="1" aria-roledescription="2D slider" aria-valuetext="Brightness: 89%, Saturation: 74%, Hue: 228.21°, dark vibrant blue" aria-orientation="vertical" tabindex="-1" aria-hidden="true" value="89.02"/></div>
        </div>
        <div class="smbk-color-slider smbk-color-slider--channel-hue smbk-color-slider--size-md smbk-color-picker__slider">
          <div
            role="group"
            id="react-aria-color-picker-6"
            aria-label="Hue"
            style="position:relative;touch-action:none;forced-color-adjust:none"
            class="smbk-color-slider__track"
          ><span class="smbk-color-slider__gradient" style="background:linear-gradient(to right, hsla(0, 100%, 50%, 1), hsla(60, 100%, 50%, 1), hsla(120, 100%, 50%, 1), hsla(180, 100%, 50%, 1), hsla(240, 100%, 50%, 1), hsla(300, 100%, 50%, 1), hsla(360, 100%, 50%, 1))"></span><div class="smbk-color-slider__rail"><div style="position:absolute;left:63.33333333333333%;transform:translate(-50%, -50%);touch-action:none;forced-color-adjust:none;background-color:hsla(228.21000000000004, 100%, 50%, 1)" class="smbk-color-thumb smbk-color-thumb--size-md smbk-color-slider__thumb"><input tabindex="0" id="react-aria-color-picker-6-0" aria-labelledby="react-aria-color-picker-6" type="range" min="0" max="360" step="1" aria-orientation="horizontal" aria-valuetext="228.21°, blue" aria-describedby="" aria-details="" style="border:0;clip:rect(0 0 0 0);clip-path:inset(50%);height:100%;margin:-1px;overflow:hidden;padding:0;position:absolute;width:100%;white-space:nowrap;opacity:0.0001;pointer-events:none" value="228"/></div></div></div>
        </div>
        <div class="smbk-color-slider smbk-color-slider--channel-alpha smbk-color-slider--size-md smbk-color-picker__slider">
          <div
            role="group"
            id="react-aria-color-picker-7"
            aria-label="Opacity"
            style="position:relative;touch-action:none;forced-color-adjust:none"
            class="smbk-color-slider__track"
          ><span class="smbk-color-checker"></span><span class="smbk-color-slider__gradient" style="background:linear-gradient(to right, rgba(59, 92, 227, 0), rgba(59, 92, 227, 1))"></span><div class="smbk-color-slider__rail"><div style="position:absolute;left:100%;transform:translate(-50%, -50%);touch-action:none;forced-color-adjust:none;background-color:rgba(59, 92, 227, 1)" class="smbk-color-thumb smbk-color-thumb--size-md smbk-color-slider__thumb"><input tabindex="0" id="react-aria-color-picker-7-0" aria-labelledby="react-aria-color-picker-7" type="range" min="0" max="1" step="0.01" aria-orientation="horizontal" aria-valuetext="100%" aria-describedby="" aria-details="" style="border:0;clip:rect(0 0 0 0);clip-path:inset(50%);height:100%;margin:-1px;overflow:hidden;padding:0;position:absolute;width:100%;white-space:nowrap;opacity:0.0001;pointer-events:none" value="1"/></div></div></div>
        </div>
        <div class="smbk-color-picker__code">
          <span class="smbk-select smbk-select--size-sm smbk-color-picker__format">
            <button
              type="button"
              id="selectcolor-picker-8"
              class="smbk-input smbk-input--size-sm smbk-select__well"
              role="combobox"
              aria-haspopup="listbox"
              aria-expanded="false"
              aria-label="Color format"
            >
              <span class="smbk-select__value">Hex</span>
              <i
                class="ph ph-caret-down smbk-icon smbk-icon--size-md smbk-input__icon smbk-select__icon"
                aria-hidden="true"
              ></i>
            </button>
          </span>
          <span class="smbk-input smbk-input--size-sm smbk-color-field smbk-color-field--size-sm smbk-color-picker__field">
            <span class="smbk-input__leading-content">
              <span
                aria-hidden="true"
                class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square smbk-color-field__swatch"
              ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(59, 92, 227, 1)"></span></span>
            </span>
            <input
              id="react-aria-color-picker-9"
              aria-label="Color code"
              aria-describedby="react-aria-color-picker-10 react-aria-color-picker-11"
              type="text"
              autoComplete="off"
              autoCapitalize="off"
              autoCorrect="off"
              spellCheck="false"
              tabindex="0"
              role="textbox"
              class="smbk-input__control smbk-color-field__control"
              value="#3B5CE3"
            >
          </span>
        </div>
      </div>
    </div>
  </div>
</span>
<div
  role="dialog"
  aria-label="Color picker"
  class="smbk-popover smbk-popover--align-start smbk-popover--side-below smbk-color-picker__panel"
>
  <div
    id="react-aria-color-picker-12"
    role="group"
    style="position:relative;touch-action:none;forced-color-adjust:none;background:linear-gradient(to top, black, transparent), linear-gradient(to right, hsla(228.21, 0%, 100%, 1), transparent), hsla(228.21, 100%, 50%, 1)"
    class="smbk-color-area smbk-color-picker__area"
  >
    <div
      style="position:absolute;left:74.01%;top:10.98%;transform:translate(-50%, -50%);touch-action:none;forced-color-adjust:none;background-color:hsla(228.21, 75%, 56.08%, 1)"
      role="presentation"
      class="smbk-color-thumb smbk-color-area__thumb"
    ><input id="react-aria-color-picker-13" aria-label="Color picker" style="border:0;clip:rect(0 0 0 0);clip-path:inset(50%);height:100%;margin:-1px;overflow:hidden;padding:0;position:absolute;width:100%;white-space:nowrap;opacity:0.0001;pointer-events:none" type="range" min="0" max="100" step="1" aria-roledescription="2D slider" aria-valuetext="Saturation: 74%, Brightness: 89%, Hue: 228.21°, dark vibrant blue" aria-orientation="horizontal" value="74.01"/><input id="react-aria-color-picker-14" aria-label="Color picker" style="border:0;clip:rect(0 0 0 0);clip-path:inset(50%);height:100%;margin:-1px;overflow:hidden;padding:0;position:absolute;width:100%;white-space:nowrap;opacity:0.0001;pointer-events:none" type="range" min="0" max="100" step="1" aria-roledescription="2D slider" aria-valuetext="Brightness: 89%, Saturation: 74%, Hue: 228.21°, dark vibrant blue" aria-orientation="vertical" tabindex="-1" aria-hidden="true" value="89.02"/></div>
  </div>
  <div class="smbk-color-slider smbk-color-slider--channel-hue smbk-color-slider--size-md smbk-color-picker__slider">
    <div
      role="group"
      id="react-aria-color-picker-15"
      aria-label="Hue"
      style="position:relative;touch-action:none;forced-color-adjust:none"
      class="smbk-color-slider__track"
    ><span class="smbk-color-slider__gradient" style="background:linear-gradient(to right, hsla(0, 100%, 50%, 1), hsla(60, 100%, 50%, 1), hsla(120, 100%, 50%, 1), hsla(180, 100%, 50%, 1), hsla(240, 100%, 50%, 1), hsla(300, 100%, 50%, 1), hsla(360, 100%, 50%, 1))"></span><div class="smbk-color-slider__rail"><div style="position:absolute;left:63.33333333333333%;transform:translate(-50%, -50%);touch-action:none;forced-color-adjust:none;background-color:hsla(228.21000000000004, 100%, 50%, 1)" class="smbk-color-thumb smbk-color-thumb--size-md smbk-color-slider__thumb"><input tabindex="0" id="react-aria-color-picker-15-0" aria-labelledby="react-aria-color-picker-15" type="range" min="0" max="360" step="1" aria-orientation="horizontal" aria-valuetext="228.21°, blue" aria-describedby="" aria-details="" style="border:0;clip:rect(0 0 0 0);clip-path:inset(50%);height:100%;margin:-1px;overflow:hidden;padding:0;position:absolute;width:100%;white-space:nowrap;opacity:0.0001;pointer-events:none" value="228"/></div></div></div>
  </div>
  <div class="smbk-color-slider smbk-color-slider--channel-alpha smbk-color-slider--size-md smbk-color-picker__slider">
    <div
      role="group"
      id="react-aria-color-picker-16"
      aria-label="Opacity"
      style="position:relative;touch-action:none;forced-color-adjust:none"
      class="smbk-color-slider__track"
    ><span class="smbk-color-checker"></span><span class="smbk-color-slider__gradient" style="background:linear-gradient(to right, rgba(59, 92, 227, 0), rgba(59, 92, 227, 1))"></span><div class="smbk-color-slider__rail"><div style="position:absolute;left:100%;transform:translate(-50%, -50%);touch-action:none;forced-color-adjust:none;background-color:rgba(59, 92, 227, 1)" class="smbk-color-thumb smbk-color-thumb--size-md smbk-color-slider__thumb"><input tabindex="0" id="react-aria-color-picker-16-0" aria-labelledby="react-aria-color-picker-16" type="range" min="0" max="1" step="0.01" aria-orientation="horizontal" aria-valuetext="100%" aria-describedby="" aria-details="" style="border:0;clip:rect(0 0 0 0);clip-path:inset(50%);height:100%;margin:-1px;overflow:hidden;padding:0;position:absolute;width:100%;white-space:nowrap;opacity:0.0001;pointer-events:none" value="1"/></div></div></div>
  </div>
  <div class="smbk-color-picker__code">
    <span class="smbk-select smbk-select--size-sm smbk-color-picker__format">
      <button
        type="button"
        id="selectcolor-picker-17"
        class="smbk-input smbk-input--size-sm smbk-select__well"
        role="combobox"
        aria-haspopup="listbox"
        aria-expanded="false"
        aria-label="Color format"
      >
        <span class="smbk-select__value">Hex</span>
        <i
          class="ph ph-caret-down smbk-icon smbk-icon--size-md smbk-input__icon smbk-select__icon"
          aria-hidden="true"
        ></i>
      </button>
    </span>
    <span class="smbk-input smbk-input--size-sm smbk-color-field smbk-color-field--size-sm smbk-color-picker__field">
      <span class="smbk-input__leading-content">
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square smbk-color-field__swatch"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(59, 92, 227, 1)"></span></span>
      </span>
      <input
        id="react-aria-color-picker-18"
        aria-label="Color code"
        aria-describedby="react-aria-color-picker-19 react-aria-color-picker-20"
        type="text"
        autoComplete="off"
        autoCapitalize="off"
        autoCorrect="off"
        spellCheck="false"
        tabindex="0"
        role="textbox"
        class="smbk-input__control smbk-color-field__control"
        value="#3B5CE3"
      >
    </span>
  </div>
  <div class="smbk-color-picker__swatches">
    <hr class="smbk-divider smbk-divider--orientation-horizontal smbk-color-picker__divider"/>
    <div
      role="listbox"
      aria-orientation="horizontal"
      aria-label="Saved colors"
      class="smbk-color-swatch-picker smbk-color-swatch-picker--shape-square smbk-color-swatch-picker--size-sm"
    >
      <div
        role="option"
        aria-selected="false"
        aria-label="vibrant red"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(243, 67, 54, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="light vibrant red orange"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(250, 131, 73, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="light yellow green"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(223, 206, 100, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="light vibrant green"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(84, 184, 91, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="dark vibrant green"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(3, 122, 31, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="light blue"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(127, 160, 255, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="true"
        aria-label="dark vibrant blue"
        tabindex="0"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(59, 92, 227, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="dark blue"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(33, 53, 131, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="dark vibrant red"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(165, 29, 23, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="grayish cyan blue"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(124, 134, 146, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="very dark grayish cyan blue"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(17, 18, 19, 1)"></span></span>
      </div>
      <div
        role="option"
        aria-selected="false"
        aria-label="white"
        tabindex="-1"
        class="smbk-color-swatch-picker__item"
      >
        <span
          aria-hidden="true"
          class="smbk-color-swatch smbk-color-swatch--size-xs smbk-color-swatch--shape-square"
        ><span class="smbk-color-checker"></span><span class="smbk-color-swatch__color" style="background-color:rgba(255, 255, 255, 1)"></span></span>
      </div>
    </div>
  </div>
</div>
```

## React

```tsx
import { ColorPicker, ColorPickerPanel } from './design-system/components/color-picker/color-picker.js';

<ColorPicker type="field" size="md" defaultValue="#3b5ce3" aria-label="Brand color" />
<ColorPickerPanel defaultValue="#3b5ce3" showOpacity showFormat swatches={["#f34336", "#fa8349", "#dfce64", "#54b85b", "#037a1f", "#7fa0ff", "#3b5ce3", "#213583", "#a51d17", "#7c8692", "#111213", "#ffffff"]} />
```

## Stylesheet

```css
/* smbk-color-picker — Color picker. Figma "Color picker" 7411:823 and "Color picker panel" 7411:824.
 * The trigger is a button that is the input's well, built as the select's is: it carries smbk-input and the
 * select's well part, so its chrome, hover, focus, disabled and two sizes are the input's and its button rules
 * the select's. Field holds a swatch, the code (the select's value part) and the caret (the input's icon part);
 * Swatch holds a swatch alone and hugs it. The panel is the popover's panel at its own width, holding the color
 * area, the sliders, the code row and the swatches, the medium stack step apart. This stylesheet only adds the
 * picker's own widths and rows. */

.smbk-color-picker {
  display: inline-flex;
  width: 100%;
}

/* Swatch: a square as tall as the input, the swatch in its middle, the medium inset round it at md. */
.smbk-color-picker--type-swatch {
  width: auto;
}

/* Field: the trigger fills the picker's width, as a field does; the popover's anchor around it does too. */
.smbk-color-picker--type-field > .smbk-popover__anchor {
  flex: 1 1 auto;
  min-width: 0;
}

.smbk-input.smbk-color-picker__trigger {
  flex: 1 1 auto;
}

.smbk-color-picker--type-swatch .smbk-input.smbk-color-picker__trigger {
  flex: none;
  justify-content: center;
  width: var(--smbk-size-control-md);
  padding: 0;
}

.smbk-color-picker--type-swatch .smbk-input--size-sm.smbk-color-picker__trigger {
  width: var(--smbk-size-control-sm);
}

/* The code and the color in words, which name the trigger for screen readers only. */
/* .smbk-color-picker__name: hidden from view, kept for screen readers and the keyboard, by the shared rule in visually-hidden/visually-hidden.css. */

/* ---- the panel: the popover's, at the picker's width and the medium stack step ---- */

.smbk-popover.smbk-color-picker__panel {
  width: var(--smbk-size-color-picker-width);
  gap: var(--smbk-space-stack-md);
}

/* The area fills the panel's width. */
.smbk-color-area.smbk-color-picker__area {
  max-width: none;
}

/* The format, the code and the eyedropper in one row: the code takes what the others leave. */
.smbk-color-picker__code {
  display: flex;
  align-items: center;
  gap: var(--smbk-space-inline-sm);
}

.smbk-select.smbk-color-picker__format {
  flex: none;
  width: auto;
}

.smbk-input.smbk-color-picker__field {
  flex: 1 1 auto;
  min-width: 0;
}

.smbk-color-picker__eyedropper {
  flex: none;
}

.smbk-color-picker__swatches {
  display: flex;
  flex-direction: column;
  gap: var(--smbk-space-stack-md);
}

/* ---- touch: the last strip and the code row stop halfway to each other ----
   The last strip takes an invisible press area on a touch screen, and the code row's text box reaches above its line
   to take the press; over a row that holds the format's select, the strip's area stops halfway into the panel's gap,
   and the text's reach stops halfway to the strip (the panel's gap and the room over the line in the small well). Nothing drawn moves. */

@media (pointer: coarse) {
  .smbk-color-slider:has(+ .smbk-color-picker__code .smbk-select__well) .smbk-color-slider__track::after {
    inset-block-end: max(min(0%, (100% - var(--smbk-size-target-comfortable)) / 2), var(--smbk-space-stack-md) / -2);
  }

  .smbk-color-picker__code .smbk-input__control {
    padding-block-start: max(0%, min((var(--smbk-size-target-comfortable) - 1lh) / 2, (var(--smbk-space-stack-md) + (var(--smbk-size-control-sm) - 1lh) / 2) / 2));
    margin-block-start: min(0%, max((1lh - var(--smbk-size-target-comfortable)) / 2, (var(--smbk-space-stack-md) + (var(--smbk-size-control-sm) - 1lh) / 2) / -2));
  }
}
```

## Tokens it reads

```json
{
  "size": {
    "control": {
      "md": {
        "$type": "dimension",
        "$value": "{{size.40}}",
        "$description": "Height of a medium control, where controls insert by default: 40 comfortable, 32 compact. Dashboard recipe: use compact density; 40 for the page’s one main action and for forms; 32 for toolbars and filters, the size used most; 28 for actions inside table rows and cards. On phones switch to comfortable density, or give small controls an invisible 44 px tap area (size/target/comfortable)."
      },
      "sm": {
        "$type": "dimension",
        "$value": "{{size.32}}",
        "$description": "Height of a small control: 32 comfortable, 28 compact. Dashboard recipe: use compact density; 40 for the page’s one main action and for forms; 32 for toolbars and filters, the size used most; 28 for actions inside table rows and cards. On phones switch to comfortable density, or give small controls an invisible 44 px tap area (size/target/comfortable)."
      }
    },
    "color-picker": {
      "width": {
        "$type": "dimension",
        "$value": "256px",
        "$description": "Width of the color picker panel. A fixed frame width in Figma with no variable behind it; it should become one."
      }
    },
    "target": {
      "comfortable": {
        "$type": "dimension",
        "$value": "{{size.44}}",
        "$description": "Comfortable touch target (44)."
      }
    }
  },
  "space": {
    "stack": {
      "md": {
        "$type": "dimension",
        "$value": "{{space.12}}",
        "$description": "Gap between things stacked one above another, medium."
      }
    },
    "inline": {
      "sm": {
        "$type": "dimension",
        "$value": "{{space.6}}",
        "$description": "Gap between things side by side, small."
      }
    }
  }
}
```

## Purpose

Lets the reader set a color, such as a brand color, a chart series or a label's color. It is a field or a swatch that opens a panel: a color area, a hue slider and an opacity slider to find a color by eye, the code to type an exact one, an eyedropper to take one from the screen, and saved colors to pick from. Every part works from the keyboard and says its value in words.

## Anatomy

- The block, around the trigger and the panel.
- The trigger part, a button that is the input's well: its markup carries the input's classes and the select's well, value and icon parts. The field type holds the swatch part (a color swatch), the value part (the code) and the caret part, which turns up while the panel is open; the swatch type holds the swatch alone in a square as tall as the input.
- The name part, the code and the color in words, read by screen readers only: it names the trigger after its label, and the visible code is hidden from them so it is not heard twice.
- The panel part, the popover's panel at the picker's own width, holding, the medium stack step apart:
  - the area part, a color area that fills the panel's width;
  - two slider parts, a hue slider and an opacity slider, with their top rows hidden;
  - the code part, a row of the format part (a small select), the field part (a small color field) and the eyedropper part (a small secondary icon button);
  - the swatches part, a divider part over a small square color swatch picker.
- The opacity slider, the format, the eyedropper and the swatches can each be left out.

## When to use

- A setting that is a color: a brand color, a theme's accent, a chart series, a label.
- The swatch type in a toolbar or a tight row of settings, such as fill and line.

## When not to use

- To choose among a few set colors only. Use the [color swatch picker](color-swatch-picker.md).
- To enter a code with nothing else. Use the [color field](color-field.md).

## Behavior

Pressing the trigger opens the panel under it, or above it when there is more room there; pressing it again closes it. Every part of the panel shares one color, so a change in one shows in all, and in the trigger. The picker holds its own color from a first color, or follows the color the page gives it, and reports each change.

The eyedropper is shown only in a browser that has one, once the page runs; it takes a color from anywhere on the screen and keeps the color's opacity. The format menu offers the hex code. A change in the code field keeps the color's opacity too. Given a name, the picker sends the color with the form as a hex code with its opacity.

Disabled, the trigger is dimmed and does not open; read-only, the color can be read and the panel does not open. The panel alone is also a component, for a page that shows and places it itself, such as a side panel of settings.

## Accessibility

### What it does for you

- The trigger is one button, named by its label and the color: the code and its name in words, such as “Brand color, #3E63DD, vibrant blue”. It says it opens a dialog, and whether it is open.
- Enter, Space or the down arrow open the panel, a dialog named “Color picker”. Focus stays on the trigger, and Tab goes into the panel next, through the area, the sliders, the format, the code, the eyedropper and the swatches.
- Escape closes the panel and puts focus back on the trigger; a press outside or focus moving away close it too.
- Each part of the panel keeps its own keys and says its value in words: see the color area, the color slider, the color field and the color swatch picker.
- The eyedropper button is named “Pick a color from the screen”.

### What you must do

- Give the trigger a label, such as “Brand color”, so its name says what the color is for.
- Give the words the picker says by itself, such as the names of the panel's sliders, format, code, eyedropper and swatches, in the page's own language. They keep their English unless the page gives its own.

### How to test

- Tab to the trigger and press Enter, Space or Down Arrow: the panel opens with focus still on the trigger. Press Tab: focus goes into the panel through each part in turn.
- Press Escape: the panel closes and focus is back on the trigger.
- With a screen reader, the trigger is read by its label, the code and the color's name, as a button that opens a dialog, and the panel as a dialog named “Color picker”.
- With text at 200% and the page 320 pixels wide, the panel stays whole and every part stays reachable.
- In a forced-color mode, the focus ring shows on every part.

### Keyboard

| Key | What it does |
|---|---|
| Tab | Moves focus to the trigger. With the panel open, moves into the panel and through its parts. |
| Enter, Space or Down Arrow | On the trigger, opens the panel. |
| Escape | Closes the panel and puts focus back on the trigger. |

## Usage rules

### Do

- Label the picker with what the color is for.
- Give saved colors when the reader is likely to reuse them, such as a brand's palette.

### Don't

- Use the swatch type where there is room for the field: the code is what many readers check.
- Put a picker in a row so tight its panel has no room; the panel is as wide as it is.
