Component
Form
Accessible form primitives built on react-hook-form. They wire labels, controls, descriptions, and error messages together with the correct ids and ARIA attributes, so any input becomes a fully-labelled, validated field.
Basic field
Spread useForm() into Form, then compose FormField → FormItem → FormLabel/FormControl/FormDescription/FormMessage.
Installation
$
pnpm add @refraction-ui/react-formUsage
tsx
import {
Form,
FormField,
FormItem,
FormLabel,
FormControl,
FormMessage,
useForm,
} from '@refraction-ui/react/form'
export function SignUpForm() {
const form = useForm({ defaultValues: { email: '' } })
return (
<Form {...form}>
<form onSubmit={form.handleSubmit(console.log)}>
<FormField
control={form.control}
name="email"
rules={{ required: 'Email is required.' }}
render={({ field }) => (
<FormItem>
<FormLabel>Email</FormLabel>
<FormControl>
<input placeholder="you@example.com" {...field} />
</FormControl>
<FormMessage />
</FormItem>
)}
/>
<button type="submit">Submit</button>
</form>
</Form>
)
}Validation
Pass RHF rules to FormField. FormMessage renders the error and the label turns destructive automatically. Submit an empty or malformed email to see it.
Primitives
| Prop | Type | Default | Description |
|---|---|---|---|
Form | FormProvider | -- | React Hook Form provider. Spread the result of `useForm()` into it so descendants can read form state. Renders no DOM of its own. |
FormField | ControllerProps | -- | Connects a named field to RHF’s Controller and supplies field-name context to the descendant primitives. Accepts `control`, `name`, `rules`, and a `render` prop. |
FormItem | HTMLAttributes<HTMLDivElement> | -- | Wraps one field and emits a stable id used by Label, Control, Description, and Message. |
FormLabel | LabelHTMLAttributes<HTMLLabelElement> | -- | Field label, wired to the control via `htmlFor`. Turns destructive when the field is invalid. |
FormControl | HTMLAttributes<HTMLElement> | -- | Slot that injects `id`, `aria-describedby`, and `aria-invalid` onto the input it wraps (a single child). |
FormDescription | HTMLAttributes<HTMLParagraphElement> | -- | Helper text linked to the control via `aria-describedby`. |
FormMessage | HTMLAttributes<HTMLParagraphElement> | -- | Renders the field’s validation error message (or its children when there is no error). Returns null when empty. |
useFormField | () => { id, name, error, invalid, … } | -- | Hook exposing the current field’s ids and live error state — for building custom controls. |