Skip to main content
Copy for LLM

Label

A minimal label component for form fields with optional required indicator.

Basic Usage

A label bound to its input

Required Indicator

A required field, marked on the label

Displays a red asterisk (*) using the --color-wk-danger-text CSS variable. The asterisk includes aria-hidden="true" since it is purely decorative.

Narrow Column — Label Above Field

When the form lives in a sidebar, modal, or mobile-narrow column, place the label directly above the input. The label inherits the input's full width without competing for horizontal space. This is the default layout used by <x-wirekit::input label="…"> and every other WireKit form component when you pass the label prop.

Stacked label + input in a 16rem column

Horizontal Form — Inputs Aligned on a Vertical Line

For wider forms (settings pages, billing-address screens), pair each label with its input on a single row and pin the labels to a fixed-width column so every input starts at the same horizontal position. CSS Grid with grid-template-columns: <label-col> 1fr keeps the alignment robust across long labels and varying input widths:

Billing address — labels left, inputs aligned on a vertical line

The 9rem label column is the smallest width that holds the longest label (Street & number) without wrapping; raise to 10–12rem if your form has longer field names.

A media query in your stylesheet cannot narrow this layout, and that is not a bug in the query. template is an arbitrary value, so <x-wirekit::grid> can only emit it as an inline style — Tailwind extracts class names from source text, and a track built at runtime leaves its scanner nothing to find. An inline style beats a stylesheet rule at any specificity and in any media query.

To stack on a narrow viewport, move the decision to where it can be made: give <x-wirekit::grid> its responsive cols instead of template — <x-wirekit::grid cols="1 md:2">, or set grid-template-columns in your own CSS on your own wrapper and leave template off. The stacked pattern shown above is the same layout with the column dropped.

Props

Prop Type Default Description
for string|null null The id of the associated form element. Not a declared prop — it passes through the attribute bag onto the <label>, which is why any other valid label attribute works here too
required bool false Shows a required indicator (*)
help string|null null An explanation shown in a tooltip from a question mark beside the label. The button sits beside the <label>, never inside it, so it stays out of the name of the field the label names. Classes given to the label then go on the row that holds both
helpId string|null null The id of a hidden copy of help, for the field's control to list in its aria-describedby. The field components set it; without it the help is the tooltip alone
helpField string|null null The name of the field the help explains. A click on the question mark dispatches wirekit:field-help with it as name and the label's text as label; see Explaining a Field at Length. The field components set it
scope string|null null Scoped personalization name

Slots

Slot Description
Default The label text.
after Markup after the label and its help question mark, in the same row and outside both. The field components that draw their label with this one hand their labelAfter slot on to it; see A Mark After the Label.

Accessibility

The label component renders a native <label> element — the most important accessibility primitive for form fields.

  • for attribute — Always set the for prop to the id of the associated input. This creates a programmatic association so screen readers announce the label when the input receives focus, and clicking the label focuses the input.

    You almost never set that id yourself, which is why every example on this page passes only a name. A WireKit form control derives its DOM id from id if you gave one and from name otherwise, so <x-wirekit::input name="email"> renders id="email" and for="email" matches it. The one case where they diverge is a repeat: a second control with the same name on one page becomes email-2, email-3, … so that two labels never point at one id. If you render the same field twice — a filter row above a form, a value edited in two places — pass an explicit id to both and use it as the for.

  • Required indicator — The red asterisk (*) includes aria-hidden="true" because it is purely visual. Screen readers should not announce "asterisk" — instead, mark required fields with the native required attribute on the input itself, which assistive technology announces as "required".

  • Implicit vs. explicit labeling — WireKit form components (Input, Textarea, Select, etc.) handle labeling automatically when you pass the label prop — they render <x-wirekit::label for="{id}"> internally. Use the standalone Label component only when building custom form layouts.

Keyboard Interaction

This component is purely presentational and does not respond to keyboard input.

Design Tokens

Token Used for
--font-wk-sans Label font family
--font-wk-letter-spacing Letter spacing
--text-wk-md Label font size
--color-wk-text Label text
--color-wk-danger-text Required indicator (*)

Further Reading

Updated in WireKit v2.66.0 (2026-10-13)

Was this page helpful?

Thank you for your feedback!

Voting requires cookies or local storage. What we store