Playground로 바로 이동
Components

Switch

독립적인 설정이나 기능을 즉시 켜고 끄는 컴포넌트입니다. 24px Control이 기본값입니다.

명세 문서 보기

🚩 Playground

On/Off, Disabled, Size와 Label 위치를 조합하고 실제 전환 동작을 확인합니다.

Appearance

Size
Label position

State

Disabled

Content

On

Anatomy

Switch Control과 Label을 구성하는 실제 요소입니다.

  1. 1.Track
  2. 2.Thumb
  3. 3.Label

Structure map

Field
├─ Track
│  └─ Thumb
└─ Label

Properties · Size

Switch Control 전체 높이를 기준으로 16, 24, 32 세 크기를 제공합니다. 24px이 기본값이며 실제 조작 영역은 Control보다 크게 확보할 수 있습니다.

Small · Control 26×16px · Thumb 12px

Medium · Control 38×24px · Thumb 20px · Default

Large · Control 52×32px · Thumb 26px

Properties · Label position

별도 Block Layout 없이 Label을 Switch Control의 오른쪽 또는 왼쪽에 배치합니다. 오른쪽이 기본값입니다.

Label right · Default

Label left

Properties · State

On/Off 값은 고정하고 Focus와 Pressed 피드백은 실제로 확인합니다.

Off

On

Focus visible

Disabled · Off

Disabled · On

Behavior

Switch는 값을 선택해 나중에 제출하는 요소가 아니라 설정을 즉시 전환합니다.

Immediate change

누르면 On/Off 값이 즉시 변경되고 연결된 설정이나 기능에 바로 반영됩니다.

Keyboard

Focus 상태에서 Space를 누르면 On/Off가 전환됩니다.

Disabled

현재 On/Off 값은 유지하지만 사용자가 변경할 수 없습니다.

Boundary

선택 결과를 모아 저장하거나 제출해야 한다면 Checkbox를 사용합니다.

Guidelines

현재 확정한 Switch의 타깃 영역과 사용 범위입니다.

Target area 확보하기

16px Control

Row composition

  • 16px Control도 최소 24px 높이의 Target area를 확보합니다.
  • Switch Control과 Label을 포함한 전체 영역이 Target으로 동작합니다.
  • List처럼 다른 요소와 결합하면 전체 Row를 Target으로 사용합니다.

상태를 즉시 활성화할 때만 사용하기

Don’t

즉각적인 결과가 없는 상황에서는 Switch를 사용하지 마세요.

Do

즉각적인 결과가 나타나지 않는 경우 Checkbox를 사용합니다.

  • Switch는 토글 시 즉각적인 결과가 나타나야 합니다. 마지막 버튼을 누를 때까지 결과가 나타나지 않는 경우 Checkbox를 사용합니다.

독립적인 기능에서만 사용하기

Do

각 Switch가 서로 영향을 주지 않는 독립적인 설정에 사용하세요.

Don’t

하나의 Switch로 다른 Switch의 상태를 함께 바꾸지 마세요.

  • Switch는 각각 독립적으로 On/Off되는 기능을 제어합니다.
  • 전체 선택과 하위 선택처럼 부모–자식 관계가 필요하면 Checkbox 구조를 사용합니다.

Disabled 상태는 명확하게 표현하기

알림 받기

Do

Switch와 Label을 함께 Disabled 상태로 표현하세요.

Don’t

Switch Control만 Disabled 색상으로 바꾸지 마세요.

  • Switch를 사용할 수 없다면 Label도 disabled foreground를 사용합니다.
  • Control과 Label의 상태를 일치시켜 항목 전체를 조작할 수 없다는 점을 명확히 전달합니다.

Property map

현재 구현된 Base UI Switch 속성과 ooee가 확정한 Field 범위입니다.

PropertyValuesDefault
controlSizesmall (16) | medium (24) | large (32)medium (24)
checkedfalse | truefalse
defaultCheckedfalse | truefalse
disabledfalse | truefalse
readOnlyfalse | truefalse
requiredfalse | truefalse
labelReactNode (SwitchField)required
labelPositionleft | rightright
name / value / formstringundefined
onCheckedChange(checked: boolean) => voidundefined

명세 문서

docs/system/components/switch.md

Switch

packages/ui/src/switch.tsx

설정이나 기능을 즉시 켜고 끄는 Boolean control이다. 동작은 Base UI Switch를 기반으로 하며 시각 상태는 oe semantic token을 사용한다.

역할과 경계

  • Switch는 누르는 즉시 연결된 설정이나 기능의 On/Off 값을 변경한다.
  • 여러 선택 결과를 모아 나중에 저장하거나 제출하는 항목에는 Checkbox를 사용한다.
  • 원자적인 Switch와 Label을 결합하는 SwitchField를 제공한다.
  • 별도 SwitchContainer는 제공하지 않는다.

