Skip to main content

U.S. flagU.S. flag

An official website of the United States government

CMS Design System

CMS Design System v2 is released!  See our migration guide.

Checkbox & Radio

Jump to guidance View related guidance in the U.S. Web Design System

Checkboxes allow users to select one or more options from a visible list, whereas radio buttons allow a user to select only one option.

Code snippet
<div class="example--wrapper">
  <fieldset class="ds-c-fieldset">
    <legend class="ds-c-label"><span>Checkbox example</span></legend>
    <span class="ds-c-field__hint">Helpful hint text</span>
    <input
      class="ds-c-choice"
      id="checkbox-1"
      type="checkbox"
      name="checkbox-choices"
      value="checkbox-1"
      checked
    />
    <label for="checkbox-1">
      <span>Choice 1</span>
    </label>
    <input
      class="ds-c-choice"
      id="checkbox-2"
      type="checkbox"
      name="checkbox-choices"
      value="checkbox-2"
    />
    <label for="checkbox-2">
      <span>Choice 2</span>
    </label>
    <input
      class="ds-c-choice"
      id="checkbox-3"
      type="checkbox"
      name="checkbox-choices"
      value="checkbox-3"
      disabled
    />
    <label for="checkbox-3">
      <span>Disabled choice 3</span>
    </label>
  </fieldset>
  <fieldset class="ds-c-fieldset">
    <legend class="ds-c-label"><span>Radio example</span></legend>
    <span class="ds-c-field__error-message" role="alert">
      Example error message
    </span>
    <input
      class="ds-c-choice ds-c-choice--error"
      id="radio-1"
      type="radio"
      name="radio-choices"
      value="radio-1"
    />
    <label for="radio-1">
      <span>Choice 1</span>
      <span class="ds-c-field__hint">Choice hint text</span>
    </label>
    <input
      class="ds-c-choice ds-c-choice--error"
      id="radio-2"
      type="radio"
      name="radio-choices"
      value="radio-2"
    />
    <label for="radio-2"><span>Choice 2</span></label>
  </fieldset>
  <fieldset class="ds-c-fieldset">
    <legend class="ds-c-label"><span>Small size example</span></legend>
    <input
      class="ds-c-choice ds-c-choice--small"
      id="small-1"
      type="radio"
      name="size-variants"
      value="normal"
      checked
    />
    <label for="small-1">
      <span>Choice 1</span>
    </label>
    <input
      class="ds-c-choice ds-c-choice--small"
      id="small-2"
      type="radio"
      name="size-variants"
      value="small"
    />
    <label for="small-2">
      <span>Choice 2</span>
    </label>
  </fieldset>
  <div class="example--wrapper example--inverse">
    <fieldset class="ds-c-fieldset">
      <legend class="ds-c-label"><span>Inverse example</span></legend>
      <span class="ds-c-field__hint ds-c-field__hint--inverse">Helpful hint text</span>
      <span class="ds-c-field__error-message ds-c-field__error-message--inverse"
        >Example error message</span
      >
      <input
        class="ds-c-choice ds-c-choice--inverse ds-c-choice--error"
        id="inverse-1"
        type="checkbox"
        name="inverse-choices"
        value="inverse-1"
      />
      <label for="inverse-1">
        <span>Choice 1</span>
        <span class="ds-c-field__hint ds-c-field__hint--inverse">Choice hint text</span>
      </label>
      <input
        class="ds-c-choice ds-c-choice--inverse ds-c-choice--error"
        id="inverse-2"
        type="checkbox"
        name="inverse-choices"
        value="inverse-2"
      />
      <label for="inverse-2">
        <span>Choice 2</span>
      </label>
      <input
        class="ds-c-choice ds-c-choice--inverse ds-c-choice--error"
        id="inverse-3"
        type="checkbox"
        name="inverse-choices"
        value="inverse-3"
        disabled
      />
      <label for="inverse-3">
        <span>Disabled choice 3</span>
      </label>
    </fieldset>
  </div>
</div>
React

<ChoiceList>

View source file

A ChoiceList component can be used to render a radio button group, or checkbox group. Use the type prop to specify the type of field to display.

