WCAG 준수 가이드
WCAG 2.1/2.2 AA 준수 가이드
내장 기능 — 별도 구현 불필요
이 페이지에서 설명하는 모든 접근성 기능은 Unveily SDK 네이티브 컴포넌트에 이미 구현되어 있습니다. 웹 개발자가 별도로 네이티브 코드를 작성할 필요가 없습니다. Android와 iOS 모두 동일하게 지원됩니다.
개요
Unveily SDK의 네이티브 UI 컴포넌트는 WCAG 2.1/2.2 AA 기준을 충족하도록 설계되었습니다. 접근성이 필요한 사용자(시각장애, 운동장애, 청각장애 등)도 앱을 동등하게 이용할 수 있습니다.
| 기준 | 항목 | 적용 컴포넌트 | Android | iOS |
|---|---|---|---|---|
| WCAG 1.1.1 | 텍스트가 아닌 콘텐츠 (스크린 리더 레이블) | 패널, 메뉴, 탭, 드로어 | ✓ | ✓ |
| WCAG 1.4.3 | 명도 대비 (4.5:1 이상) | 패널 배경, 메뉴 아이콘 | ✓ | ✓ |
| WCAG 1.4.4 | 텍스트 크기 조정 (200%까지) | 접근성 패널 설정 | ✓ | ✓ |
| WCAG 2.1.1 | 키보드 접근 | 모든 인터랙티브 요소 | ✓ | ✓ |
| WCAG 2.4.3 | 포커스 순서 | AccessibilityPanel, SideDrawer, TopDownMenu | ✓ | ✓ |
| WCAG 2.5.5 | 최소 터치 타겟 (48dp / 44pt) | 탭, 드로어 행, 메뉴 항목 | ✓ | ✓ |
| WCAG 2.5.8 | 최소 타겟 크기 (24dp, WCAG 2.2) | 뱃지, 아이콘 버튼 | ✓ | ✓ |
브릿지 준비 시점
이 페이지의 JavaScript 예제는 window.unveilyBridge(소문자)를 사용합니다. React·Vue 등 SPA의 마운트 시점에서 accessibilityPanel 같은 네임스페이스를 호출한다면 먼저 unveilyGlueReady 이벤트를 기다린 뒤 호출하세요. 버튼 클릭 등 사용자 동작으로 호출할 때는 필요 없습니다.
포커스 트랩 (WCAG 2.4.3)
패널·드로어·메뉴가 열릴 때 포커스가 내부에서만 순환합니다.
Android: Tab → 다음 요소, Shift+Tab → 이전 요소, 마지막 요소에서 Tab → 첫 요소로 돌아옵니다.
// Tab / Shift+Tab 순환 — SDK가 자동으로 처리합니다
setOnKeyListener { _, keyCode, event ->
if (keyCode == KeyEvent.KEYCODE_TAB && event.action == KeyEvent.ACTION_DOWN) {
val focusables = getFocusableChildren()
val nextIndex = if (event.isShiftPressed)
(currentIndex - 1 + focusables.size) % focusables.size
else
(currentIndex + 1) % focusables.size
focusables[nextIndex].requestFocus()
true
} else false
}iOS: 패널이 열릴 때 UIAccessibility.post(notification: .screenChanged, argument: containerView)를 호출하여 VoiceOver가 패널 내부로 즉시 포커스를 이동합니다.
// 패널 표시 시 VoiceOver 자동 알림 — SDK가 자동으로 처리합니다
UIAccessibility.post(notification: .screenChanged, argument: containerView)스크린 리더 레이블 (WCAG 1.1.1)
모든 UI 요소에 스크린 리더(Android TalkBack / iOS VoiceOver)가 읽을 수 있는 레이블이 자동 설정됩니다.
메뉴 항목 — 비활성 상태 안내
// 활성 항목: "카메라"
// 비활성 항목: "카메라, 비활성화됨" — 색상만으로 구분하지 않음
itemView.contentDescription = if (enabled) label
else "$label, ${getString(R.string.acc_state_disabled)}"// NSLocalizedString으로 자동 적용
button.accessibilityLabel = NSLocalizedString("acc_state_disabled", comment: "")
button.accessibilityTraits = enabled ? .button : [.button, .notEnabled]뱃지 알림 수 안내
// TalkBack: "알림 3건"
badge.contentDescription = getString(R.string.acc_badge_count, count)// VoiceOver: "3 notifications"
badge.accessibilityLabel = String(format: NSLocalizedString("acc_badge_count", comment: ""), count)텍스트 크기 조정 (WCAG 1.4.4)
접근성 패널에서 사용자가 글자 크기를 설정하면 WebView의 텍스트 크기도 함께 조정됩니다.
접근성 패널은 normal / large / extraLarge 3단계를 제공합니다. WCAG 1.4.4는 200%까지 확대해도 콘텐츠를 이용할 수 있어야 한다고 규정하며, WebView는 이 패널 설정에 더해 사용자의 시스템 글자 크기 설정도 반영하므로 200% 확대에서도 콘텐츠를 이용할 수 있습니다.
| 설정 | WebView textZoom |
|---|---|
| 기본 (Normal) | 100% |
| 크게 (Large) | 130% |
| 매우 크게 (Extra Large) | 160% |
JavaScript에서 현재 설정을 읽을 수 있습니다. getSettings는 콜백 함수명을 문자열로 받으며, 동기 반환 형태는 없습니다:
window.unveilyBridge.accessibilityPanel.getSettings("onAccessibilitySettingsLoaded");
window.onAccessibilitySettingsLoaded = function (settings) {
console.log(settings.fontSize); // "normal" | "large" | "extraLarge"
};최소 터치 타겟 (WCAG 2.5.5 / 2.5.8)
모든 인터랙티브 요소는 최소 터치 크기를 보장합니다. iOS는 44pt, Android는 48dp 기준을 적용합니다 (물리적 크기 동등).
| 컴포넌트 | Android | iOS |
|---|---|---|
| 접근성 패널 항목 | 48dp × 72dp | 44pt × 66pt |
| 하단 탭 | 48dp × 48dp | 44pt × 44pt |
| 드로어 행 | 48dp × 56dp | 44pt × 52pt |
| 뱃지 | 24dp × 24dp (WCAG 2.2) | 24pt × 24pt (WCAG 2.2) |
고대비 모드 (WCAG 1.4.3)
접근성 패널에서 고대비 모드를 활성화하면 배경 스타일이 동적으로 변경됩니다.
iOS: 배경색 systemBackground → black, 텍스트색 label → white로 전환하여 4.5:1 명도 대비를 보장합니다.
Android: 패널 배경 불투명도를 높이고 블러 효과를 제거합니다.
window.unveilyBridge.accessibilityPanel.getSettings("onAccessibilitySettingsLoaded");
window.onAccessibilitySettingsLoaded = function (settings) {
if (settings.highContrast) {
// Recommended: also apply a high-contrast style to web content
document.body.classList.add("high-contrast");
}
};다국어 접근성 문자열
TalkBack/VoiceOver 레이블이 앱 언어에 맞춰 자동으로 변경됩니다. SDK는 한국어(ko), 영어(en), 일본어(ja) 3개 언어를 지원합니다.
| 문자열 키 | 한국어 | English | 日本語 |
|---|---|---|---|
acc_high_contrast | 고대비 | High Contrast | ハイコントラスト |
acc_font_size | 글꼴 크기 | Font Size | 文字サイズ |
acc_tts | 읽어주기 | Read Aloud | 読み上げ |
acc_easy_read | 쉬운 읽기 | Easy Read | かんたん表示 |
acc_haptic | 진동 피드백 | Vibration | 振動フィードバック |
acc_tab_pin | 탭 바 고정 | Pin Tab Bar | タブ固定 |
acc_left_handed | 왼손 모드 | Left-Hand Mode | 左利きモード |
acc_one_handed | 한손 모드 | One-Hand Mode | 片手モード |
acc_state_disabled | 비활성화됨 | Disabled | 無効 |
acc_state_selected | 선택됨 | Selected | 選択済み |
acc_badge_count | 알림 %ld건 | %ld notifications | %ld件の通知 |
TTS 음성 언어는 별개
위 표는 UI(스크린 리더 레이블) 언어입니다. TTS 음성 합성은 이와 별개로 zh-CN(중국어 간체)도 지원합니다 — UI 언어가 아니라 음성 출력용입니다.
운동장애 지원
왼손잡이 모드
드로어 위치를 화면 오른쪽 → 왼쪽으로 전환합니다.
window.unveilyBridge.accessibilityPanel.open();패널 내 "왼손 모드" 토글로 설정합니다.
한손 모드
화면 하단 영역으로 콘텐츠를 압축하여 한 손으로 조작 가능하게 합니다.
탭 바 고정
자동 숨김 탭 바를 항상 표시 상태로 고정합니다.
window.unveilyBridge.accessibilityPanel.open();패널 내 "탭 바 고정" 토글로 설정합니다.
쉬운 읽기
레이아웃을 단순화하여 인지 장애가 있는 사용자도 쉽게 이용할 수 있도록 합니다.
웹 콘텐츠 접근성
WebView 내 웹 콘텐츠의 접근성은 웹 개발자가 담당합니다.
aria-* 속성, 시맨틱 HTML, 포커스 관리 등 표준 웹 접근성 기법을 적용하세요.
TTS Bridge 활용
웹 콘텐츠에서 직접 TTS를 호출하면 Android TalkBack / iOS VoiceOver 없이도 읽어주기 기능을 구현할 수 있습니다. 자세한 내용은 접근성 Bridge API를 참고하세요.