Skip to main content
You are viewing Pre-Alpha documentation.
Vuetify0 Logo
Theme
Mode
Accessibility
Vuetify
Vuetify One

Sign in to Vuetify One

Access premium tools across the Vuetify ecosystem — Bin, Play, Studio, and more.

Not a subscriber? See what's included

Checkbox

A headless checkbox component with dual-mode support: standalone boolean binding or group multi-selection with tri-state.


Intermediate100% coverageJan 27, 2026

Usage

The Checkbox component supports two modes:

  • Standalone mode: Use v-model on Checkbox.Root for simple boolean state

  • Group mode: Wrap in Checkbox.Group for multi-selection with array v-model

<script setup lang="ts">
  import { Checkbox } from '@vuetify/v0'
</script>

<template>
  <label class="inline-flex items-center gap-2">
    <Checkbox.Root class="size-5 border rounded inline-flex items-center justify-center border-divider">
      <Checkbox.Indicator class="text-primary text-sm">✓</Checkbox.Indicator>
    </Checkbox.Root>
    <span>I agree to the terms and conditions</span>
  </label>
</template>

Anatomy

Anatomy
<script setup lang="ts">
  import { Checkbox } from '@vuetify/v0'
</script>

<template>
  <!-- Standalone -->
  <Checkbox.Root>
    <Checkbox.Indicator />
  </Checkbox.Root>

  <!-- Group -->
  <Checkbox.Group>
    <Checkbox.Root>
      <Checkbox.Indicator />
    </Checkbox.Root>

    <Checkbox.Root>
      <Checkbox.Indicator />
    </Checkbox.Root>
  </Checkbox.Group>

  <!-- Group with Select All -->
  <Checkbox.Group>
    <Checkbox.SelectAll>
      <Checkbox.Indicator />
    </Checkbox.SelectAll>

    <Checkbox.Root>
      <Checkbox.Indicator />
    </Checkbox.Root>
  </Checkbox.Group>

  <!-- With form submission -->
  <Checkbox.Root>
    <Checkbox.Indicator />

    <Checkbox.HiddenInput />
  </Checkbox.Root>
</template>

Group Mode

Wrap checkboxes in Checkbox.Group for multi-selection with array-based v-model:

Selected: none

<script setup lang="ts">
  import { Checkbox } from '@vuetify/v0'
  import { ref } from 'vue'

  const selected = ref<string[]>([])

  const options = [
    { value: 'apple', label: 'Apple' },
    { value: 'banana', label: 'Banana' },
    { value: 'cherry', label: 'Cherry' },
  ]
</script>

<template>
  <Checkbox.Group v-model="selected" class="flex flex-col gap-2">
    <label
      v-for="option in options"
      :key="option.value"
      class="inline-flex items-center gap-2"
    >
      <Checkbox.Root
        class="size-5 border rounded inline-flex items-center justify-center border-divider data-[state=checked]:bg-primary data-[state=checked]:border-primary"
        :value="option.value"
      >
        <Checkbox.Indicator class="text-on-primary text-sm">✓</Checkbox.Indicator>
      </Checkbox.Root>
      <span>{{ option.label }}</span>
    </label>
  </Checkbox.Group>

  <p class="mt-4 text-sm text-on-surface-variant">
    Selected: {{ selected.join(', ') || 'none' }}
  </p>
</template>

Accessibility

The Checkbox.Root component renders as a button and handles all ARIA attributes automatically:

  • role="checkbox" for proper semantics

  • aria-checked reflects state (true, false, or "mixed")

  • aria-disabled when checkbox is disabled

  • aria-label from the label prop

  • tabindex="0" for keyboard focus (removed when disabled)

  • Space key toggles the checkbox (Enter works when rendered as button)

For custom implementations, use renderless mode and bind the attrs slot prop to your element:

vue
<template>
  <Checkbox.Root v-slot="{ attrs }" renderless>
    <div v-bind="attrs">
      <!-- Custom checkbox visual -->
    </div>
  </Checkbox.Root>
</template>

Form Integration

When the name prop is provided on Checkbox.Root, a hidden native checkbox is automatically rendered for form submission:

vue
<template>
  <!-- Auto-renders hidden input for form submission -->
  <Checkbox.Root name="agree" value="yes">
    <Checkbox.Indicator>✓</Checkbox.Indicator>
  </Checkbox.Root>
</template>

For custom form integration, use Checkbox.HiddenInput explicitly:

vue
<template>
  <Checkbox.Root>
    <Checkbox.Indicator>✓</Checkbox.Indicator>

    <Checkbox.HiddenInput name="custom" value="override" />
  </Checkbox.Root>
</template>

Indeterminate State

Use Checkbox.SelectAll within a group for “select all” patterns. It automatically reflects the group’s aggregate state and toggles all items on click:

Selected: none

