Form

A wrapper component for forms

UsageCodeAccessibility
MathematicsGeographyPhysicsHistoryCancelCreate course
<sl-form>
  <sl-form-field hint="Please enter a descriptive name for the course." label="Course name">
    <sl-text-field name="courseName" required></sl-text-field>
  </sl-form-field>

  <sl-form-field label="Subjects">
    <sl-checkbox-group name="subjects">
      <sl-checkbox>Mathematics</sl-checkbox>
      <sl-checkbox>Geography</sl-checkbox>
      <sl-checkbox>Physics</sl-checkbox>
      <sl-checkbox>History</sl-checkbox>
    </sl-checkbox-group>
  </sl-form-field>

  <sl-button-bar align="end">
    <sl-button fill="outline">Cancel</sl-button>
    <sl-button variant="primary">Create course</sl-button>
  </sl-button-bar>
</sl-form>

When to use

The form component should be used whenever you have a form that needs to be filled out by a user. The form component is a container for form fields.

When not to use

Do not use the form component if you only have one form field. Usually this indicates a specific usage of a form control, and that it should be used on its own.

Added to prevent rendering additional paragraph around, which causes navigation problems

The <sl-form> component fulfills four functions:

  1. It provides a default layout for form fields.
  2. It manages the way required/optional fields should be marked.
  3. It provides a way to validate all form fields at once.
  4. It allows you to query the state of the form.

Layout

By default, the form component has a vertical flexbox layout. This means that form fields will stack on top of each other. If you want to change this, you can customize the CSS to use a grid layout instead.

/* Define a two column grid layout. */
sl-form {
  display: grid;
  gap: 1rem;
  grid-template-columns: 1fr 1fr;
}

/* Position the form fields in specific columns here... */

/* Make the button bar span both columns. */
sl-button-bar {
  grid-column: 1 / 3;
}

Required or optional

The form itself manages a mark state. This determines how required or optional labels should be shown. If the required fields outnumber the optional fields, only the optional fields will be marked. If it is the other way around, then only the required fields will be marked.

This behavior happens automatically, and the developer does not need to do anything to make it work.

Validation

The form component provides a way to validate all form fields at once. The reportValidity() method can be used to trigger validation on all form fields. This method returns a boolean indicating whether the form is valid or not.

submitButton.addEventListener('click', event => {
  const form = event.target.closest('sl-form');

  if (form?.reportValidity()) {
    // Submit the form
  }
});

State

You can query the state of the entire form by simply getting the valid property on the <sl-form>. This will return false if any form field within the form is not valid.

Validate on blur

By default, validation feedback is only shown after reportValidity() is called (for example on form submit). You can opt in to validation on blur by adding the validate-on-blur attribute to <sl-form>:

<sl-form validate-on-blur>
  <!-- form fields -->
</sl-form>

With this enabled, each field is validated when the user leaves it. For required fields, this behavior is designed with accessibility in mind:

  • Just tabbing through a field shows no error. This allows keyboard and screen reader users to explore the form and hear all field labels and hints without being interrupted by error announcements on empty fields they haven't interacted with yet.
  • Typing and clearing a field, then leaving it, shows the required error on blur. The user has interacted with the field and is expected to see feedback.
  • Mouse actions such as unchecking a checkbox or removing the last selection in a combobox do not show the error immediately; the error is shown when the control loses focus (for example by clicking outside the field).

Fields that were never interacted with are still validated when reportValidity() is called, for example on submit.

Validation triggers per field type

