Skip to content

RadioGroup

Pick exactly one of 2 to about 6 options, all visible. Radio for short labels, RadioCard for options that need a sentence.

  • Free core, MIT
  • Version 2.0.0-rc.1
  • APG pattern: Radio group

Examples

These are the real React components. Use them with a mouse, touch or keyboard, and switch the theme and density for every example at once.

Default

Delivery
Show the code

Default, code

<RadioGroup defaultValue="standard" label="Delivery">
  <Radio value="standard" description="3 to 5 working days">Standard</Radio>
  <Radio value="express" description="Next working day">Express</Radio>
  <Radio value="collect">Collect from store</Radio>
</RadioGroup>

Horizontal

DeliveryYou can change this at checkout.
Show the code

Horizontal, code

<RadioGroup orientation="horizontal" defaultValue="express" hint="You can change this at checkout." label="Delivery">
  <Radio value="standard" description="3 to 5 working days">Standard</Radio>
  <Radio value="express" description="Next working day">Express</Radio>
  <Radio value="collect">Collect from store</Radio>
</RadioGroup>

Invalid

Delivery
Error: Choose a delivery option
Show the code

Invalid, code

<RadioGroup isRequired isInvalid errorMessage="Choose a delivery option" label="Delivery">
  <Radio value="standard" description="3 to 5 working days">Standard</Radio>
  <Radio value="express" description="Next working day">Express</Radio>
  <Radio value="collect">Collect from store</Radio>
</RadioGroup>

Disabled

Delivery
Show the code

Disabled, code

<RadioGroup isDisabled defaultValue="collect" label="Delivery">
  <Radio value="standard" description="3 to 5 working days">Standard</Radio>
  <Radio value="express" description="Next working day">Express</Radio>
  <Radio value="collect">Collect from store</Radio>
</RadioGroup>

Cards

Plan
Show the code

Cards, code

<div className="max-w-lg">
  <RadioGroup label="Plan" defaultValue="team">
    <RadioCard value="free" title="Free" description="WhatsApp plus one sample flow per app" meta="$0" />
    <RadioCard value="pro" title="Pro" description="Every clone and pack, one person" meta="$240 a year" />
    <RadioCard value="team" title="Team" description="Minimum 2 seats" meta="$200 a seat a year" />
  </RadioGroup>
</div>

Cards with media

Pay with
Show the code

Cards with media, code

<div className="max-w-lg">
  <RadioGroup label="Pay with" defaultValue="visa">
    <RadioCard value="visa" title="Visa ending 4242" description="Expires 08/28" media={<IconTile icon={CreditCard} tone="brand" />} />
    <RadioCard value="mastercard" title="Mastercard ending 4444" description="Expires 11/27" media={<IconTile icon={CreditCard} tone="info" />} />
    <RadioCard value="new" title="Add a new card" media={<IconTile icon={Plus} />} />
  </RadioGroup>
</div>

Label hidden

Default card
Show the code

Label hidden, code

<RadioGroup label="Default card" defaultValue="visa" orientation="horizontal">
  <Radio value="visa" hideLabel>Visa ending 4242</Radio>
  <Radio value="mastercard" hideLabel>Mastercard ending 4444</Radio>
</RadioGroup>

Tokens

The 27 design tokens RadioGroup reads, with the value each has in the theme and density chosen above. Change a token and the component follows, in Figma and in code.

Show all 27 tokens
Tokens RadioGroup reads
TokenValue nowCSS variable
checkbox.bg…--sd-checkbox-bg
checkbox.bg-checked…--sd-checkbox-bg-checked
checkbox.border…--sd-checkbox-border
checkbox.border-width…--sd-checkbox-border-width
checkbox.gap…--sd-checkbox-gap
checkbox.label…--sd-checkbox-label
color.bg.canvas…--sd-color-bg-canvas
color.bg.muted…--sd-color-bg-muted
color.bg.subtle…--sd-color-bg-subtle
color.border.brand…--sd-color-border-brand
color.border.control…--sd-color-border-control
color.border.subtle…--sd-color-border-subtle
color.text.default…--sd-color-text-default
color.text.disabled…--sd-color-text-disabled
color.text.secondary…--sd-color-text-secondary
control.indicator…--sd-control-indicator
field.hint…--sd-field-hint
input.border-invalid…--sd-input-border-invalid
motion.duration.fast…--sd-motion-duration-fast
motion.easing.standard…--sd-motion-easing-standard
radius.full…--sd-radius-full
shape.radius-surface…--sd-shape-radius-surface
spacing.gap.lg…--sd-spacing-gap-lg
spacing.gap.sm…--sd-spacing-gap-sm
spacing.inset.md…--sd-spacing-inset-md
spacing.stack.xs…--sd-spacing-stack-xs
target.min…--sd-target-min

Install

The npm package isn’t published yet. When it is, this is the install line; until then, this page runs the same build of the package (from commit fa3abf8).

Install

npm i @superduperui/react @superduperui/tokens

Import

import { RadioGroup, Radio, RadioCard } from "@superduperui/react"

Props

RadioGroup also takes the props of the React Aria component it’s built on.

RadioGroup props
PropTypeWhat it does
labelrequiredstringGroup label (acts as the legend; names the radiogroup).
hintstring
errorMessagestring | ((validation: ValidationResult) => string)
childrenrequiredReactNodeRadio or RadioCard elements.

When to use it

Use it for

  • 2 to 6 mutually exclusive options people should compare
  • Plans, delivery speeds, payment methods (RadioCard)

Use something else for

  • Several can be chosen: use CheckboxGroup
  • More than about 6 options: use Select or Combobox
  • A setting that applies immediately: use Switch or SegmentedControl

Accessibility

Screen readers announce "Delivery, radio group" then "Standard, radio button, checked, 1 of 3".

WCAG 2.2 AAA criteria the component meets in Comfortable density: 1.4.6, 1.4.9, 2.1.3, 2.3.2, 2.4.13, 2.5.5, 2.5.6.

Compact density meets AA (2.5.8, 24px targets), not AAA.

What your product still has to do

  • Pre-select a sensible default unless the choice is consent or payment

This release’s test results

Test results for RadioGroup in this release
axe-core (WCAG A, AA, AAA and best practice)160 runs across every story, theme, density and width: 0 violations
Rendered text contrast525 text runs: 0 below 7:1, lowest 8.43:1
Target size84 targets: 0 under 44px in Comfortable
Focus appearance (2.4.13)18 focus stops in 3 browser engines: all pass
Keyboard scriptChromium 5 of 5, Firefox 5 of 5, WebKit 5 of 5

Manual passes with VoiceOver and NVDA haven’t been done yet.

Keyboard

Each step is scripted and run in Chromium, Firefox and WebKit.

RadioGroup keyboard steps
KeyWhat happens
TabTab enters the group on the selected radio
ArrowDownDown moves to and selects the next radio
ArrowDownDown again selects the last radio
ArrowDownDown wraps to the first radio
ArrowUpUp moves back (wrapping)

In Figma

The Figma component is RadioGroup, with Orientation (Vertical, Horizontal); State (Default, Disabled, Invalid). The Figma library isn’t published yet.

Figma to code: Orientation → orientation (Vertical = "vertical", Horizontal = "horizontal"); State (Default, Disabled = isDisabled, Invalid = isInvalid); Options → children; nested Label → label; nested Hint → hint; nested FieldError → errorMessage.