ARIA 접근성 가이드

기본 개념

이름·역할·상태·값

보조기술은 UI 요소마다 이름(name)·역할(role)·상태(state)·값(value)을 읽어 사용자에게 전달합니다. 이 네 가지가 WCAG 4.1.2 “이름, 역할, 값”의 핵심입니다.

네 가지 핵심 정보

화면낭독기는 포커스가 간 요소에 대해 보통 “이름, 역할, 상태, 값” 순서로 안내합니다. 이 정보만 정확하면 사용자는 화면을 보지 않고도 요소가 무엇이고 어떻게 쓰는지 알 수 있습니다.

네 가지 핵심 정보
구성 요소뜻예정하는 방법
이름 (Name)요소를 부르는 말“저장”, “검색어”, “닫기”요소의 글자, <label>, alt, aria-label, aria-labelledby
역할 (Role)요소의 종류와 사용 방법버튼, 링크, 체크박스, 탭HTML 요소의 암묵적 역할, role 속성
상태 (State)지금의 상황. 자주 바뀝니다.선택됨, 펼쳐짐, 눌림, 사용 불가HTML 속성(checked, disabled), aria-checked, aria-expanded, aria-pressed
값 (Value)요소가 담은 내용·수치입력한 글자, 슬라이더 50%value, 입력 내용, aria-valuenow, aria-valuetext
네 가지 정보가 모두 전달되는 예
<label for="vol">음량</label>
<input id="vol" type="range" min="0" max="100" value="40">
<!-- 안내 예: "음량, 슬라이더, 40" -->

<button type="button" aria-pressed="true">굵게</button>
<!-- 안내 예: "굵게, 전환 버튼, 눌림" -->

여기서 “상태”는 넓게 보면 aria-required, aria-haspopup 같은 속성도 포함합니다. ARIA 명세는 둘을 구분하지만(역할·상태·속성 참고), 보조기술 사용자 입장에서는 모두 요소에 대한 추가 정보입니다.

이름 (Name)

접근 가능한 이름(accessible name)은 보조기술이 요소를 부를 때 쓰는 문자열입니다. 버튼·링크·입력 필드처럼 조작 가능한 요소에는 반드시 이름이 있어야 합니다. 이름이 없으면 화면낭독기는 “버튼”이라고만 읽어, 무엇을 하는 버튼인지 알 수 없습니다.

비권장이름 없는 아이콘 버튼
<button type="button">
  <svg viewBox="0 0 24 24"><path d="…"/></svg>
</button>
<!-- "버튼" -->
권장aria-label로 이름 지정
<button type="button" aria-label="닫기">
  <svg viewBox="0 0 24 24" aria-hidden="true"><path d="…"/></svg>
</button>
<!-- "닫기, 버튼" -->

이름은 정해진 우선순위에 따라 계산됩니다. 대략 aria-labelledby → aria-label → 네이티브 수단(<label>, alt, <caption> 등) → 콘텐츠(버튼·링크 안의 글자) → title 순입니다. 자세한 규칙은 접근 가능한 이름 계산 문서를 참고하세요.

좋은 이름의 조건

  • 짧고 구체적입니다. “여기를 클릭” 대신 “2025년 사업계획서 내려받기”.
  • 역할을 반복하지 않습니다. “닫기 버튼”이라고 쓰면 “닫기 버튼, 버튼”으로 읽힙니다.
  • 화면에 보이는 글자와 같거나, 보이는 글자로 시작합니다(음성 인식 사용자를 위해 — WCAG 2.5.3).

역할 (Role)

역할은 요소가 무엇이고 어떻게 조작하는지 알려 줍니다. “버튼”이라고 들으면 사용자는 Enter나 Space로 누를 수 있다고 기대하고, “링크”라고 들으면 다른 곳으로 이동한다고 기대합니다. “탭”이라고 들으면 화살표 키로 다른 탭으로 옮길 수 있다고 기대합니다.

대부분의 HTML 요소는 암묵적 역할을 가집니다. <button>은 button, <a href>는 link, <h2>는 heading입니다. 대응하는 HTML 요소가 없을 때만 role 속성으로 지정합니다.

비권장역할이 없는 클릭 요소
<span class="link" onclick="go()">더 보기</span>
<!-- "더 보기" (역할 없음, 포커스 불가) -->
권장알맞은 HTML 요소
<a href="/notice">공지사항 더 보기</a>
<!-- "공지사항 더 보기, 링크" -->

