Switch
A switch allows users to turn an individual option on or off.
Features
Install
Install the component from your command line.
Anatomy
Import all parts and piece them together.
<script setup lang="ts">import * as switchs from '@destyler/switch'import { normalizeProps, useMachine } from '@destyler/vue'import { computed, useId } from 'vue'
const [state, send] = useMachine(switchs.machine({ id: useId(),}))
const api = computed(() => switchs.connect(state.value, send, normalizeProps),)</script>
<template> <label v-bind="api.getRootProps()"> <input v-bind="api.getHiddenInputProps()"> <span v-bind="api.getControlProps()" > <span v-bind="api.getThumbProps()" /> </span> </label></template>import { normalizeProps, useMachine } from '@destyler/react'import * as switchs from '@destyler/switch'import { useId } from 'react'
export default function Switch() { const [state, send] = useMachine(switchs.machine({ id: useId(), }))
const api = switchs.connect(state, send, normalizeProps)
return ( <label {...api.getRootProps()} > <input {...api.getHiddenInputProps()} /> <span {...api.getControlProps()} > <span {...api.getThumbProps()} /> </span> </label> )}<script lang="ts"> import * as switchs from '@destyler/switch' import { normalizeProps, useMachine } from '@destyler/svelte'
const id = $props.id()
const [state, send] = useMachine(switchs.machine({ id, }))
const api = $derived(switchs.connect(state, send, normalizeProps))</script>
<label {...api.getRootProps()}> <input {...api.getHiddenInputProps()}> <span {...api.getControlProps()} > <span {...api.getThumbProps()} ></span> </span></label>import { normalizeProps, useMachine } from '@destyler/solid'import * as switchs from '@destyler/switch'import { createMemo, createUniqueId } from 'solid-js'
export default function Switch() { const [state, send] = useMachine(switchs.machine({ id: createUniqueId(), }))
const api = createMemo(() => switchs.connect(state, send, normalizeProps))
return ( <label {...api().getRootProps()} > <input {...api().getHiddenInputProps()} /> <span {...api().getControlProps()} > <span {...api().getThumbProps()} /> </span> </label> )}Disabling the switch
To make a switch disabled, set the context’s disabled property to true
const [state, send] = useMachine( switch.machine({ disabled: true, }),)Making it checked by default
To make a switch checked by default without taking ownership of state, use defaultChecked. Prefer this over seeding with checked (which is presence-controlled after Phase 2).
const [state, send] = useMachine( switch.machine({ defaultChecked: true, }),)Controlled usage
To control the checked state from your app, pass checked into machine(...) and sync with onCheckedChange (plus the adapter context option). Use defaultChecked for uncontrolled demos instead of always passing checked. See Controllable State.
const checked = false // your reactive stateswitch.machine({ id: "1", checked, onCheckedChange(details) { // details => { checked: boolean } },})Listening for changes
When the switch value changes, the onCheckedChange callback is invoked.
const [state, send] = useMachine( switch.machine({ onCheckedChange(details) { // details => { checked: boolean } console.log("switch is:", details.checked ? "On" : "Off") }, }),)Usage within forms
To use switch within forms, use the exposed inputProps from the connect
function and ensure you pass name value to the destyler’s context. It will
render a hidden input and ensure the value changes get propagated to the
form correctly.
const [state, send] = useMachine( switch.machine({ name: "feature", }),)Styling guide
Earlier, we mentioned that each Switch part has a
data-partattribute added to them to select and style them in the DOM.
Focused State
When the switch input is focused, the data-focus attribute is added to the root, control and label parts.
[data-part="root"][data-focus] { /* styles for root focus state */}
[data-part="control"][data-focus] { /* styles for control focus state */}
[data-part="label"][data-focus] { /* styles for label focus state */}Disabled State
When the switch is disabled, the data-disabled attribute is added to the root, control and label parts.
[data-part="root"][data-disabled] { /* styles for root disabled state */}
[data-part="control"][data-disabled] { /* styles for control disabled state */}
[data-part="label"][data-disabled] { /* styles for label disabled state */}Invalid State
When the switch is invalid, the data-invalid attribute is added to the root, control and label parts.
[data-part="root"][data-invalid] { /* styles for root invalid state */}
[data-part="control"][data-invalid] { /* styles for control invalid state */}
[data-part="label"][data-invalid] { /* styles for label invalid state */}Methods and Properties
Machine Context
The switch machine exposes the following context properties:
Partial<{ root: string; hiddenInput: string; control: string; label: string; thumb: string; }>stringbooleanbooleanbooleanboolean(details: CheckedChangeDetails) => voidbooleanbooleanstringstringstring | number"ltr" | "rtl"string() => ShadowRoot | Node | DocumentMachine API
The switch api exposes the following methods:
booleanbooleanboolean(checked: boolean) => void() => voidData Attributes
Root
data-activedata-focusdata-focus-visibledata-readonlydata-hoverdata-disableddata-statedata-invalidLabel
data-activedata-focusdata-focus-visibledata-readonlydata-hoverdata-disableddata-statedata-invalidThumb
data-activedata-focusdata-focus-visibledata-readonlydata-hoverdata-disableddata-statedata-invalidControl
data-activedata-focusdata-focus-visibledata-readonlydata-hoverdata-disableddata-statedata-invalidAccessibility
Keyboard Interaction
Space Enter