Checkbox 复选框
复选框允许用户从列表中选择多项,或标记单个项目为选中状态
用法
import { Checkbox } from '@lenso/ui';此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox } from "@lenso/ui";
export function Basic() { return ( <Checkbox name="basic-terms"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Accept terms and conditions </Checkbox.Content> </Checkbox> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
组件结构
import { Checkbox, Description, FieldError } from '@lenso/ui';
export default () => ( <Checkbox> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Label {/* 纯文本 — 可点击标签与无障碍名称 */} </Checkbox.Content> <Description /> {/* 可选 — 字段级帮助文本 */} <FieldError /> {/* 可选 — 校验消息 */} </Checkbox>);示例
变体
Checkbox 组件支持两种视觉变体:
primary(默认)- 标准样式与默认背景,适用于大多数场景secondary- 低强调变体,适用于 Surface 组件内
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox, Description, TextField } from "@lenso/ui";import { checkboxSupportingStyles } from "@lenso/tokens/checkbox";import * as stylex from "@stylexjs/stylex";const styles = stylex.create({ root: { display: "flex", flexDirection: "column", gap: "1rem" }, section: { display: "flex", flexDirection: "column", gap: ".5rem" }, heading: { fontSize: ".875rem", fontWeight: 500, color: "var(--muted)" },});export function Variants() { return ( <div {...stylex.props(styles.root)}> <div {...stylex.props(styles.section)}> <p {...stylex.props(styles.heading)}>Primary variant</p> <TextField> <Checkbox id="primary" name="primary" variant="primary"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Primary checkbox </Checkbox.Content> <Description xstyle={checkboxSupportingStyles.direct}> Standard styling with default background </Description> </Checkbox> </TextField> </div> <div {...stylex.props(styles.section)}> <p {...stylex.props(styles.heading)}>Secondary variant</p> <TextField> <Checkbox id="secondary" name="secondary" variant="secondary"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Secondary checkbox </Checkbox.Content> <Description xstyle={checkboxSupportingStyles.direct}> Lower emphasis variant for use in surfaces </Description> </Checkbox> </TextField> </div> </div> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
全圆角
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox } from "@lenso/ui";import { labelStyles } from "@lenso/tokens/label";import * as stylex from "@stylexjs/stylex";const styles = stylex.create({ root: { display: "flex", flexDirection: "column", gap: "1.5rem" }, section: { display: "flex", flexDirection: "column", gap: ".75rem" }, label: { color: "var(--muted)" }, smallIndicator: { "--checkbox-checkmark-size": ".5rem" }, extraLargeIndicator: { "--checkbox-checkmark-size": "1rem" }, small: { width: ".75rem", height: ".75rem", borderRadius: "9999px", "::before": { borderRadius: "9999px" }, }, medium: { width: "1rem", height: "1rem", borderRadius: "9999px", "::before": { borderRadius: "9999px" }, }, large: { width: "1.25rem", height: "1.25rem", borderRadius: "9999px", "::before": { borderRadius: "9999px" }, }, extraLarge: { width: "1.5rem", height: "1.5rem", borderRadius: "9999px", "::before": { borderRadius: "9999px" }, },});export function FullRounded() { return ( <div {...stylex.props(styles.root)}> <div {...stylex.props(styles.section)}> <span {...stylex.props(labelStyles.label, styles.label)}>Rounded checkboxes</span> <Checkbox name="small-rounded"> <Checkbox.Content> <Checkbox.Control xstyle={styles.small}> <Checkbox.Indicator xstyle={styles.smallIndicator} /> </Checkbox.Control> Small size </Checkbox.Content> </Checkbox> </div> <div {...stylex.props(styles.section)}> <Checkbox name="default-rounded"> <Checkbox.Content> <Checkbox.Control xstyle={styles.medium}> <Checkbox.Indicator /> </Checkbox.Control> Default size </Checkbox.Content> </Checkbox> </div> <div {...stylex.props(styles.section)}> <Checkbox name="large-rounded"> <Checkbox.Content> <Checkbox.Control xstyle={styles.large}> <Checkbox.Indicator /> </Checkbox.Control> Large size </Checkbox.Content> </Checkbox> </div> <div {...stylex.props(styles.section)}> <Checkbox name="xl-rounded"> <Checkbox.Content> <Checkbox.Control xstyle={styles.extraLarge}> <Checkbox.Indicator xstyle={styles.extraLargeIndicator} /> </Checkbox.Control> Extra large size </Checkbox.Content> </Checkbox> </div> </div> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
禁用
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox, Description, TextField } from "@lenso/ui";import { checkboxSupportingStyles } from "@lenso/tokens/checkbox";export function Disabled() { return ( <TextField> <Checkbox disabled id="feature" aria-describedby="feature-help"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Premium Feature </Checkbox.Content> <Description id="feature-help" xstyle={checkboxSupportingStyles.direct}> This feature is coming soon </Description> </Checkbox> </TextField> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
外部标签
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox } from "@lenso/ui";import { labelStyles } from "@lenso/tokens/label";import * as stylex from "@stylexjs/stylex";const styles = stylex.create({ root: { display: "flex", alignItems: "center", gap: ".75rem" } });export function ExternalLabel() { return ( <div {...stylex.props(styles.root)}> <Checkbox id="label-marketing"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> </Checkbox.Content> </Checkbox> <label {...stylex.props(labelStyles.label)} htmlFor="label-marketing"> Send me marketing emails </label> </div> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
带描述
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox, Description, TextField } from "@lenso/ui";import { checkboxSupportingStyles } from "@lenso/tokens/checkbox";export function WithDescription() { return ( <TextField> <Checkbox name="description-notifications" aria-describedby="description-notifications-help"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Email notifications </Checkbox.Content> <Description id="description-notifications-help" xstyle={checkboxSupportingStyles.direct}> Get notified when someone mentions you in a comment </Description> </Checkbox> </TextField> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
默认选中
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox } from "@lenso/ui";export function DefaultSelected() { return ( <Checkbox defaultChecked id="default-notifications"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Enable email notifications </Checkbox.Content> </Checkbox> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
无效状态
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox, FieldError, TextField } from "@lenso/ui";import { checkboxSupportingStyles } from "@lenso/tokens/checkbox";export function Invalid() { return ( <TextField invalid> <Checkbox required name="agreement"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> I agree to the terms </Checkbox.Content> <FieldError match xstyle={[checkboxSupportingStyles.direct, checkboxSupportingStyles.error]} > You must accept the terms to continue </FieldError> </Checkbox> </TextField> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
受控组件
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox } from "@lenso/ui";import { useState } from "react";import * as stylex from "@stylexjs/stylex";const styles = stylex.create({ root: { display: "flex", flexDirection: "column", gap: ".75rem" }, status: { fontSize: ".875rem", color: "var(--muted)" }, strong: { fontWeight: 500 },});export function Controlled() { const [isSelected, setIsSelected] = useState(true); return ( <div {...stylex.props(styles.root)}> <Checkbox id="email-notifications" checked={isSelected} onCheckedChange={setIsSelected}> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Email notifications </Checkbox.Content> </Checkbox> <p {...stylex.props(styles.status)}> Status: <span {...stylex.props(styles.strong)}>{isSelected ? "Enabled" : "Disabled"}</span> </p> </div> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
半选状态
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox, Description, TextField } from "@lenso/ui";import { checkboxSupportingStyles } from "@lenso/tokens/checkbox";import { useState } from "react";export function Indeterminate() { const [isIndeterminate, setIsIndeterminate] = useState(true); const [isSelected, setIsSelected] = useState(false); return ( <TextField> <Checkbox id="select-all" indeterminate={isIndeterminate} checked={isSelected} onCheckedChange={(selected) => { setIsSelected(selected); setIsIndeterminate(false); }} > <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Select all </Checkbox.Content> <Description xstyle={checkboxSupportingStyles.direct}> Shows indeterminate state (dash icon) </Description> </Checkbox> </TextField> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
表单集成
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Button, Checkbox } from "@lenso/ui";import type { FormEvent } from "react";import * as stylex from "@stylexjs/stylex";const styles = stylex.create({ form: { display: "flex", flexDirection: "column", gap: "1rem" }, items: { display: "flex", flexDirection: "column", gap: ".75rem" }, submit: { marginTop: "1rem" },});export function Form() { const handleSubmit = (e: FormEvent<HTMLFormElement>) => { e.preventDefault(); const formData = new FormData(e.currentTarget); alert( `Form submitted with:\n${Array.from(formData.entries()) .map(([key, value]) => `${key}: ${value}`) .join("\n")}`, ); }; return ( <form {...stylex.props(styles.form)} onSubmit={handleSubmit}> <div {...stylex.props(styles.items)}> <Checkbox name="notifications" value="on"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Enable notifications </Checkbox.Content> </Checkbox> <Checkbox defaultChecked name="newsletter" value="on"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Subscribe to newsletter </Checkbox.Content> </Checkbox> <Checkbox name="marketing" value="on"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Receive marketing updates </Checkbox.Content> </Checkbox> </div> <Button xstyle={styles.submit} size="sm" type="submit" variant="primary"> Submit </Button> </form> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
渲染属性
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox, Description, TextField } from "@lenso/ui";import { checkboxSupportingStyles } from "@lenso/tokens/checkbox";export function RenderProps() { return ( <TextField> <Checkbox id="render-props-terms" render={(props, { checked }) => ( <span {...props}> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> {checked ? "Terms accepted" : "Accept terms"} </Checkbox.Content> <Description xstyle={checkboxSupportingStyles.direct}> {checked ? "Thank you for accepting" : "Please read and accept the terms"} </Description> </span> )} /> </TextField> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
渲染函数
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox } from "@lenso/ui";export function RenderFunction() { return ( <Checkbox render={(props) => <div {...props} data-custom="bar" />}> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator /> </Checkbox.Control> Accept terms and conditions </Checkbox.Content> </Checkbox> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
自定义指示器
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox } from "@lenso/ui";import * as stylex from "@stylexjs/stylex";const styles = stylex.create({ root: { display: "flex", gap: "1rem" } });export function CustomIndicator() { return ( <div {...stylex.props(styles.root)}> <Checkbox defaultChecked name="heart"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator render={(props, { checked }) => ( <span {...props}> {checked ? ( <svg aria-hidden="true" fill="currentColor" viewBox="0 0 24 24"> <path d="M12.62 20.81c-.34.12-.9.12-1.24 0C8.48 19.82 2 15.69 2 8.69 2 5.6 4.49 3.1 7.56 3.1c1.82 0 3.43.88 4.44 2.24a5.53 5.53 0 0 1 4.44-2.24C19.51 3.1 22 5.6 22 8.69c0 7-6.48 11.13-9.38 12.12Z" /> </svg> ) : null} </span> )} /> </Checkbox.Control> Heart </Checkbox.Content> </Checkbox> <Checkbox defaultChecked name="plus"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator render={(props, { checked }) => ( <span {...props}> {checked ? ( <svg aria-hidden="true" fill="none" viewBox="0 0 24 24"> <path d="M6 12H18" stroke="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="3" /> <path d="M12 18V6" stroke="currentColor" strokeLinecap="round" strokeLinejoin="round" strokeWidth="3" /> </svg> ) : null} </span> )} /> </Checkbox.Control> Plus </Checkbox.Content> </Checkbox> <Checkbox indeterminate name="indeterminate"> <Checkbox.Content> <Checkbox.Control> <Checkbox.Indicator render={(props, { indeterminate }) => ( <span {...props}> {indeterminate ? ( <svg aria-hidden="true" stroke="currentColor" strokeWidth={3} viewBox="0 0 24 24" > <line x1="21" x2="3" y1="12" y2="12" /> </svg> ) : null} </span> )} /> </Checkbox.Control> Indeterminate </Checkbox.Content> </Checkbox> </div> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
自定义样式
Tailwind CSS
此预览复用英文版适配,不代表中文源示例已完成本地实现。
"use client";/** Adapted from HeroUI v3.2.6. SPDX-License-Identifier: Apache-2.0 */import { Checkbox } from "@lenso/ui";import * as stylex from "@stylexjs/stylex";const styles = stylex.create({ control: { backgroundColor: "var(--success-soft)", "::before": { backgroundColor: { default: "var(--success)", ":is([data-slot='checkbox']:hover *)": "var(--success)", ":is([data-slot='checkbox'][data-invalid] *)": "var(--success)", }, }, }, indicator: { color: "var(--success-foreground)" },});export function CustomStyles() { return ( <Checkbox id="custom"> <Checkbox.Content> <Checkbox.Control xstyle={styles.control}> <Checkbox.Indicator xstyle={styles.indicator} /> </Checkbox.Control> Custom styled checkbox </Checkbox.Content> </Checkbox> );}Local adaptation source above. Derived from HeroUI v3.2.6 source.
全局 CSS
可使用 @layer components 指令自定义 Checkbox 组件类。
了解更多。
@layer components { .checkbox { @apply inline-flex gap-3 items-center; }
.checkbox__control { @apply size-5 border-2 border-gray-400 rounded data-[selected=true]:bg-blue-500 data-[selected=true]:border-blue-500;
/* Animated background indicator */ &::before { @apply bg-accent pointer-events-none absolute inset-0 z-0 origin-center scale-50 rounded-md opacity-0 content-[''];
transition: scale 200ms linear, opacity 200ms linear, background-color 200ms ease-out; }
/* Show indicator when selected */ &[data-selected="true"]::before { @apply scale-100 opacity-100; } }
.checkbox__indicator { @apply text-white; }
.checkbox__content { @apply items-center gap-3; }}样式参考
HeroUI 遵循 BEM 方法论,确保组件变体与状态可复用且易于自定义。
CSS 类
Checkbox 组件使用以下 CSS 类(查看源码样式):
基础类 [!toc]
.checkbox- 基础复选框容器(字段).checkbox__content- 包裹控件与标签文本的可点击 label.checkbox__control- 复选框控件框.checkbox__indicator- 复选框勾选指示器
交互状态
复选框同时支持 CSS 伪类与 data 属性:
- Selected:
[data-selected="true"]或[aria-checked="true"](显示勾选与背景色变化) - Indeterminate:
[data-indeterminate="true"](显示不确定状态的短横线) - Invalid:
[data-invalid="true"]或[aria-invalid="true"](显示 danger 色错误状态) - Hover:
Checkbox.Control(按钮)上的:hover或[data-hovered="true"] - Focus:按钮上的
:focus-visible或[data-focus-visible="true"](控件上显示焦点环) - Disabled:字段上的
[data-disabled="true"](降低透明度,包括帮助文本) - Pressed:
:active或[data-pressed="true"]
API 参考
Checkbox
| Prop | 类型 | 默认值 | 描述 |
|---|---|---|---|
isSelected | boolean | false | 是否选中 |
defaultSelected | boolean | false | 默认是否选中(非受控) |
isIndeterminate | boolean | false | 是否处于不确定状态 |
isDisabled | boolean | false | 是否禁用 |
isInvalid | boolean | false | 是否无效 |
isReadOnly | boolean | false | 是否只读 |
isRequired | boolean | false | 是否必须选中 |
validate | (value: boolean) => ValidationError | true | null | undefined | - | 自定义验证函数 |
validationBehavior | 'native' | 'aria' | 'native' | 使用原生 HTML 表单验证还是 ARIA |
variant | "primary" | "secondary" | "primary" | 视觉变体。primary 为默认带阴影样式;secondary 为低强调无阴影,适用于 Surface 内 |
name | string | - | 提交 HTML 表单时 input 元素的名称 |
value | string | - | 提交 HTML 表单时 input 元素的值 |
onChange | (isSelected: boolean) => void | - | 值变化时的回调 |
children | React.ReactNode | (values: CheckboxFieldRenderProps) => React.ReactNode | - | 内容或字段 render prop |
render | DOMRenderFunction<keyof React.JSX.IntrinsicElements, CheckboxFieldRenderProps> | - | 使用自定义 render 函数覆盖默认 DOM 元素 |
Checkbox.Content
可点击的 <label>,包裹控件与标签文本。将 Checkbox.Control 与 Label 放在其中;Description/FieldError 作为 Checkbox.Content 的兄弟节点。无标签的复选框可省略 Label,并在 Checkbox 上传递 aria-label。
| Prop | 类型 | 默认值 | 描述 |
|---|---|---|---|
children | React.ReactNode | (values: CheckboxButtonRenderProps) => React.ReactNode | - | 按钮内容(控件 + 标签)或按钮 render prop |
className | string | (values: CheckboxButtonRenderProps) => string | - | 应用于可点击 label 的类 |
CheckboxFieldRenderProps
在根 Checkbox 上使用 render prop 时,提供以下字段级值:
| Prop | 类型 | 描述 |
|---|---|---|
isSelected | boolean | 是否当前选中 |
isIndeterminate | boolean | 是否处于不确定状态 |
isDisabled | boolean | 是否禁用 |
isReadOnly | boolean | 是否只读 |
isInvalid | boolean | 是否无效 |
isRequired | boolean | 是否必填 |
CheckboxButtonRenderProps
Checkbox.Control 与 Checkbox.Indicator 使用按钮级 render props(isHovered、isPressed、isFocusVisible 等)。将函数作为 Checkbox.Control 子节点或传给 Checkbox.Indicator 以访问它们。