suiss/uim · React Native Component
Checkbox
A small box that toggles an option on or off, with an indeterminate state.
Checkbox is an open-source mobile component from suiss/uim for React Native and Expo, with SwiftUI and Jetpack Compose versions built from the same design tokens. The @esuiss/uim CLI copies its source into your project, so you own the code.


import * as React from "react"
import { Checkbox } from "@/components/ui/checkbox"
function CheckboxDemo({ initial = false }: { initial?: boolean }) {
const [checked, setChecked] = React.useState(initial)
return <Checkbox checked={checked} onCheckedChange={setChecked} />
}
export function CheckboxExample() {
return (
<CheckboxDemo />
)
}import EsuissUI
import SwiftUI
struct CheckboxExample: View {
var body: some View {
CheckboxDemo(initial: false)
}
}
struct CheckboxDemo: View {
@State private var checked: Bool
init(initial: Bool) {
_checked = State(initialValue: initial)
}
var body: some View {
Toggle(isOn: $checked) { EmptyView() }
.toggleStyle(.checkbox)
}
}import androidx.compose.foundation.layout.Row
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.runtime.setValue
import com.esuiss.ui.components.Checkbox
@Composable
fun CheckboxExample() {
CheckboxDemo(initial = false)
}
@Composable
fun CheckboxDemo(initial: Boolean) {
var checked by rememberSaveable { mutableStateOf(initial) }
Row {
Checkbox(checked, { checked = it })
}
}Checkbox is a Pressable with the checkbox role that shows a check icon when checked and a minus icon when indeterminate. It has an enlarged hit area around the box so it is easy to tap.
Use it for options that can be combined, such as terms acceptance or multi-select lists. For a single on/off setting that applies right away, use Switch.
Installation
$ pnpm dlx @esuiss/uim@latest add checkbox$ pnpm dlx @esuiss/uim@latest add checkbox --platform swift$ pnpm dlx @esuiss/uim@latest add checkbox --platform kotlinThe CLI also adds what it builds on: Icon, Text.
Manual
- Install the dependencies:
npx expo install cn phosphor-react-native react-native-svg-
Add the pieces it builds on: Icon, Text, and the primitives
components/primitives/checkbox.tsx,components/primitives/use-render.tsx. -
Copy the source into
components/ui/checkbox.tsx:
import { cn } from "cn"
import { CheckIcon, MinusIcon } from "phosphor-react-native"
import * as CheckboxPrimitive from "@/components/primitives/checkbox"
import { resolveClassName } from "@/components/primitives/use-render"
import { Icon } from "@/components/ui/icon"
const HIT_SLOP = { top: 8, bottom: 8, left: 12, right: 12 }
function checkboxClassName(
state: CheckboxPrimitive.RootState,
invalid: boolean | undefined
) {
const checked = state.checked || state.indeterminate
return cn(
"size-4 shrink-0 items-center justify-center rounded-[4px] border",
checked- Update the import paths to match your project.
- Install the dependencies:
npx expo install cn phosphor-react-native react-native-svg-
Add the pieces it builds on: Icon, Text, and the primitives
components/primitives/checkbox.tsx,components/primitives/use-render.tsx. -
Copy the source into
components/ui/checkbox.tsx:
import { cn } from "cn"
import { CheckIcon, MinusIcon } from "phosphor-react-native"
import * as CheckboxPrimitive from "@/components/primitives/checkbox"
import { resolveClassName } from "@/components/primitives/use-render"
import { Icon } from "@/components/ui/icon"
const HIT_SLOP = { top: 8, bottom: 8, left: 12, right: 12 }
function checkboxClassName(
state: CheckboxPrimitive.RootState,
invalid: boolean | undefined
) {
const checked = state.checked || state.indeterminate
return cn(
"size-4 shrink-0 items-center justify-center rounded-[4px] border",
checked- Update the import paths to match your project.
- Install the dependencies:
npx expo install phosphor-react-native react-native-svg-
Add the pieces it builds on: Icon, Text, and the primitives
components/primitives/checkbox.tsx,components/primitives/use-render.tsx. -
Copy the source into
components/ui/checkbox.tsx:
import { CheckIcon, MinusIcon } from "phosphor-react-native"
import {
Pressable,
type StyleProp,
StyleSheet,
type TextStyle,
type ViewStyle,
} from "react-native"
import * as CheckboxPrimitive from "@/components/primitives/checkbox"
import { resolveStyle } from "@/components/primitives/use-render"
import { Icon } from "@/components/ui/icon"
import { TextStyleContext } from "@/components/ui/text"
import { shadow, type ThemeColors, useTheme } from "@/components/ui/theme"
const HIT_SLOP = { top: 8, bottom: 8, left: 12, right: 12 }- Update the import paths to match your project.
-
Target iOS 17 or later.
-
Add the Swift package to your app:
.package(url: "https://github.com/phosphor-icons/swift", from: "2.1.0")- Copy the theme files every view uses:
import SwiftUI
import UIKit
struct RGBA: Sendable {
let red: CGFloat
let green: CGFloat
let blue: CGFloat
let alpha: CGFloat
init(_ hex: UInt32, _ alpha: CGFloat = 1) {
red = CGFloat((hex >> 16) & 0xFF) / 255
green = CGFloat((hex >> 8) & 0xFF) / 255
blue = CGFloat(hex & 0xFF) / 255
self.alpha = alpha
}import SwiftUI
extension Color {
public static let surface = Color.adaptive(light: .init(0xFFFFFF), dark: .init(0x000000))
public static let surfaceSecondary = Color.adaptive(light: .init(0xF5F5F7), dark: .init(0x161617))
public static let surfaceTertiary = Color.adaptive(light: .init(0xE8E8ED), dark: .init(0x2C2C2E))
public static let surfaceRaised = Color.adaptive(light: .init(0xFFFFFF), dark: .init(0x1D1D1F))
public static let label = Color.adaptive(light: .init(0x1D1D1F), dark: .init(0xF5F5F7))
public static let labelSecondary = Color.adaptive(light: .init(0x6E6E73), dark: .init(0xA1A1A6))
public static let labelTertiary = Color.adaptive(light: .init(0x86868B), dark: .init(0x86868B))
public static let labelQuaternary = Color.adaptive(light: .init(0xD2D2D7), dark: .init(0x424245))
public static let control = Color.adaptive(light: .init(0x000000, 0.04), dark: .init(0xFFFFFF, 0.1))
public static let controlPressed = Color.adaptive(light: .init(0x000000, 0.12), dark: .init(0xFFFFFF, 0.22))
public static let controlSelected = Color.adaptive(light: .init(0x1D1D1F), dark: .init(0xF5F5F7))
public static let controlDisabled = Color.adaptive(light: .init(0x000000, 0.03), dark: .init(0xFFFFFF, 0.05))
public static let onControlSelected = Color.adaptive(light: .init(0xFFFFFF), dark: .init(0x000000))- Copy the source and every file it uses:
import PhosphorSwift
import SwiftUI
extension Shadow {
static let control = Shadow(color: .black.opacity(0.08), radius: 0.5, y: 0.5)
static let thumb = Shadow(color: .black.opacity(0.12), radius: 1.5, y: 1)
}
struct SelectionIndicator<Mark: View>: View {
let checked: Bool
let pressed: Bool
let cornerRadius: CGFloat
let mark: Mark
@Environment(\.isEnabled) private var isEnabled
@Environment(\.isInvalid) private var invalidimport SwiftUI
extension EnvironmentValues {
@Entry public var isInvalid = false
@Entry var fieldInset = false
@Entry var fieldGroupInset = false
@Entry var fieldSetInset = false
}
extension View {
public func invalid(_ isInvalid: Bool = true) -> some View {
environment(\.isInvalid, isInvalid)
}
}
public enum FieldOrientation: CaseIterable, Sendable {import SwiftUI
extension EnvironmentValues {
@Entry public var hapticsEnabled = true
}
extension View {
public func haptics(_ enabled: Bool) -> some View {
environment(\.hapticsEnabled, enabled)
}
func hapticFeedback<Trigger: Equatable>(_ feedback: SensoryFeedback, trigger: Trigger) -> some View {
modifier(HapticFeedbackModifier(feedback: feedback, trigger: trigger) { _, _ in true })
}
func hapticFeedback<Trigger: Equatable>(import SwiftUI
public struct Separator: View {
let orientation: Axis
public init(_ orientation: Axis = .horizontal) {
self.orientation = orientation
}
public var body: some View {
Rectangle()
.fill(Color.separator)
.frame(width: orientation == .vertical ? 1 : nil, height: orientation == .horizontal ? 1 : nil)
.frame(maxWidth: orientation == .horizontal ? .infinity : nil, maxHeight: orientation == .vertical ? .infinity : nil)
.accessibilityHidden(true)
}import SwiftUI
public enum TextVariant: CaseIterable, Sendable {
case `default`, h1, h2, h3, h4, p, blockquote, code, lead, large, small, muted
var style: TextStyle {
switch self {
case .h1: .xl3
case .h2: .xl2
case .h3: .xl
case .h4, .lead, .large: .lg
case .code, .small, .muted: .sm
default: .base
}
}- Add the files to your app target.
- Set
minSdkto 24 or higher and add the dependencies:
implementation(platform("androidx.compose:compose-bom:2026.09.00"))
implementation("androidx.compose.foundation:foundation")
implementation("androidx.compose.ui:ui")
implementation("com.adamglin:phosphor-icon-android:1.0.0")- Copy the theme files every view uses:
package com.esuiss.ui.theme
import androidx.compose.foundation.isSystemInDarkTheme
import androidx.compose.runtime.Composable
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.runtime.Immutable
import androidx.compose.runtime.staticCompositionLocalOf
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.dropShadow
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.Shape
import androidx.compose.ui.graphics.shadow.Shadow as DropShadow
import androidx.compose.ui.text.TextStyle
import androidx.compose.ui.text.style.LineHeightStyle
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.DpOffsetpackage com.esuiss.ui.theme
import androidx.compose.runtime.Immutable
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.unit.dp
@Immutable
data class Colors(
val surface: Color,
val surfaceSecondary: Color,
val surfaceTertiary: Color,
val surfaceRaised: Color,
val label: Color,
val labelSecondary: Color,
val labelTertiary: Color,
val labelQuaternary: Color,- Copy the source and every file it uses:
package com.esuiss.ui.components
import androidx.compose.foundation.background
import androidx.compose.foundation.border
import androidx.compose.foundation.interaction.MutableInteractionSource
import androidx.compose.foundation.interaction.collectIsPressedAsState
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.size
import androidx.compose.foundation.selection.triStateToggleable
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Colorpackage com.esuiss.ui.components
import androidx.compose.runtime.compositionLocalOf
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.TextStyle
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.dp
val LocalContentStyle = compositionLocalOf { TextStyle.Default }
val LocalContentColor = compositionLocalOf { Color.Unspecified }
val LocalIconSize = compositionLocalOf { 20.dp }package com.esuiss.ui.components
import androidx.compose.foundation.background
import androidx.compose.foundation.gestures.Orientation
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.ColumnScope
import androidx.compose.foundation.layout.LayoutScopeMarker
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.RowScope
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.heightIn
import androidx.compose.foundation.layout.padding
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.foundation.text.BasicTextpackage com.esuiss.ui.components
import android.provider.Settings
import androidx.compose.animation.core.CubicBezierEasing
import androidx.compose.foundation.background
import androidx.compose.foundation.border
import androidx.compose.foundation.gestures.Orientation
import androidx.compose.foundation.text.selection.TextSelectionColors
import androidx.compose.runtime.Composable
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
import androidx.compose.ui.draw.drawWithContent
import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.geometry.Sizepackage com.esuiss.ui.components
import androidx.compose.runtime.Composable
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.runtime.remember
import androidx.compose.runtime.staticCompositionLocalOf
import androidx.compose.ui.hapticfeedback.HapticFeedback
import androidx.compose.ui.hapticfeedback.HapticFeedbackType
import androidx.compose.ui.platform.LocalHapticFeedback
val LocalHapticsEnabled = staticCompositionLocalOf { true }
@Composable
fun ProvideHaptics(enabled: Boolean, content: @Composable () -> Unit) {
CompositionLocalProvider(LocalHapticsEnabled provides enabled, content = content)
}package com.esuiss.ui.components
import androidx.compose.foundation.Image
import androidx.compose.foundation.layout.size
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.ColorFilter
import androidx.compose.ui.graphics.takeOrElse
import androidx.compose.ui.graphics.vector.ImageVector
import androidx.compose.ui.unit.Dp
import com.esuiss.ui.theme.EsuissTheme
@Composable
fun Icon(
imageVector: ImageVector,package com.esuiss.ui.components
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.RowScope
import androidx.compose.foundation.text.BasicText
import androidx.compose.runtime.Composable
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.unit.dp
import com.esuiss.ui.theme.EsuissTheme
import com.esuiss.ui.theme.Typography
@Composablepackage com.esuiss.ui.components
import androidx.compose.foundation.background
import androidx.compose.foundation.gestures.Orientation
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxHeight
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.width
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
import com.esuiss.ui.theme.EsuissTheme
@Composable
fun Separator(- Update the
com.esuiss.uipackage names to match your project.
Usage
import { Checkbox } from "@/components/ui/checkbox"<CheckboxDemo />Use checked with onCheckedChange for controlled state, or defaultChecked for uncontrolled. Set indeterminate for a parent checkbox whose children are partly selected.
Pair the checkbox with a Label: give the label a nativeID and the checkbox a matching accessibilityLabelledBy, and toggle the value from the label's onPress. Set invalid to show a danger border.
Examples
Checked
Starts checked.


import * as React from "react"
import { Checkbox } from "@/components/ui/checkbox"
function CheckboxDemo({ initial = false }: { initial?: boolean }) {
const [checked, setChecked] = React.useState(initial)
return <Checkbox checked={checked} onCheckedChange={setChecked} />
}
export function CheckboxCheckedExample() {
return (
<CheckboxDemo initial />
)
}import EsuissUI
import SwiftUI
struct CheckboxCheckedExample: View {
var body: some View {
CheckboxDemo(initial: true)
}
}
struct CheckboxDemo: View {
@State private var checked: Bool
init(initial: Bool) {
_checked = State(initialValue: initial)
}
var body: some View {
Toggle(isOn: $checked) { EmptyView() }
.toggleStyle(.checkbox)
}
}import androidx.compose.foundation.layout.Row
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.runtime.setValue
import com.esuiss.ui.components.Checkbox
@Composable
fun CheckboxCheckedExample() {
CheckboxDemo(initial = true)
}
@Composable
fun CheckboxDemo(initial: Boolean) {
var checked by rememberSaveable { mutableStateOf(initial) }
Row {
Checkbox(checked, { checked = it })
}
}With label
Linked to a Label that also toggles it.


import * as React from "react"
import { View } from "react-native"
import { Checkbox } from "@/components/ui/checkbox"
import { Label } from "@/components/ui/label"
function WithLabelDemo() {
const [checked, setChecked] = React.useState(false)
return (
<View className="flex-row items-center gap-3">
<Checkbox
accessibilityLabelledBy="terms"
checked={checked}
onCheckedChange={setChecked}
/>
<Label nativeID="terms" onPress={() => setChecked((value) => !value)}>
Accept terms and conditions
</Label>
</View>
)
}
export function CheckboxWithLabelExample() {
return (
<WithLabelDemo />
)
}import EsuissUI
import SwiftUI
struct CheckboxWithLabelDemo: View {
@State private var checked = false
var body: some View {
Toggle(isOn: $checked) {
FieldLabel("Accept terms and conditions")
}
.toggleStyle(.checkbox)
}
}import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Row
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.semantics.contentDescription
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.unit.dp
import com.esuiss.ui.components.Checkbox
import com.esuiss.ui.components.Label
fun Modifier.checkboxLabelToggle(onToggle: () -> Unit): Modifier =
clickable(interactionSource = null, indication = null, onClick = onToggle)
@Composable
fun CheckboxWithLabel() {
var checked by rememberSaveable { mutableStateOf(false) }
Row(horizontalArrangement = Arrangement.spacedBy(12.dp), verticalAlignment = Alignment.CenterVertically) {
Checkbox(checked, { checked = it }, Modifier.semantics { contentDescription = "Accept terms and conditions" })
Label("Accept terms and conditions", Modifier.checkboxLabelToggle { checked = !checked })
}
}With description
A label with a supporting description.


import * as React from "react"
import { View } from "react-native"
import { Checkbox } from "@/components/ui/checkbox"
import { Label } from "@/components/ui/label"
import { Text } from "@/components/ui/text"
function WithDescriptionDemo() {
const [checked, setChecked] = React.useState(true)
return (
<View className="flex-row items-start gap-3">
<Checkbox
accessibilityLabelledBy="notifications"
checked={checked}
onCheckedChange={setChecked}
/>
<View className="flex-1 gap-1.5">
<Label
nativeID="notifications"
onPress={() => setChecked((value) => !value)}
>
Enable notifications
</Label>
<Text className="text-sm text-label-secondary">
You can enable or disable notifications at any time.
</Text>
</View>
</View>
)
}
export function CheckboxWithDescriptionExample() {
return (
<WithDescriptionDemo />
)
}import EsuissUI
import SwiftUI
struct CheckboxWithDescriptionDemo: View {
@State private var checked = true
var body: some View {
HStack(alignment: .top, spacing: 12) {
Toggle(isOn: $checked) { EmptyView() }
.toggleStyle(.checkbox)
.accessibilityLabel(Text("Enable notifications"))
.padding(.top, 2)
VStack(alignment: .leading, spacing: 6) {
FieldLabel("Enable notifications")
.onTapGesture { checked.toggle() }
Text("You can enable or disable notifications at any time.")
.textStyle(.sm)
.foregroundStyle(Color.labelSecondary)
}
.frame(maxWidth: .infinity, alignment: .leading)
}
}
}import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.semantics.contentDescription
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.unit.dp
import com.esuiss.ui.components.Checkbox
import com.esuiss.ui.components.Label
import com.esuiss.ui.components.Text
import com.esuiss.ui.theme.EsuissTheme
import com.esuiss.ui.theme.Typography
fun Modifier.checkboxLabelToggle(onToggle: () -> Unit): Modifier =
clickable(interactionSource = null, indication = null, onClick = onToggle)
@Composable
fun CheckboxWithDescription() {
var checked by rememberSaveable { mutableStateOf(true) }
Row(horizontalArrangement = Arrangement.spacedBy(12.dp), verticalAlignment = Alignment.Top) {
Checkbox(checked, { checked = it }, Modifier.semantics { contentDescription = "Enable notifications" })
Column(Modifier.weight(1f), verticalArrangement = Arrangement.spacedBy(6.dp)) {
Label("Enable notifications", Modifier.checkboxLabelToggle { checked = !checked })
Text(
"You can enable or disable notifications at any time.",
style = Typography.sm.copy(color = EsuissTheme.colors.labelSecondary),
)
}
}
}Disabled
Disabled checkboxes in both states.


import { View } from "react-native"
import { Checkbox } from "@/components/ui/checkbox"
import { Label } from "@/components/ui/label"
export function CheckboxDisabledExample() {
return (
<View className="gap-4">
<View className="flex-row items-center gap-3">
<Checkbox disabled checked={false} onCheckedChange={() => {}} />
<Label disabled>Unchecked</Label>
</View>
<View className="flex-row items-center gap-3">
<Checkbox disabled checked onCheckedChange={() => {}} />
<Label disabled>Checked</Label>
</View>
</View>
)
}import EsuissUI
import SwiftUI
struct CheckboxDisabledExample: View {
var body: some View {
VStack(alignment: .leading, spacing: 16) {
Toggle(isOn: .constant(false)) { FieldLabel("Unchecked") }
Toggle(isOn: .constant(true)) { FieldLabel("Checked") }
}
.toggleStyle(.checkbox)
.disabled(true)
}
}import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.unit.dp
import com.esuiss.ui.components.Checkbox
import com.esuiss.ui.components.Label
@Composable
fun CheckboxDisabled() {
Column(verticalArrangement = Arrangement.spacedBy(16.dp)) {
Row(horizontalArrangement = Arrangement.spacedBy(12.dp), verticalAlignment = Alignment.CenterVertically) {
Checkbox(false, {}, enabled = false)
Label("Unchecked", enabled = false)
}
Row(horizontalArrangement = Arrangement.spacedBy(12.dp), verticalAlignment = Alignment.CenterVertically) {
Checkbox(true, {}, enabled = false)
Label("Checked", enabled = false)
}
}
}Indeterminate
A select-all checkbox in the indeterminate state.


import { View } from "react-native"
import { Checkbox } from "@/components/ui/checkbox"
import { Label } from "@/components/ui/label"
export function CheckboxIndeterminateExample() {
return (
<View className="flex-row items-center gap-3">
<Checkbox
indeterminate
checked={false}
onCheckedChange={() => {}}
accessibilityLabelledBy="select-all"
/>
<Label nativeID="select-all">Select all</Label>
</View>
)
}import EsuissUI
import SwiftUI
struct CheckboxIndeterminateExample: View {
var body: some View {
Toggle(sources: [Binding.constant(true), .constant(false)], isOn: \.self) {
FieldLabel("Select all")
}
.toggleStyle(.checkbox)
}
}import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Row
import androidx.compose.runtime.Composable
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.semantics.contentDescription
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.state.ToggleableState
import androidx.compose.ui.unit.dp
import com.esuiss.ui.components.Label
import com.esuiss.ui.components.TriStateCheckbox
fun Modifier.checkboxLabelToggle(onToggle: () -> Unit): Modifier =
clickable(interactionSource = null, indication = null, onClick = onToggle)
@Composable
fun CheckboxIndeterminate() {
Row(horizontalArrangement = Arrangement.spacedBy(12.dp), verticalAlignment = Alignment.CenterVertically) {
TriStateCheckbox(ToggleableState.Indeterminate, {}, Modifier.semantics { contentDescription = "Select all" })
Label("Select all")
}
}Invalid
A required checkbox with the invalid border.


import * as React from "react"
import { View } from "react-native"
import { Checkbox } from "@/components/ui/checkbox"
import { Label } from "@/components/ui/label"
function InvalidDemo() {
const [checked, setChecked] = React.useState(false)
return (
<View className="flex-row items-center gap-3">
<Checkbox
invalid={!checked}
accessibilityLabelledBy="terms-invalid"
checked={checked}
onCheckedChange={setChecked}
/>
<Label
nativeID="terms-invalid"
onPress={() => setChecked((value) => !value)}
>
Accept terms and conditions
</Label>
</View>
)
}
export function CheckboxInvalidExample() {
return (
<InvalidDemo />
)
}import EsuissUI
import SwiftUI
struct CheckboxInvalidDemo: View {
@State private var checked = false
var body: some View {
Toggle(isOn: $checked) {
FieldLabel("Accept terms and conditions")
}
.toggleStyle(.checkbox)
.invalid(!checked)
}
}import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Row
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.saveable.rememberSaveable
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.semantics.contentDescription
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.unit.dp
import com.esuiss.ui.components.Checkbox
import com.esuiss.ui.components.Label
fun Modifier.checkboxLabelToggle(onToggle: () -> Unit): Modifier =
clickable(interactionSource = null, indication = null, onClick = onToggle)
@Composable
fun CheckboxInvalid() {
var checked by rememberSaveable { mutableStateOf(false) }
Row(horizontalArrangement = Arrangement.spacedBy(12.dp), verticalAlignment = Alignment.CenterVertically) {
Checkbox(
checked,
{ checked = it },
Modifier.semantics { contentDescription = "Accept terms and conditions" },
invalid = !checked,
)
Label("Accept terms and conditions", Modifier.checkboxLabelToggle { checked = !checked })
}
}API Reference
Checkbox
React.ComponentProps<typeof CheckboxPrimitive.Root>- About
- Extra classes for the check icon.
- Type
string- Default
- —
- About
- Shows a danger-colored border.
- Type
boolean- Default
- —
Accessibility
- Has the
checkboxrole withchecked(ormixedwhen indeterminate) anddisabledstate. - Link it to a visible label with
accessibilityLabelledBy, or give it anaccessibilityLabel.
Notes
- Uses
bg-accentwhen checked andbg-surfacewith a translucent border when unchecked; in dark mode the unchecked box is filled instead of outlined. - Light and dark follow the system appearance.