Code snippet
ReactDOM.render(
  <div className="example--wrapper">
    <ChoiceList
      choices={[
        { label: 'Choice 1', value: 'A', defaultChecked: true },
        { label: 'Choice 2', value: 'B' },
        { label: 'Disabled choice 3', value: 'C', disabled: true },
      ]}
      className="ds-u-margin-top--0"
      label="Checkbox example"
      hint="Helpful hint text"
      name="checkbox_choices"
      type="checkbox"
    />
    <ChoiceList
      choices={[
        { label: 'Choice 1', value: 'A', hint: 'Choice hint text' },
        {
          label: 'Choice 2',
          value: 'B',
        },
      ]}
      errorMessage="Example error message"
      label="Radio example"
      name="radio_choices"
      type="radio"
    />
    <ChoiceList
      choices={[
        { label: 'Choice 1', value: 'A', defaultChecked: true },
        { label: 'Choice 2', value: 'B' },
      ]}
      label="Small size example"
      name="size-variants"
      type="radio"
      size="small"
    />
    <div className="example--wrapper example--inverse">
      <ChoiceList
        choices={[
          {
            label: 'Choice 1',
            requirementLabel: 'Choice hint text',
            value: 'A',
          },
          { label: 'Choice 2', value: 'B' },
          { label: 'Disabled choice 3', value: 'c', disabled: true },
        ]}
        label="Inverse example"
        errorMessage="Example error message"
        hint="Helpful hint text"
        name="inverse_choices_field"
        type="checkbox"
        inversed
      />
    </div>
  </div>,
  document.getElementById('js-example')
);

Props

React Properties Documentation
NameTypeDefaultDescription
choices

Required

arrayOf[custom]

Array of Choice data objects to be rendered.

classNamestring

Additional classes to be added to the root element.

disabledbool

Disables the entire field.

errorMessagestring, number, element, or array
errorMessageClassNamestring

Additional classes to be added to the error message

errorPlacement'top', 'bottom'

Location of the error message relative to the field input

hintstring, number, element, or array

Additional hint text to display

requirementLabelstring, number, element, or array

Text showing the requirement ("Required", "Optional", etc.). See Required and Optional Fields.

inversedbool

Applies the "inverse" UI theme

label

Required

string, number, element, or array

Label for the field

labelClassNamestring

Additional classes to be added to the FormLabel.

name

Required

string

The field's name attribute

onBlurfunc

Called anytime any choice is blurred

onComponentBlurfunc

Called when any choice is blurred and the focus does not land on one of the other choices inside this component (i.e., when the whole component loses focus)

onChangefunc
size'small'

Sets the size of the checkbox or radio button

type

Required

'checkbox', 'radio'

Sets the type to render checkbox fields or radio buttons

React

<Choice>

View source file

A Choice component can be used to render a checkbox or radio button.

Any undocumented props that you pass to this component will be passed to the input element, so you can use this to set additional attributes if necessary.

Code snippet
const childField = (
  <TextField label="Child field" labelClassName="ds-u-margin-top--0" name="textfield_child" />
);

ReactDOM.render(
  <div className="example--wrapper">
    <fieldset className="ds-c-fieldset">
      <legend className="ds-c-label">
        <span>Custom checkbox inputs</span>
      </legend>
      <Choice name="checkbox_choice" type="checkbox" label="Checkbox A" value="a" />
      <Choice
        defaultChecked
        name="checkbox_choice"
        type="checkbox"
        label="Checkbox B with checked children"
        value="b"
        checkedChildren={<div className="ds-c-choice__checkedChild">{childField}</div>}
      />
      <Choice
        defaultChecked
        name="checkbox_choice"
        type="checkbox"
        label="Checkbox C with unchecked children"
        value="c"
        uncheckedChildren={<div className="ds-c-choice__checkedChild">{childField}</div>}
      />
      <Choice
        name="checkbox_choice"
        type="checkbox"
        label="Disabled Checkbox d"
        value="d"
        disabled
      />
    </fieldset>
    <fieldset className="ds-c-fieldset">
      <legend className="ds-c-label">
        <span>Custom radio inputs</span>
      </legend>
      <Choice name="radio_choice" type="radio" label="Radio A" value="a" />
      <Choice
        name="radio_choice"
        type="radio"
        label="Radio B with checked children"
        value="b"
        checkedChildren={<div className="ds-c-choice__checkedChild">{childField}</div>}
      />
      <Choice
        defaultChecked
        name="radio_choice"
        type="radio"
        label="Radio C with unchecked children"
        value="c"
        uncheckedChildren={<div className="ds-c-choice__checkedChild">{childField}</div>}
      />
      <Choice name="radio_choice" type="radio" label="Disabled Radio D" value="d" disabled />
    </fieldset>
  </div>,
  document.getElementById('js-example')
);

Props

React Properties Documentation
NameTypeDefaultDescription
checkedbool

Sets the input's checked state. Use this in combination with onChange for a controlled component; otherwise, set defaultChecked.

