A switch input is a UI/UX component that provides a binary toggle control, similar to a physical on/off switch. It uses role="switch" with aria-checked to communicate the current state to assistive technologies. The component supports both click and keyboard (Space key) activation for accessibility compliance.
Switch inputs are commonly used for settings, preferences, and feature toggles where users need to enable or disable a single option without submitting a form. Unlike checkboxes, switches provide immediate effect and convey an on/off semantic rather than checked/unchecked.
<script lang="ts">
import SwitchButton from "./SwitchButton.svelte";
let enabled = $state(false);
</script>
<SwitchButton label="Enable notifications" bind:checked={enabled} />
<p>Notifications are {enabled ? "on" : "off"}</p>
Show Svelte source
// In your Svelte component:
import SwitchButton from "lily-design-system-svelte-headless/components/SwitchButton/SwitchButton.svelte";
<SwitchButton>SwitchButton</SwitchButton>
label: string (required) -- accessible name applied via aria-label
checked: boolean (default: false) -- whether the switch is on, bindable with two-way checked binding
disabled: boolean (default: false) -- whether the switch is disabled
...restProps: spread onto the <button> element
Keyboard Interactions
Space: toggles the switch between on and off states (custom handler with preventDefault)
Enter: activates the button (native button behavior)
ARIA
role="switch" -- identifies the element as a two-state toggle switch
aria-checked={checked} -- communicates whether the switch is currently on (true) or off (false)
aria-label={label} -- provides the accessible name for the switch control
When to Use
Use for binary settings that take immediate effect, such as enabling or disabling notifications.
Use for toggling features on and off, such as dark mode, Wi-Fi, or Bluetooth.
Use when the on/off semantic is more appropriate than a checked/unchecked semantic.
Use when a single control needs to toggle a preference without a separate save action.
Use in settings panels, preference screens, and feature flag dashboards.
When Not to Use
Do not use for form selections that require submission to take effect -- use CheckboxInput instead.
Do not use for choosing between two distinct options -- use RadioGroup instead.
Do not use when the control is part of a group of related options in a form -- use CheckboxGroup instead.
Do not use for toggling a button's pressed state in a toolbar -- use ToggleButton instead.
Headless
This headless component renders a <button> with role="switch" and aria-checked, providing proper switch semantics and keyboard activation (Space and Enter keys). The consumer provides all visual styling including the track, thumb, on/off indicators, and transition animations.
Styles
The consumer provides all CSS styling. The component renders with a .switch-button class for targeting. No default styles are included — this is a fully headless component.
Testing
Verify the component renders a <button> element with class switch-button
Verify role="switch"` -- identifies the element as a two-state toggle switch
Verify aria-label={label}` -- provides the accessible name for the switch control
Verify keyboard interactions work correctly
Verify pass-through attributes are applied
Advice
Designers: Make the on and off states visually distinct using color, position, and optionally text labels. Ensure the switch is large enough for touch targets (at least 44x44px).
Developers: Use the two-way bindable checked prop for reactive state. Remember that switches convey immediate effect -- do not use them for settings that require a separate save action.
Implementation Notes
Renders a <button type="button"> element with role="switch" for switch semantics
Supports two-way binding for the checked prop enabling two-way data binding with two-way checked binding
Click handler toggles checked when not disabled
Custom onkeydown handler processes the Space key to toggle state, with preventDefault() to avoid scrolling
The type="button" prevents accidental form submission
Supports rest props via ...restProps for extensibility (e.g., id, class)
Related components
toggle-button — a button that toggles between pressed and unpressed states
checkbox-input — a checkbox input for toggling a boolean value <input type="checkbox">