Deck
Browse the catalog

Build / Molecules

ColorField

  • molecule
  • play-fn

A colour, picked or typed.

Two controls over one value, because the two ways of choosing a colour are genuinely different jobs: the swatch opens the platform's picker for finding a colour, and the hex field is for entering one you already have — which is how a brand colour actually arrives, out of a guidelines PDF.

The text field takes what you type as you type it, and the swatch follows only once the value is a complete hex. Anything else means a half-typed #2E6 snapping the swatch to black between keystrokes.

import { ColorField } from '@meetcard/deck'

Example

<ColorField label="Primary color" colorName="Signal Green" value={primary} onValueChange={setPrimary} />

Stories

Every preview below is the real component, rendered in this page from the same story Storybook runs. The width control resizes each preview's container; CSS media queries still follow the browser window, so breakpoint behaviour is worth checking in Storybook.

A brand colour: pick it, or paste the hex out of the guidelines.

Default
Source
const Default = args => {
    const [value, setValue] = useState(args.value)

    return (
        <div style={{ maxWidth: 320 }}>
            <ColorField
                label="Primary color"
                colorName="Signal Green"
                value={value}
                onValueChange={setValue} />
        </div>
    );
};

Typed rather than picked, which is how a brand colour usually arrives.

Typing A Hex
Source
const TypingAHex = args => {
    const [value, setValue] = useState(args.value)

    return (
        <div style={{ maxWidth: 320 }}>
            <ColorField
                label="Primary color"
                colorName="Signal Green"
                value={value}
                onValueChange={setValue} />
        </div>
    );
};

Without a brand name — just the field, for a one-off colour.

Without A Color Name
Source
const WithoutAColorName = args => {
    const [value, setValue] = useState(args.value)

    return (
        <div style={{ maxWidth: 320 }}>
            <ColorField
                label="Highlight"
                colorName={undefined}
                value={value}
                onValueChange={setValue} />
        </div>
    );
};

The pair a company's brand actually comes in.

A Pair Of Brand Colors
Source
const APairOfBrandColors = function Pair() {
  const [primary, setPrimary] = useState('#2E6E5B')
  const [accent, setAccent] = useState('#C66A4A')
  return (
    <Stack gap={16} style={{ maxWidth: 320 }}>
      <ColorField
        label="Primary color"
        colorName="Signal Green"
        value={primary}
        onValueChange={setPrimary}
      />
      <ColorField
        label="Accent color"
        colorName="Warm Clay"
        value={accent}
        onValueChange={setAccent}
      />
    </Stack>
  )
};

Props

PropTypeDefaultDescription
labelrequiredReactNode—What the colour is for, e.g. "Primary color".
valuerequiredstring—Hex, #rrggbb. The swatch and the text field are two views of it.
classNamestring——
colorNameReactNode—The colour's name in the brand's own words — "Signal Green". Shown beside the label, because #2E6E5B is not what anyone calls it.
descriptionReactNode——
idstring——
onValueChange(value: string) => void——

Open in Storybookfor controls, the a11y panel and the interaction runner.