checkedChildrenstring, number, element, or array

Content to be shown when the choice is checked. See Checked children and the expose within pattern on the Guidance tab for detailed instructions.

uncheckedChildrenstring, number, element, or array

Content to be shown when the choice is not checked

classNamestring

Additional classes to be added to the root div element.

inputClassNamestring

Additional classes to be added to the input element.

labelstring, node

Label text or HTML.

labelClassNamestring

Additional classes to be added to the FormLabel.

defaultCheckedbool

Sets the initial checked state. Use this for an uncontrolled component; otherwise, use the checked property.

disabledbool
inputReffunc

Access a reference to the input element

hintstring, number, element, or array

Additional hint text to display below the choice's label

idstring

A unique ID to be used for the input field, as well as the label's for attribute. A unique ID will be generated if one isn't provided.

requirementLabelstring, number, element, or array

Text showing the requirement ("Required", "Optional", etc.). See Required and Optional Fields.

inversedbool

Applies the "inverse" UI theme

size'small'
name

Required

string

The input field's name attribute

onBlurfunc
onChangefunc
type

Required

'checkbox', 'radio'

Sets the type to render checkbox fields or radio buttons

value

Required

number, string

The input value attribute

Guidance

When to use

Checkboxes

  • When a user can select any number of choices from a set list.
  • When a user needs to choose “yes” or “no” on only one option (use a stand-alone checkbox). For example, to toggle a setting on or off.
  • When users need to see all the available options at a glance.
  • When users should be able to select zero of the options.

Radio buttons

  • When users need to select only one option out of a set of mutually exclusive choices.

When to consider alternatives

  • If there are too many options to display on a mobile screen. Consider a dropdown menu if you don’t have enough space to list out all available options, and if the user can only select one of the options.
  • Never use radio buttons for optional questions, since once a radio button is selected from a list, it or another choice will remain selected.

Usage

  • Don't rely on the visual difference between radio buttons and checkboxes. Make it clear with words when users can select one or multiple options.
  • Users should be able to tap on or click on either the text label or the checkbox to select or deselect an option.
  • In general, list choices vertically; horizontal listings can make it difficult to tell which label pertains to which choice. An exception is where you have binary choices with short labels, like 'Yes / No'. The convention here is for horizontal alignment.
  • Avoid using negative language in labels as they can be counterintuitive. For example, “I want to receive a promotional email” instead of “I don’t want to receive promotional email.”
  • Use caution if you decide to set a default value. Setting a default value can discourage users from making conscious decisions, seem pushy, or alienate users who don’t fit into your assumptions. In addition, you'll never know if the user explicitly chose that option or just didn't notice the question. If you're unsure, leave nothing selected by default.

View the "Forms" guidelines for additional guidance and best practices.

Checked children and the expose within pattern

  • The <Choice> component includes a checkedChildren prop that can expose hidden text information or form elements. This expose within pattern is especially useful if you need to collect data from follow up questions or give just-in-time feedback.
  • Checked children can be exposed by checking the parent checkbox or radio button
  • The checkedChildren prop should return one or more items wrapped in a div with the following className: .ds-c-choice__checkedChild. This class sets the spacing and border color for the exposed elements.
  • Add the className .ds-c-choice__checkedChild--inverse to the div to show the inverse white border
  • You may need to add the className .ds-u-margin--0 to your child element(s) to avoid extra top margin
  • If you opt for smaller radio buttons or checkboxes, add className .ds-c-choice__checkedChild--small to your checked child container

Accessibility

  • Surround a related set of choices with a <fieldset>. The <legend> provides context for the grouping. Do not use fieldset and legend for a single checkbox.
  • Some screen readers read the legend text for each fieldset, so it should be brief and descriptive.
  • Each input should have a semantic id attribute, and its corresponding label should have the same value in its for attribute.
  • The custom checkboxes and radio buttons here are accessible to screen readers because the default fields are moved off-screen.
  • checkedChildren will be announced to screen readers when they are exposed. They have been tested with the following devices:
    • Windows 10 + Internet Explorer 11 + JAWS screen reader
    • Windows 10 + Chrome + JAWS
    • Windows10 - Firefox + NVDA
      • NVDA reads out the <select> label and every <option> value
    • MacOS Mojave + Safari + VoiceOver

Customization

The following Sass variables can be overridden to theme choice fields:

  • $choice-size
  • $choice-border-width
  • $choice-border-radius
  • $choice-background-color
  • $choice-border-color
  • $choice-checked-background-color
  • $choice-checked-border-color
  • See form variables for the full list of choice variables.

Related patterns

Learn more