<script setup lang="ts">
  import { Checkbox } from '@vuetify/v0'
  import { ref } from 'vue'

  const selected = ref<string[]>([])

  const options = [
    { value: 'apple', label: 'Apple' },
    { value: 'banana', label: 'Banana' },
    { value: 'cherry', label: 'Cherry' },
  ]
</script>

<template>
  <Checkbox.Group v-model="selected">
    <div class="flex flex-col gap-2">
      <label class="inline-flex items-center gap-2 font-medium">
        <Checkbox.SelectAll
          class="size-5 border rounded inline-flex items-center justify-center border-divider data-[state=checked]:bg-primary data-[state=checked]:border-primary data-[state=indeterminate]:bg-primary data-[state=indeterminate]:border-primary"
        >
          <Checkbox.Indicator v-slot="{ isMixed }" class="text-on-primary text-sm">
            <span v-if="isMixed">−</span>
            <span v-else>✓</span>
          </Checkbox.Indicator>
        </Checkbox.SelectAll>
        <span>Select All</span>
      </label>

      <div class="ml-6 flex flex-col gap-2">
        <label
          v-for="option in options"
          :key="option.value"
          class="inline-flex items-center gap-2"
        >
          <Checkbox.Root
            class="size-5 border rounded inline-flex items-center justify-center border-divider data-[state=checked]:bg-primary data-[state=checked]:border-primary"
            :value="option.value"
          >
            <Checkbox.Indicator class="text-on-primary text-sm">✓</Checkbox.Indicator>
          </Checkbox.Root>
          <span>{{ option.label }}</span>
        </label>
      </div>
    </div>
  </Checkbox.Group>

  <p class="mt-4 text-sm text-on-surface-variant">
    Selected: {{ selected.join(', ') || 'none' }}
  </p>
</template>

The SelectAll component:

  • Binds to the group’s isAllSelected and isMixed state

  • Calls toggleAll on click

  • Does NOT register as a group item

  • Sets aria-checked="mixed" and data-state="indeterminate" when partially selected

API Reference

The following API details are for all variations of the Checkbox component.

Checkbox.Root

Props

id

ID

Unique identifier (auto-generated if not provided)

Default: useId()

label

string

Optional display label (passed through to slot)

value

V

Value associated with this checkbox (used in group mode and form submission)

name

string

Form field name - triggers auto hidden input when provided

form

string

Associate with form by ID

disabled

MaybeRef<boolean>

Disables this checkbox

Default: false

indeterminate

MaybeRef<boolean>

Sets the indeterminate state

Default: false

namespace

string

Namespace for context provision to children (Indicator, HiddenInput)

Default: "v0:checkbox:root"

groupNamespace

string

Namespace for connecting to parent Checkbox.Group

Default: "v0:checkbox:group"

ariaLabelledby

string

ID of element that labels this checkbox

ariaDescribedby

string

ID of element that describes this checkbox

ariaInvalid

boolean

Whether the checkbox has an invalid value

modelValue

boolean

Events

update:model-value

[value: boolean]

Slots

default

CheckboxRootSlotProps<V>

Checkbox.Group

Props

namespace

string

Namespace for dependency injection

Default: "v0:checkbox:group"

disabled

boolean

Disables the entire checkbox group

Default: false

enroll

boolean

Auto-select non-disabled items on registration

Default: false

mandatory

boolean | "force"

Controls mandatory checkbox behavior: - false (default): No mandatory enforcement - true: Prevents deselecting the last selected item - `force`: Automatically selects the first non-disabled item on registration

Default: false

label

string

Accessible name for the group

ariaLabelledby

string

ID of element that labels this group

ariaDescribedby

string

ID of element that describes this group

modelValue

T | T[]

Events

update:model-value

[value: T | T[]]

Slots

default

CheckboxGroupSlotProps

Checkbox.HiddenInput

Props

value

string

Submitted value when checked (defaults to context value or 'on')

name

string

Form field name (defaults to context value)

namespace

string

Namespace for context injection from parent Checkbox.Root

Default: "v0:checkbox:root"

form

string

Associate with form by ID (defaults to context value)

Checkbox.Indicator

Props

namespace

string

Namespace for context injection from parent Checkbox.Root

Default: "v0:checkbox:root"

Slots

default

CheckboxIndicatorSlotProps

Checkbox.SelectAll

Props

label

string

Optional display label (passed through to slot and aria-label)

disabled

boolean

Disables this checkbox

namespace

string

Namespace for context provision to children (Indicator)

groupNamespace

string

Namespace for connecting to parent Checkbox.Group

ariaLabelledby

string

ID of element that labels this checkbox

ariaDescribedby

string

ID of element that describes this checkbox

Slots

default

CheckboxSelectAllSlotProps
Was this page helpful?

© 2016-1970 Vuetify, LLC
Ctrl+/