Collect information from your users using validation rules.
import React from 'react';import * as Form from '@radix-ui/react-form';import './styles.css';const FormDemo = () => (<Form.Root className="FormRoot"><Form.Field className="FormField" name="email"><div style={{ display: 'flex', alignItems: 'baseline', justifyContent: 'space-between' }}><Form.Label className="FormLabel">Email</Form.Label><Form.Message className="FormMessage" match="valueMissing">Please enter your email</Form.Message><Form.Message className="FormMessage" match="typeMismatch">Please provide a valid email</Form.Message></div><Form.Control asChild><input className="Input" type="email" required /></Form.Control></Form.Field><Form.Field className="FormField" name="question"><div style={{ display: 'flex', alignItems: 'baseline', justifyContent: 'space-between' }}><Form.Label className="FormLabel">Question</Form.Label><Form.Message className="FormMessage" match="valueMissing">Please enter a question</Form.Message></div><Form.Control asChild><textarea className="Textarea" required /></Form.Control></Form.Field><Form.Submit asChild><button className="Button" style={{ marginTop: 10 }}>Post question</button></Form.Submit></Form.Root>);export default FormDemo;
Built on top of the native browser constraint validation API.
Supports built-in validation.
Supports custom validation.
Full customization of validation messages.
Accessible validation messages.
Supports client-side and server-side scenarios.
Focus is fully managed.
Install the component from your command line.
Import all parts and piece them together.
Contains all the parts of a form.
The wrapper for a field. It handles id/name and label accessibility automatically.
A label element which is automatically wired when nested inside a Field
part.
A control element (by default an input
) which is automatically wired when nested inside a Field
part.
A validation message which is automatically wired (functionality and accessibility) to a given control when nested inside a Field
part. It can be used for built-in and custom client-side validation, as well as server-side validation. When used outside a Field
you must pass a name
prop matching a field.
Form.Message
accepts a match
prop which is used to determine when the message should show. It matches the native HTML validity state (ValidityState
on MDN) which validates against attributes such as required
, min
, max
. The message will show if the given match
is true
on the control’s validity state.
You can also pass a function to match
to provide custom validation rules.
Use this render-prop component to access a given field’s validity state in render (see ValidityState
on MDN). A field's validity is available automatically when nested inside a Field
part, otherwise you must pass a name
prop to associate it.
The submit button.
Using asChild
you can compose the Form
primitive parts with your own components.
It can also be used to compose other types of controls, such as a select
:
Note: At the moment, it is not possible to compose
Form
with Radix's other form primitives such asCheckbox
,Select
, etc. We are working on a solution for this.
When no children
are provided, Form.Message
will render a default error message for the given match
.
You can provide a more meaningful message by passing your own children
. This is also useful for internationalization.
On top of all the built-in client-side validation matches described above you can also provide your own custom validation whilst still making use of the platform's validation abilities. It uses the customError
type present in the constraint validition API.
You can pass your own validation function into the match
prop on Form.Message
. Here's an example:
match
will be called with the current value of the control as first argument and the entireFormData
as second argument.match
can also be anasync
function (or return a promise) to perform async validation.
We add data-valid
and data-invalid
attributes to the relevant parts. Use it to style your components accordingly.
Here is an example styling the Label
part.
You may need to access the raw validity state of a field in order to display your own icons, or interface with a component library via it's defined props. You can do this by using the Form.ValidityState
part:
The component also supports server-side validation using the same Form.Message
component.
You can re-use the same messages you defined for client-side errors by passing a forceMatch
prop which will force the message to show regardless of the client-side matching logic.
If the message doesn't exist on the client-side, you can render a Form.Message
without a match
too.
The field is marked as invalid by passing a serverInvalid
boolean prop to the Form.Field
part.
Here's an example with server-side error handling:
You should clear the server errors using the onClearServerErrors
callback prop on the Form.Root
part. It will clear the server errors before the form is re-submitted, and when the form is reset.
In addition, this provides control over when to reset single server errors. For example you could reset the email server error as soon as the user edits it:
The component follows the "inline errors" pattern for validation:
name
provided on Form.Field