상태 (State)

상태는 사용자 조작이나 프로그램에 따라 바뀌는 요소의 현재 상황입니다. 상태가 바뀌면 브라우저가 이벤트를 보내 보조기술이 바로 알려 줍니다. 그래서 화면과 상태 값이 항상 같아야 합니다.

상태 (State)
상태HTML 대체 수단안내 예
aria-checked<input type="checkbox">의 checked선택됨 / 선택 안 됨
aria-expanded<details open>확장됨 / 축소됨
aria-pressed없음눌림 / 눌리지 않음
aria-selected<option selected>선택됨
aria-disableddisabled사용 불가
aria-invalid제약 검증(:invalid)과는 별개잘못됨 / 유효하지 않음
aria-current없음현재 페이지
화면과 상태를 함께 바꾸기
const btn = document.querySelector('#menu-btn');
btn.addEventListener('click', () => {
  const open = btn.getAttribute('aria-expanded') === 'true';
  btn.setAttribute('aria-expanded', String(!open));  // 상태 갱신
  menu.hidden = open;                                 // 화면 갱신
});

상태 동기화 방법은 상태 동기화 문서에서 자세히 다룹니다.

값 (Value)

값은 입력 필드에 들어 있는 글자나 범위 위젯의 현재 수치입니다. 네이티브 입력 요소는 값을 자동으로 전달하고, 직접 만든 슬라이더·스핀버튼·진행 막대는 aria-valuenow, aria-valuemin, aria-valuemax로 알립니다. 숫자만으로 의미가 부족하면 aria-valuetext로 사람이 읽기 좋은 문장을 줍니다.

직접 만든 슬라이더의 값
<div role="slider" tabindex="0" aria-label="화면 밝기"
     aria-valuemin="0" aria-valuemax="100" aria-valuenow="70"
     aria-valuetext="70%, 밝음"></div>
<!-- 안내 예: "화면 밝기, 슬라이더, 70%, 밝음" -->

직접 만들면 키보드도 직접 구현합니다

위 슬라이더는 화살표 키로 값을 바꾸는 스크립트가 있어야 완성됩니다. 가능하면 <input type="range">를 먼저 고려하세요. 키보드 동작은 슬라이더 패턴을 참고합니다.

WCAG 4.1.2 이름, 역할, 값

네 가지 정보는 WCAG 2.2 성공 기준 4.1.2 이름, 역할, 값(Name, Role, Value)(수준 A)의 요구 사항 그 자체입니다. 이 기준은 다음을 요구합니다.

모든 사용자 인터페이스 구성 요소(폼 요소, 링크, 스크립트로 생성한 구성 요소 등)에 대해, 이름과 역할을 프로그램이 알아낼 수 있어야 하고, 사용자가 설정할 수 있는 상태·속성·값을 프로그램이 설정할 수 있어야 하며, 이 항목들이 바뀌었다는 알림이 보조기술을 포함한 사용자 에이전트에 전달되어야 합니다.

즉, 단순히 처음에 올바른 값을 넣는 것만으로는 부족하고, 상태가 바뀔 때 접근성 트리도 함께 갱신되어야 합니다. 국내 KWCAG 2.2에서는 “웹 애플리케이션 접근성 준수” 항목이 같은 내용을 다룹니다.

WCAG 4.1.2 이름, 역할, 값
흔한 4.1.2 실패 사례빠진 정보
아이콘만 있는 버튼에 이름이 없음이름
<div onclick>로 만든 버튼역할(그리고 키보드 동작)
직접 만든 체크박스에 aria-checked가 없거나 갱신되지 않음상태, 변경 알림
아코디언 버튼의 aria-expanded가 항상 false상태 변경 알림
직접 만든 슬라이더에 aria-valuenow가 없음값
라벨 없는 <input>, 이름 없는 <iframe>이름

확인하는 방법

  1. 브라우저 개발자 도구의 접근성 패널에서 요소의 Name, Role, 상태 값을 확인합니다(접근성 트리 보기).
  2. 요소를 조작하면서 상태·값이 실제로 바뀌는지 확인합니다.
  3. 화면낭독기로 포커스를 이동해 이름·역할·상태가 모두 들리는지 확인합니다(화면낭독기로 테스트하기).

직접 해 보기

실습실에서 코드를 바꿔 가며 이름·역할·상태가 어떻게 계산되는지 확인할 수 있습니다.