Figma UI kit
Form controls

Text inputs and steppers

v1.2.1

Enter text or a number. Fields sit in rows, so they share one height.

Quick usage

Import the shared component; never copy its markup into a feature. The Web TSX tab beside the live stage has a complete, working example.

import Input from '@/shared/components/Input';

Live stage and code

The live component and its controls on the left, the code on the right; change a control and the code follows: Web TSX (the component in a working example), Tailwind and HTML (the markup it renders, with its data attributes), React Native, SwiftUI and Jetpack Compose. The header theme switch drives every stage.

Props

Read from the component's source when the docs build: names and defaults from its signature, types and descriptions from its JSDoc. A blank type means the prop has no JSDoc yet.

PropTypeDefaultDescription
type'single-line'|'text-area'|'date-picker''single-line'Variant axis (see SCOPE).
size'medium'|'small''medium'medium = 32px frame, small = 24px.
feedback'default'|'info'|'warning'|'error'|'success'|'read-only''default'-
origin'human'|'ai''human'ai swaps the focus ring for the info border.
iconReact.ReactNodenullRendered inside the frame, before the text.
trailingReact.ReactNodenullAn interactive control at the trailing edge (a clear button, a reveal toggle). Unlike `icon` this is meant to be pressed, so the caller passes a real <button> and owns its 44px boundary.
rowsnumber-text-area only; the frame's height follows it.
inputTypestring-The NATIVE input type (date, datetime-local, …). Separate from `type` because that name is already the kit's variant axis: a date-picker frame can hold a `date` or a `datetime-local` control, and the frame is what the variant describes.
className---
inputClassName---
...rest--Any other prop is passed through to the root element.

Source: frontend/src/shared/components/Input/Input.js

DOM contract

What the rendered element carries: the data attributes its styles key on, its roles and ARIA, its focus style, and whether its stylesheet draws the 44px hit boundary. Also read from the source.

Data attributesdata-disableddata-feedbackdata-has-icondata-origindata-sizedata-type
RolesNative element semantics only
ARIANone set by the component
FocusNo :focus-visible rule of its own
44px hit boundaryNot a pressable root

Accessibility and touch

The whole field is the target.

Text

Visible height 28px. The ::after boundary adds 8px above and below, so a gloved finger lands on a 44px target while the row keeps its density.

Do and avoid

Do
A36 plate
Do: draw a field at 32px with square corners, the receptive shape.
Avoid
A36 plate
Avoid: a rounded or 40px field. A ragged baseline beside 32px fields reads as breakage.

Rules and constraints

Use it for

  • Any typed value; the number stepper for small integer quantities.

Avoid

  • Never a field at 24, 28, 36 or 40px: every form control is 32px.

Constraints

  • Square (--radius-none) so the 2px focus underline runs flush into both corners.
  • Textareas: min-height 48px, resize vertical only.
  • Label to control 6px, field to field 12px.

More in Form controls