Forms

Field

Form-field layout primitive. Standardises the label + control + description + error stack with consistent spacing and ARIA wiring.

Preview
01 Installation

Install

Pull Field from the barrel for everyday use, or the granular path when you want a tighter bundle.

tsxBarrel1 line
import { Field } from "@brika/clay";
tsxGranular1 line
import { Field } from "@brika/clay/components/field";
02 Usage

A minimal example

Drop this into a page. Native HTML attributes pass through to the underlying primitive.

tsxField.tsx17 lines
import {
  Field,
  FieldDescription,
  FieldLabel,
} from '@brika/clay/components/field';
import { Input } from '@brika/clay/components/input';

/** Single field with label, control, and helper description. */
export default function FieldBasicDemo() {
  return (
    <Field>
      <FieldLabel htmlFor="email">Email</FieldLabel>
      <Input id="email" type="email" placeholder="you@example.com" />
      <FieldDescription>We'll never share your email.</FieldDescription>
    </Field>
  );
}
03 Examples

Field, every way

Checkbox

Inline checkbox + label pattern using `Field` with row layout.

Error

Invalid state pairs `aria-invalid` on the control with `<FieldError>`.

Group

`FieldGroup` stacks multiple fields with consistent vertical rhythm.

Set

`FieldSet` + `FieldLegend` group related controls semantically.

04 Accessibility

Accessibility

  • Always associate FieldLabel with its control via htmlFor matching the input id.
  • Wire aria-describedby on the control to FieldDescription/FieldError ids when present so assistive tech announces helper and error copy.
  • Use FieldSet + FieldLegend (semantic <fieldset>/<legend>) to group related controls such as radio options.
  • FieldError should set role="alert" (default here) so dynamically appearing validation messages are announced.
05 Tokens 5 theme-overridable

Theme tokens

Every CSS variable Field reads, with its default and the dotted path you'd write in a ThemeConfig JSON to override it. Set any of these in your theme to retune Field without touching component code.

Field tokens

5 tokens
ColorFill, border, and text colors.4
  • --field-description-colorcolorvar(--muted-foreground)
    components.field.descriptionColor

    Text color of the supporting description copy below the control.

  • --field-error-colorcolorvar(--destructive)
    components.field.errorColor

    Text color of the validation error message rendered by `FieldError`.

  • --field-legend-colorcolorvar(--foreground)
    components.field.legendColor

    Text color of the `FieldLegend` heading inside a `FieldSet`.

  • --field-separator-colorcolorvar(--border)
    components.field.separatorColor

    Line color of the optional `FieldSeparator` divider.

GeometrySizes, lengths, and corner radii.1
  • --field-gapsizecalc(var(--spacing) * 1.5)
    components.field.gap

    Gap between adjacent children inside the field.

Override in a theme

Authoring a theme is plain JSON. Drop overrides under components.field, the names are camelCase versions of the variable suffix.

jsonmy-theme.json12 lines
{
  "id": "my-theme",
  "name": "My Theme",
  "description": "...",
  "accentSwatches": ["#000"],

  "components": {
    "field": {
      "descriptionColor": "var(--muted-foreground)"
    }
  }
}

Then apply with applyTheme(myTheme) (see the theming guide), scope it to a subtree with themeToCssVars(myTheme, mode), or consume any token directly in your own JSX with the matching Tailwind utility (e.g. bg-field-…) — see the chips on each token row.

06 API reference

API reference

Props specific to Field. Native HTML attributes pass through to the underlying primitive, see the component source on GitHub for the full type signature.

<Field />

passthrough

No wrapper-specific props, all attributes pass through to the underlying primitive.

<FieldDescription />

passthrough

No wrapper-specific props, all attributes pass through to the underlying primitive.

<FieldError />

passthrough

No wrapper-specific props, all attributes pass through to the underlying primitive.

<FieldGroup />

passthrough

No wrapper-specific props, all attributes pass through to the underlying primitive.

<FieldLabel />

passthrough

No wrapper-specific props, all attributes pass through to the underlying primitive.

<FieldLegend />

passthrough

No wrapper-specific props, all attributes pass through to the underlying primitive.

<FieldSeparator />

passthrough

No wrapper-specific props, all attributes pass through to the underlying primitive.

<FieldSet />

passthrough

No wrapper-specific props, all attributes pass through to the underlying primitive.