Checkboxes

Checkboxes

Material Design 3 checkboxes, from the HTML.

A <label> wrapping <input type="checkbox"> is the control. The label text is a sibling of the input — no extra class, no required <span>. They are CSS only. There is no JavaScript component and nothing to AutoInit.

Tokens follow the M3 checkbox spec. The container is 18dp with 2dp corners. Unselected is a 2dp on-surface-variant outline. Selected is a primary fill with an on-primary check. Indeterminate is the same fill with a dash. The state layer is 40dp at 8% hover and 10% focus. The touch target is 48dp. The label is body-large / on-surface. Disabled is 38%.

Put the input first. Add checked or disabled on the input. Indeterminate is not an HTML attribute — set element.indeterminate = true in script. filled-in is a no-op: the selected state is always the filled box.

<label>
  <input type="checkbox">
  Red
</label>
<label>
  <input type="checkbox" checked>
  Yellow
</label>
<label>
  <input type="checkbox" disabled>
  Brown
</label>
document.getElementById('indeterminate-checkbox').indeterminate = true;

An input + span still works if you already have that markup, or if you follow BeerCSS’s <label class="checkbox"> pattern. Multiple <select> still emits input + span that way.

<label class="checkbox">
  <input type="checkbox">
  <span>Yellow</span>
</label>

In a row

Put the labels in a <div class="inline"> to sit them on one line. A bare group stacks vertically.

<div class="inline">
  <label>
    <input type="checkbox" checked>
    Red
  </label>
  <label>
    <input type="checkbox">
    Yellow
  </label>
</div>

Error

Add aria-invalid="true" or class="invalid" on the input. The box uses error / on-error.

<label>
  <input type="checkbox" aria-invalid="true">
  Accept the terms
</label>
  • Source color

    The seed every generated ramp derives from. Pick one and browse the docs — the whole theme follows. Error does not: it is a fixed hue.