ToggleGroup
概述
一组可切换开关状态的双态按钮,支持单选与多选模式。适用于格式工具栏、筛选标签,或任何即时生效的互斥(或多选)分段控件。若需要外观统一的分段单选控件,SSegment 可能更合适;若只需单个独立的开关按钮,请使用 SToggle。
用法
特性
- 🎯 单选 / 多选 — 通过
multiple在单选与多选间切换,泛型值类型安全(M extends boolean,T extends DefinedValue) - 🎚 受控 / 非受控 —
v-model与defaultValue(标量或数组)由useControllableState支撑 - ⌨️ Roving focus 键盘导航 — 方向键在条目间移动焦点,
loop支持循环,RTL 下方向自动反转 - ♿
aria-pressed+data-state(on/off)双通道反射,axe 零违规 - 🎨
toggleGroupVariants提供 3 变体(outline/soft/ghost)× 6 尺寸 × 8 颜色 × 2 方向 - 🧩 每个条目继承完整
Buttonprops(as/asChild、type、条目级disabled),slot 暴露pressed/disabled - 📝 表单集成 — 设置
name/required后渲染隐藏 input,选择值随所属表单提交 - 🧩
ui按 slot 覆盖类名(root/item)
组件系列
SToggleGroup— 组根组件,管理选择状态、方向与 roving focusSToggleGroupItem— 单个可切换按钮;传入唯一value以标识其在组内的身份
演示
基础
API
Aria 层
3ToggleGroup<M, T>
属性
| 属性名 | 类型 | 默认值 | 描述 |
|---|---|---|---|
class | ClassValue | — | 应用于根元素的额外类名。 |
color | ThemeColor | — | 组件的主题颜色。 |
size | ThemeSize | — | 组件的视觉尺寸。 |
variant | ToggleGroupVariant | — | 该组件的视觉变体。 |
ui | Partial<ToggleGroupUi> | — | 该组件的按槽类重写。 |
rovingFocus | boolean | — | 当值为 `false` 时,将禁用使用方向键浏览项目的功能。 |
disabled | boolean | — | 当值为 `true` 时,将阻止与该组中所有项的交互。 |
orientation | DataOrientation | — | 组件的取向。 |
dir | Direction | — | 如适用,请标注该组的阅读方向。 |
loop | boolean | — | 当值为 `true` 时,键盘导航将从最后一个项目循环至第一个项目,反之亦然。 |
modelValue | (M extends true ? T[] : T) | — | 所选项的受控值。
当需要控制项的状态时使用此属性。可通过 `v-model` 进行绑定。 |
defaultValue | (M extends true ? T[] : T) | — | 所选项的默认值。
当需要设置项的初始状态时,请使用此选项。 |
multiple | M | — | 用于确定一次可选择“单个”还是“多个”项目。
此属性将覆盖根据 `modelValue` 和 `defaultValue` 推断出的类型。 |
clearable | boolean | — | 当 `multiple` 为 false 时,是否可以清除所选项目。 |
selectionBehavior | SelectionBehavior | 'toggle' | 集合中多选功能应如何工作。 |
name | string | — | 字段的名称。作为名称/值对的一部分,与其所属表单一同提交。 |
required | boolean | — | 当值为 `true` 时,表示用户必须先设置该值,所属表单才能提交。 |
asChild | boolean | — | 将默认渲染元素替换为作为子元素传递的元素,并合并两者的属性及行为。 |
as | AsTag | Component | 'div' | 该组件应渲染为的元素或组件。可通过 `asChild` 进行覆盖。 |
事件
| 事件名 | 参数 | 描述 |
|---|---|---|
update:modelValue | M extends true ? T[] : T | — |
ToggleGroupItem<T>
属性
| 属性名 | 类型 | 默认值 | 描述 |
|---|---|---|---|
value | T | — | 用于标识组内项的唯一值。 |
type | ButtonType | 'button' | 按钮元素的类型。可以是 'button'、'submit' 或 'reset' 之一。 |
disabled | boolean | — | 该组件是否已禁用。 |
asChild | boolean | — | 将默认渲染元素替换为作为子元素传递的元素,并合并两者的属性及行为。 |
as | AsTag | Component | 'div' | 该组件应渲染为的元素或组件。可通过 `asChild` 进行覆盖。 |
ToggleGroupRoot<M, T>
属性
| 属性名 | 类型 | 默认值 | 描述 |
|---|---|---|---|
rovingFocus | boolean | — | 当值为 `false` 时,将禁用使用方向键浏览项目的功能。 |
disabled | boolean | — | 当值为 `true` 时,将阻止与该组中所有项的交互。 |
orientation | DataOrientation | — | 组件的取向。 |
dir | Direction | — | 如适用,请标注该组的阅读方向。 |
loop | boolean | — | 当值为 `true` 时,键盘导航将从最后一个项目循环至第一个项目,反之亦然。 |
modelValue | (M extends true ? T[] : T) | — | 所选项的受控值。
当需要控制项的状态时使用此属性。可通过 `v-model` 进行绑定。 |
defaultValue | (M extends true ? T[] : T) | — | 所选项的默认值。
当需要设置项的初始状态时,请使用此选项。 |
multiple | M | — | 用于确定一次可选择“单个”还是“多个”项目。
此属性将覆盖根据 `modelValue` 和 `defaultValue` 推断出的类型。 |
clearable | boolean | — | 当 `multiple` 为 false 时,是否可以清除所选项目。 |
selectionBehavior | SelectionBehavior | 'toggle' | 集合中多选功能应如何工作。 |
name | string | — | 字段的名称。作为名称/值对的一部分,与其所属表单一同提交。 |
required | boolean | — | 当值为 `true` 时,表示用户必须先设置该值,所属表单才能提交。 |
asChild | boolean | — | 将默认渲染元素替换为作为子元素传递的元素,并合并两者的属性及行为。 |
as | AsTag | Component | 'div' | 该组件应渲染为的元素或组件。可通过 `asChild` 进行覆盖。 |
事件
| 事件名 | 参数 | 描述 |
|---|---|---|
update:modelValue | M extends true ? T[] : T | — |
注意事项
架构与行业对标
VeanUI 由 Aria ToggleGroupRoot(useSelection + useRovingFocusGroup + 隐藏 input 表单代理)与 ToggleGroupItem(依据 rovingFocus 动态选择 useRovingFocusGroupItem 或 Button 基座)构成。UI 层 SToggleGroup 是仅计算 toggleGroupVariants 类名的薄透传包装;data-state 通过 UnoCSS data-[state=on]:* 选择器驱动按下样式。toggle-group 为 Radix/shadcn 原生模式;其余对标库以单选/按钮组或分段控件表达同一交互。
| 能力 | VeanUI | Ant Design | Element Plus | Mantine | Naive UI | shadcn ToggleGroup |
|---|---|---|---|---|---|---|
| Aria/styled 分离 | ✅ | — | — | — | — | ✅ |
| 单选 / 多选 | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ |
| 受控 / 非受控 | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ |
| Roving focus 方向键 | ✅ | — | — | — | — | ✅ |
| Loop 循环导航 | ✅ | — | — | — | — | ✅ |
| RTL 方向感知 | ✅ | — | — | — | — | ✅ |
aria-pressed + data-state | ✅ | — | — | — | — | ✅ |
| 方向(横排/竖排) | ✅ | — | ✅ | ✅ | — | ✅ |
| 变体 × 尺寸 × 颜色 | ✅ | ✅ | ✅ | ✅ | ✅ | — |
| 隐藏 input 表单提交 | ✅ | — | — | — | — | — |
| 单选可取消选中 | ✅ | ✅ | — | — | — | — |
| 禁用(组级 + 条目级) | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ |
使用注意
rovingFocus、loop、clearable默认均为true。关闭rovingFocus后退化为普通role="group",无方向键导航。- 组级
disabled会禁用全部条目;条目级disabled仅影响自身,二者取并集(group || item)。 - 单选模式下再次点击已选项会发出
update:modelValue且值为undefined(除非:clearable="false")——父组件需处理undefined。 - 表单提交需设置
name;required仅标记隐藏 input,不参与校验。 - 纯图标条目请补充
aria-label,否则按钮无可访问名称。 - 在
form中,仅当组为表单控件且设置了name时才渲染隐藏 input。
常见问题
单选还是多选?
默认单选。传入 multiple 可同时选中多个条目——此时 modelValue/defaultValue 变为数组,泛型 M 由它们自动推断。
单选模式下如何允许取消选中?
clearable 默认为 true,点击已激活条目即清除选择并发出 undefined。设置 :clearable="false" 可始终保持必选。
如何让方向键循环导航?
保持 loop(默认 true)开启,焦点会从末尾回绕到首项、反之亦然,并自动跳过禁用条目。
SToggleGroup 与 SToggle 有什么区别?
SToggleGroup 协调一组条目:统一管理单选/多选、roving-focus 键盘导航与共享的 aria-pressed 状态。SToggle 是独立单开关,无组内协调。
如何让组竖排显示?
设置 orientation="vertical" — 布局切换为纵向堆叠,方向键导航也随之沿纵轴移动。