Anatomy

  1. Track
  2. Thumb
  3. Label: SwitchField에서 필수

SwitchField는 Control과 Label만 결합한다. Description과 Leading/Trailing element는 제공하지 않는다.

Properties

Size

  • small: Control 26×16px, Thumb 12px. SwitchField의 최소 target 높이는 24px다.
  • medium: Control 38×24px, Thumb 20px. 기본값이다.
  • large: Control 52×32px, Thumb 26px.
  • React Property 이름은 공용 control 문법에 맞춰 controlSize를 사용한다.
  • Size의 16px, 24px, 32px는 Track만의 높이가 아니라 Switch Control 전체 높이다. Small은 시각 크기보다 큰 24px target을 확보하고, Medium과 Large는 Control 높이 자체가 충분하므로 별도로 넓히지 않는다.
  • SwitchField는 크기가 커질수록 Label 크기와 Control–Label gap도 함께 키운다.

Label position

  • right: Label을 Control 오른쪽에 둔다. 기본값이다.
  • left: Label을 Control 왼쪽에 둔다.
  • 별도 Inline/Block Layout은 제공하지 않는다.

Elements

  • label: SwitchField의 필수 ReactNode
  • labelPosition: left | right, 기본값 right
  • switchClassName, thumbClassName: Control과 Thumb에 각각 적용하는 class다

State

  • Off: 조작 가능한 상태가 Disabled보다 선명하게 보이도록 oe-background-control-off를 Track과 inset Border에 함께 사용한다.
  • On: oe-brand-background-bold-primary Track과 흰색 Thumb을 사용한다. Radio·Checkbox의 켜진 상태와 같은 값이며, 근거는 interaction.md의 「선택 상태와 Hover·Pressed」다. 브랜드와 분리된 oe-info-*를 쓰던 때에는 두 값이 모두 파래서 차이가 드러나지 않았으나, 브랜드 색을 갈아 끼우면 Switch만 남는다.
  • Focus visible: 기본 inset Border는 유지하고 바깥에 oe-focus-ring 2px Outline과 2px offset을 사용한다.
  • Disabled · Off: Border 없이 oe-background-control-disabled Track과 더 선명한 oe-background-disabled-selected Thumb, disabled text를 사용한다.
  • Disabled · On: Disabled · Off와 같은 Track·Thumb 색상을 사용하고 Thumb 위치만 On으로 이동한다.

Behavior

  • Pointer로 누르거나 Focus 상태에서 Space를 누르면 On/Off가 전환된다.
  • Disabled는 현재 On/Off 값을 유지하지만 변경할 수 없다.
  • checked, defaultChecked, onCheckedChange로 controlled 또는 uncontrolled 상태를 지원한다.
  • On/Off 전환에서는 Thumb 위치와 Track 색상이 함께 부드럽게 바뀐다. Disabled 전환에서는 현재 Thumb 위치를 유지하고 Track과 Thumb 색상만 전환한다.
  • readOnly, required, name, value, uncheckedValue, form은 Base UI의 Form 연결 범위에서 전달한다.
  • SwitchField는 표시 Label과 Control을 aria-labelledby로 직접 연결한다. 원자적인 Switch는 소비자가 aria-label 또는 aria-labelledby를 제공한다.

Guidelines

Target area 확보하기

  • Switch Control과 Label을 포함한 전체 영역이 Target으로 동작한다.
  • 16px Control은 최소 24px 높이의 Target area를 확보한다.
  • List처럼 다른 요소와 결합해 사용하면 전체 Row가 Target이 된다.

상태를 즉시 활성화할 때만 사용하기

  • Switch는 토글한 직후 연결된 설정이나 기능의 결과가 나타나는 경우에만 사용한다.
  • 취소·확인·가입하기처럼 마지막 버튼을 누를 때까지 결과가 나타나지 않는 경우에는 Switch를 사용하지 않고 Checkbox를 사용한다.

독립적인 기능에서만 사용하기

  • 각 Switch는 다른 Switch에 영향을 주지 않고 독립적으로 작동해야 한다.
  • 전체 선택과 하위 선택처럼 부모–자식 관계가 필요하면 Switch 대신 Checkbox 구조를 사용한다.

Disabled 상태는 명확하게 표현하기

  • Switch를 사용할 수 없다면 Control뿐 아니라 Label도 disabled foreground로 표현한다.
  • Control과 Label의 상태를 일치시켜 항목 전체를 조작할 수 없다는 점을 명확히 전달한다.

현재 정의하지 않은 항목

  • 별도 Container variant
  • Label 없이 원자적인 Switch만 사용할 때의 제품별 accessible label 정책
  • Loading 또는 Error 상태

Verification

  • Pointer와 Label 전체 영역 클릭
  • Focus 상태의 Space 전환
  • Disabled 값 유지와 상호작용 차단
  • 기본 Medium과 Small/Medium/Large Control·Thumb 크기