ControlMouseKeyboard
CheckboxWhen the user checks the checkbox, then unchecks it and moves focus away.When the user changes the value to checked, then unchecked, and moves focus away.
Checkbox GroupWhen the user selects one or more options, then removes all selections and moves focus away.When the user selects one or more options, then removes all selections and moves focus away.
RadioNot applicable — a radio button can't be unselected once checked, so the field can only be empty if never interacted with; it's validated on submit via reportValidity().Not applicable — a radio button can't be unselected once checked, so the field can only be empty if never interacted with; it's validated on submit via reportValidity().
SwitchWhen the user toggles the switch off.When the user moves focus away and the field is toggled off.
SelectWhen the user selects an item, then removes the selection or uses the ‘Clear’ button.If, after removing the selection, the field becomes empty and the focus moves away by clicking outside the field.When the user selects a value, then uses the ‘Clear’ button and moves focus away, or when the user selects a value, moves focus away, returns, removes the value, and moves focus away again.
Single ComboboxWhen the user selects an item, then removes the selection by clicking the option again or by removing the selection's text.If, after removing the selection, the field becomes empty and the focus moves away by clicking outside the field.When the user selects a value, then deselects, then moves focus away or when the user selects a value, then moves focus away, returns, and removes the value.
Multiple ComboboxWhen the user selects an item, then removes the selection by clicking the option again or by removing the selection's text.If, after removing the selection, the field becomes empty and the focus moves away by clicking outside the field.When the user selects a value, then deselects, then moves focus away or when the user selects a value, then moves focus away, returns, and removes the value.If, after removing the selections, the field becomes empty and the user moves the focus away.
Search FieldNot applicableNot applicable
Text FieldWhen the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.When the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.
Text AreaWhen the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.When the user fills the field, then removes the value and moves focus away or when the user enters invalid data and moves focus away.
Number FieldWhen the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.When the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.
Date FieldWhen the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.When the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.Focus on the field button is still considered inside the field.
Time FieldWhen the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.When the user fills the field, then removes the value and moves focus away (for required field) or when the user enters invalid data and moves focus away.Focus on the field button is considered to still be inside the field.

API

Form component is meant as a wrapper around form fields.

Properties

NameAttributeTypeDefaultDescription
announceErrorsannounce-errorsbooleantrueWhether field-level validation messages are announced via the live-region announcer.

Enabled by default. When you use aggregated validation messaging (with <sl-inline-message>), set announce-errors="false" to avoid duplicate screen reader announcements.

controls-Array<HTMLElement & FormControl>[]The controls in the form; not necessarily the same amount as the fields.
dirty-booleanA form is marked dirty when the user has modified a form control.
disableddisabledboolean | undefinedWill disable the entire form when true.
fields-FormField[][]The fields in the form.
invalid-booleanWhether the form is invalid.
pristine-booleanA form is marked pristine as long as the user hasn't modified anything in the form.
resetEvent-EventEmitter<SlResetEvent>
showValidity-booleanIndicates whether to show validity state.
touched-booleanA form is marked touched once the user has triggered a blur event on a form control.
untouched-booleanA form is marked untouched as long as the user hasn't trigger a blur event on a form control.
valid-booleanWhether the form is valid.
validateOnBlurvalidate-on-blurbooleanfalseValidates controls on blur. Format and value errors are shown when the user leaves a field. For required fields, errors are only shown when the user has actually interacted with the field (typed something, cleared it, or used the mouse to change the value). Simply tabbing through a required field without changing it shows no error, so keyboard and screen reader users can explore the form without being interrupted by error announcements. Fields never interacted with are still validated when reportValidity() is called.
value-TThe aggregated value of all form controls.

Methods

NameParametersReturnDescription
getUpdateCompletePromise<boolean>
reportValiditybooleanCalls reportValidity() on all form controls and returns if they are all valid.
requestSubmitvoidIf the form is valid, it will emit an sl-submit event.
resetvoidPuts all the initial values of the form controls back and updates the validity of all fields.

Events

NameEvent typeDescription
sl-resetSlResetEventEmits when the form has been reset.
sl-submitSlSubmitEventEmits when the form is to be submitted.

Keyboard interactions

Here's an overview of the common keyboard interactions associated with a form:

CommandDescription
TabWhen focus is outside the form, moves focus to the first form field.

Validation announcements

By default, <sl-form> announces field validation errors through the live region helper. If your form also shows an aggregated error summary (with sl-inline-message), set announce-errors="false" on <sl-form> to avoid duplicate announcements.