이벤트 전파(Event Propagation)는 브라우저가 DOM 요소에서 발생한 이벤트를 부모 요소로 전달하는 방식을 의미합니다.
이벤트 전파는 두 가지 단계로 이루어집니다.
이벤트가 가장 깊은 요소에서 시작하여 부모 요소로 전파되는 방식
자식 요소
를 클릭하면, 해당 이벤트가 부모 요소로 전파됨e.stopPropagation()
을 호출하면 버블링을 중단할 수 있음tsx
복사편집
<div onClick={() => console.log("부모 요소 클릭됨!")}>
<button onClick={() => console.log("자식 요소 클릭됨!")}>
클릭하세요
</button>
</div>
✔ 클릭하면 출력 결과:
복사편집
자식 요소 클릭됨!
부모 요소 클릭됨!
→ 버블링
때문에 자식 요소 클릭 후 부모 요소도 클릭된 것으로 감지됨
자식 요소에서 e.stopPropagation()
을 호출하면 이벤트가 부모로 전달되지 않음.
tsx
복사편집
<div onClick={() => console.log("부모 요소 클릭됨!")}>
<button onClick={(e) => {
e.stopPropagation();
console.log("자식 요소 클릭됨!");
}}>
클릭하세요
</button>
</div>
✔ 클릭하면 출력 결과:
복사편집
자식 요소 클릭됨!
→ 부모 요소는 실행되지 않음 (e.stopPropagation()
으로 차단했기 때문)
이벤트가 최상위 부모 요소에서 시작하여 자식 요소로 내려오는 방식(일반적인 버블링과는 반대 방향)
버블링
과 반대 방향으로 이벤트가 전파됨addEventListener
의 capture: true
옵션을 사용하면 버블링이 아니라 캡처링 방식으로 이벤트를 감지할 수 있음tsx
복사편집
<div onClick={() => console.log("부모 요소 클릭됨!")}>
<button onClick={() => console.log("자식 요소 클릭됨!")}>
클릭하세요
</button>
</div>
✔ 기본적으로 실행 순서 (버블링):
복사편집
자식 요소 클릭됨!
부모 요소 클릭됨!
하지만, 캡처링 모드로 실행하면?
tsx
복사편집
document.getElementById("parent")?.addEventListener("click", () => {
console.log("부모 요소 클릭됨! (캡처링)");
}, true);
document.getElementById("child")?.addEventListener("click", () => {
console.log("자식 요소 클릭됨! (캡처링)");
}, true);
✔ 실행 순서 (캡처링 활성화):
scss
복사편집
부모 요소 클릭됨! (캡처링)
자식 요소 클릭됨! (캡처링)
→ 캡처링 모드에서는 부모 이벤트가 먼저 실행된 후, 자식 이벤트가 실행됨
구분 | 버블링(Bubbling) | 캡처링(Capturing) |
---|---|---|
방향 | 자식 → 부모로 이벤트 전달 | 부모 → 자식으로 이벤트 전달 |
기본 동작 | 기본적으로 활성화됨 | 기본적으로 비활성화됨 |
설정 방법 | 기본적으로 모든 이벤트가 버블링됨 | addEventListener 의 capture: true 옵션 필요 |
사용 목적 | 부모 요소에서 자식 요소의 이벤트를 감지할 때 | 부모 요소에서 특정 자식 요소의 이벤트를 제어할 때 |
✅ 버블링 활용:
onClick
을 부모 요소에 걸어 놓고, 자식 요소의 클릭 이벤트를 감지document.addEventListener("click", handleClick)
✅ 캡처링 활용:
document.addEventListener("click", handleClick, true)
✅ 버블링을 막아야 하는 경우:
e.stopPropagation()
)1️⃣ 버블링은 기본 동작이므로, 부모 요소에서 이벤트를 감지하려면 onClick
을 부모에 설정하면 됨
2️⃣ 버블링을 막고 싶다면 e.stopPropagation()
을 사용
3️⃣ 캡처링을 활성화하려면 addEventListener("click", handleClick, true)
처럼 capture: true
옵션을 사용
4️⃣ 특정 부모에서 먼저 이벤트를 감지하고 싶을 때만 캡처링을 활용
🚀 즉, 버블링이 기본적으로 동작하지만, 상황에 따라 e.stopPropagation()
으로 차단하거나,부모에서 먼저 감지하고 싶을 때 capture: true
를 사용하면 된다! 🚀