클릭 가능한 카드 패턴 및 안티패턴
발행: (2025년 12월 16일 오후 10:04 GMT+9)
4 min read
원문: Dev.to
Source: Dev.to
인터랙티브 요소 중첩 문제
- HTML 사양 – 하이퍼링크(
<a>에href가 있음)는 인터랙티브 콘텐츠입니다. HTML Living Standard에 따르면, 인터랙티브 요소는 다른 인터랙티브하거나 포커스 가능한 요소를 자손으로 포함해서는 안 되며, 이는<button>,<input>또는 또 다른<a>와 같은 요소를 하이퍼링크 안에 넣는 것을 금지합니다. - 보조 기술 문제 – 스크린 리더와 키보드 탐색 시 겹치는 클릭 영역을 가진 두 개의 다른 링크가 나타납니다. 탭 동작이 예측 불가능해지고, 스크린 리더가 읽어주는 링크 이름이 카드 전체 내용이 됩니다.
작성자: Jamil.
권장 접근법: Stretched Link 패턴
목표는 기본 링크(예: 카드 제목)를 보조 인터랙티브 요소와 분리하면서, CSS를 사용해 기본 링크의 클릭 영역을 카드 전체로 확장하는 것입니다. 내부 링크나 버튼은 스트레치된 링크 위에 배치되어 자체 인터랙션 우선순위를 유지합니다.
HTML 구조
<div class="card">
<a href="/article/123" class="card__main-link">
<h3>Article Title</h3>
</a>
<img src="thumbnail.jpg" alt="Article Thumbnail">
<p>Author: <a href="/authors/jamil">Jamil</a>.</p>
</div>
핵심 CSS 속성
| 요소 | 핵심 CSS 속성 | 기능 |
|---|---|---|
.card | position: relative; | 절대 위치 자식 요소를 위한 스태킹 컨텍스트를 설정합니다. |
.card__main-link::after | content: ''; position: absolute; inset: 0; z-index: 1; | 보이지 않는 링크를 카드 전체에 늘려 기본 클릭 대상 역할을 하게 합니다. |
내부 인터랙티브 요소(a, button) | position: relative; z-index: 2; | 이 요소들을 스트레치된 링크 위로 올려 기능과 포커스 순서를 유지합니다. |
CSS 구현
/* 1. 부모 요소 컨텍스트 */
.card {
position: relative;
/* 기타 스타일 (border, padding 등) */
}
/* 2. 스트레치된 클릭 영역 */
.card__main-link::after {
content: '';
position: absolute;
inset: 0; /* top: 0; right: 0; bottom: 0; left: 0; */
z-index: 1; /* 내부 인터랙티브 요소보다 낮음 */
pointer-events: auto; /* 영역이 클릭 가능하도록 함 */
}
/* 3. 내부 인터랙티브 요소 우선순위 */
.card p a,
.card button {
position: relative;
z-index: 2; /* 스트레치된 클릭 영역 위에 배치 */
}
Stretched Link 패턴을 사용하면 디자인 의도(카드를 전체 클릭 가능하게 만들기)와 기술적 준수(중첩 인터랙티브 요소 회피) 사이의 충돌을 해결할 수 있습니다. 올바른 HTML 의미론을 유지하고 스태킹 컨텍스트를 관리함으로써, 개발자와 디자이너는 예측 가능한 사용자 경험을 제공하는 견고하고 완전하게 접근 가능한 컴포넌트를 만들 수 있습니다.
Photo by gabby‑k