Input
Displays a form input field for a single line of text.
Installation
Install the following dependencies:
Set up the token layer and the StyleX compiler, if you have not already. See
Installation, and paste states.ts from the same page.
The input's field surface, its focus ring and its invalid ring come from it.
Paste field-state.ts and state-styles.ts from the same installation page.
Copy and paste the following code into your project.
Update the import paths to match your project setup.
Usage
Basic
Label
Pair the input with a Label and match htmlFor to
the input's id. A Field adds the description and
error text around it.
Disabled
Set disabled on Field to disable its control and dim its label, or on a bare control directly.
Invalid
Set invalid on Field to style its control, or aria-invalid on a bare control. The examples show both.
File
Use type="file" for a file input. The browser's own button is restyled to the
control's type scale so the height does not change.
Required
Use the required attribute for required inputs. Mark the label too, since
required alone is only announced once the control has focus.
Inline
Put the input and a button in an HStack for a one-line form.
Grid
Lay several inputs out in a grid to place them side by side.
Input group
To put an icon, a prefix or a button inside the field, wrap it in InputGroup. The input detects the group and drops its own border, fill and ring so the group can draw them once.
Button group
To attach a button to the outside of the field, use
ButtonGroup. Square the input's trailing
corners yourself. The group's joining rules apply to Button, which reads the
group through context, and Input does not.
Below the md breakpoint the font size is 16px rather than 14px. iOS Safari
zooms the page when a focused control's text is any smaller, and the zoom does
not reverse on blur.
API reference
Pass render to replace a part's element or compose it with another component.
Input wraps the Base UI Input part and accepts its props, including
defaultValue, value and onValueChange. See the
Base UI reference.
Input
| Prop | Type | Default |
|---|---|---|
type | every <input> type | text |
disabled | boolean | false |
aria-invalid | boolean | — |
onValueChange | (value: string, details) => void | — |
render | ReactElement | (props, state) => Element | — |
xstyle | StyleXStyles | — |
className | string | — |
Inside an InputGroup the group's disabled and invalid win. An input can be
disabled on its own, but it cannot opt out of a disabled group.
inputStyles
The style maps behind the component. Spread them onto any element.
| Key | What it is |
|---|---|
base | The control: frame, fill, type scale, placeholder, disabled |
invalid | The destructive border and ring |
inGroup | The frameless form an InputGroup member takes |
base is three styles, in merge order: the control's own, the shared
states.focusRing, and states.fieldSurface, which is the hairline edge, the
fill and the drop. invalid is states.invalidRing from theme/states.ts. Set
a border of your own through --carbon-border-color rather than borderColor.
A flat borderColor replaces the property with all of its conditions, so the ring loses its focus colour.
Data attributes
| Attribute | On | Effect |
|---|---|---|
data-slot="input" | a standalone input | Targets the control from a parent |
data-slot="input-group-control" | an input in a group | What InputGroup watches to draw its ring |
data-disabled, data-valid, data-dirty | the control | Base UI writes them inside a Field |