Skip to content

Form pattern

Forms are at the core of Gusto’s products. Use these guidelines to create forms that are predictable, easy to use and cohesive across the platform.

Anatomy of a form in Gusto’s platform
Anatomy of a form
  • Spacing in forms follow a consistent pattern of 12px between unique elements and 8px between grouped elements (like radios and checkboxes).

  • There are subtle differences between elements with a description (0px between title and description, 4px between the description and form element) elements with just a label (4px between the label and form element)

Example of spacing between form elements
Horizontal and vertical spacing between elements within a form

The default styles for Input, Textarea, Select, Autocomplete components are: salt-300 as the background color, salt-1000 text, and a 2px salt-700 bottom border.

Please use your full name. You may use initials for your middle name(s)

 (optional)

Please enter the state in which you currently reside. If you have lived in this state less than one year, please select the last state which you lived

Add details and requirments for the job

Default text field, select, and textarea examples

The focus state styles for Input, Textarea, Select, Autocomplete components are: kale-100 as the background color, salt-1000 text, and a 2px kale-500 bottom border.

Example a focused text fieldExample a focused textareaExample a focused select
Focus state on a text field, textarea, and select

The error state styles for Input and Textarea components are: error-100 as the background color, salt-1000 text, and a 2px error-500 bottom border. Error message text should always appear below the field and be set to error-500

Please use your full name. You may use initials for your middle name(s)

Add details and requirments for the job

Error state on a text field, and textarea

Success message text should always appear below the field and be set to kale-500. This state should only be used for async form behavior (e.g. requiring validation from a third party service before the form is submitted)

  • Disabled states prevent users from interacting with an element and provides a visual indicator and a state announcment for screen readers
  • Disabled elements are not interactive and therefore do not change on hover, active, or focus
  • Disabled elements cannot be focused by keyboards and should not be used to prevent form submission

Please use your full name. You may use initials for your middle name(s)

Please enter the state in which you currently reside. If you have lived in this state less than one year, please select the last state which you lived

Add details and requirments for the job

An old fashioned paper check will be sent via USPS to 555 Drury Lane, courtesy of the muffin man.
Run payroll for 11/1/19 cycle
Disabled element examples

Avoid disabling buttons. Disabled buttons cause accessibility issues for keyboard-only users because they cannot focus on disabled elements. Disabling a button while it is focused (like an incrementing number button) will remove focus from the button and place it on the body of the document, which can confuse users.

Disabling a button to prevent invalid form submission

  • Disabling form submission makes it impossible for users to get additional feedback if the form has become invalidated in a way that hasn’t triggered an error message to appear. This causes confusion among users and compels them to scan the form to find their errors. In some cases the user may not even understand that the button is disabled, which could lead them to abandon the workflow.

  • Instead, use client-side validation and Formik to prevent invalid forms from being submitted. When the user clicks the submit button, this will reject invalid input and present them with errors explaining what they need to do to fix them, like in this example.

Buttons are disabled while the form is being submitted or processed by the server

  • Instead, offer feedback to the user via the loading prop. This will reject user input but will not cause focus to be lost on the button.

Since most form fields in Gusto’s platform are required, only optional fields should be denoted. This pattern reduces the amount of information presented to users, making forms easier to complete.

 (optional)

Please enter the state in which you currently reside. If you have lived in this state less than one year, please select the last state which you lived

Example of an optional text field

A checkbox can also have an indeterminate state when its value cannot be expressed with a binary true or false value. This state is most often used on groups of checkboxes that contain "children" elements, which can have different values.

Example of an Indeterminate checkbox

Forms are easiest when building with Formik. To use our components with Formik wrappers, make sure to import from @gusto/workbench-formik. These components work exactly the same as their @gusto/workbench counterparts, but with the added benefit of having state management handled by Formik.

Learn more about implementing forms »

  • Try to pair each form element with a label. For cases where it’s not possible/necessary, e.g., Search inputs, use an arial-label or [visuallyHidden](/components/visuallyhidden/)
  • Place label above the field
  • Optional fields should be denoted in their label i.e. Phone number (optional). Use the optionalText prop in form components to set this text
  • Add description text under the label and above the field
  • Show error/success messages below the related form field
  • Use placeholder text only for supplemental hints
  • Make sure tab order follows visual structure of the form
  • Don’t place form elements side-by-side except for cases where the format is required, like date inputs
  • Don’t call out required fields since optional fields are already marked
  • Don’t use placeholder text in place of a label
  • Don’t create custom error formatting placements

Use validation text to confirm that the input meets key criteria for that specific field—the input may have been checked against a database (like tying a routing number to a bank) or validated for certain characteristics (like making sure that a password has a certain number of characters). Here are some do’s and don’ts:

  • Use validation text as feedback on a single field; if you need to provide feedback on more than one field, use a different component
  • Use validation text to confirm the user’s entry for field types including:
  • Credit card numbers
  • Bank account numbers
  • Don’t use for dropdown or autocomplete fields
  • Don’t use validation text to explain the consequences of a choice
  • Don’t use to confirm very common, obviously formats for fields (e.g. dollars and cents)