Radio semantics in a card body, for choices that need explaining.
| Prop | Type | Notes |
|---|---|---|
| value | string | The option's identity within its group |
| multiple (group) | boolean | Checkbox semantics instead of radio |
| title / description | string | Primary label and supporting line |
| icon | ReactNode | Optional leading glyph tile |
| disabled | boolean | Unselectable, opacity 0.45 |
| ↑ / ↓ · Space | — | Move within the group; Space toggles |
Reach for a Choicebox when each option needs a sentence of explanation. For bare options use Radio or Checkbox; for a compact known list use Dropdown.
Give each card a clear title and one line of why. That is the whole point.
Don't drop the description. A titleless card is just a fat radio button.
Keep a group to a scannable few. Three to five options, one selected.
Don't use choiceboxes for a dozen bare options. That wants a Dropdown.
Pricing tiers where each option carries a price and a promise.
Role selection during onboarding, one warm card selected.
Icon-led choiceboxes for a visual set like frameworks or themes.
| Token | Value | Role |
|---|---|---|
| --choice-pad | 14px | Card padding |
| --choice-radius | 10px | Card corner |
| --choice-border | #242428 | Resting hairline |
| --choice-on-border | rgba(255,122,0,.55) | Selected border |
| --choice-on-fill | rgba(255,122,0,.06) | Selected tint |
| --choice-icon | 34px · #16171B | Leading glyph tile |
<div role="radiogroup" aria-label="Plan">
<button role="radio" aria-checked="true" class="o-choice is-selected">
<span class="o-choice__mark"><span class="o-radio is-on"></span></span>
<span class="o-choice__body">
<span class="o-choice__title">Pro</span>
<span class="o-choice__desc">For growing teams.</span>
</span>
</button>
</div>