[javascript] 이벤트 버블링과 캡처링

daewoong·2021년 10월 3일

이벤트 버블링

  • html
<div class="root">
  root
  <div class='parent'>
    parent
    <div class="child">
      child
    </div>
  </div>
</div>
  • css
.root {
  width: 300px;
  height: 300px;
  background-color: yellow;
}
.parent {
  width: 200px;
  height: 200px;
  background-color: red;
}

.child {
  width: 100px;
  height: 100px;
  background-color: blue;
}
  • javascript
window.addEventListener("click", function(e) {
	alert("window");
})
document.querySelector(".root").addEventListener("click", function(e) {
	alert("root");
})

document.querySelector(".parent").addEventListener("click", function(e) {
	alert("parent");
})

document.querySelector(".child").addEventListener("click", function(e) {
	alert("child");
})

위 코드를 실행시켜보면 child를 클릭 했을 때 child -> parent -> root -> window순으로 이벤트리스너가 동작하는 것을 볼 수 있다. 이처럼 하위 컴포넌트에서 발생한 이벤트가 상위 컴포넌트로 전파되는 것을 이벤트 버블링이라고 한다.

이벤트 캡처링

이벤트 캡처링은 버블링과 반대로 상위 컴포넌트부터 하위 컴포넌트로 전파되는 것이라고 한다.
그럼 이벤트 캡처링은 다음과 같은 형태로 사용한다고 한다.

el.addEventListener("click", function(e){}, true);

아직 잘 모르겠어서 child 컴포넌트에 캡처링을 사용해보았다.

window.addEventListener("click", function(e) {
	alert("window");
})
document.querySelector(".root").addEventListener("click", function(e) {
	alert("root");
})

document.querySelector(".parent").addEventListener("click", function(e) {
	alert("parent");
})

document.querySelector(".child").addEventListener("click", function(e) {
	alert("child");
}, true)

이전과 똑같이 child -> parent -> root -> window 순으로 리스너가 실행됐다. window -> root -> parent -> child 순으로 실행될거라는 예상과 달라 이것저것 해보며 다음과 같은 규칙을 찾을수 있었다.

  1. child 클릭
  2. window부터 child의 바로 상위컴포넌트까지 내려오며 캡처링을 사용한 리스너를 실행시킨다.
  3. child 컴포넌트의 리스너를 실행시킨다.
  4. child부터 window까지 올라가며 캡처링을 사용하지 않은 리스너를 실행시킨다.

예를 들어

window.addEventListener("click", function(e) {
	alert("window");
})
document.querySelector(".root").addEventListener("click", function(e) {
	alert("root");
}, true)

document.querySelector(".parent").addEventListener("click", function(e) {
	alert("parent");
})

document.querySelector(".child").addEventListener("click", function(e) {
	alert("child");
})

위와 같이 코드를 작성했다면 child를 클릭했을 때 root -> child -> parent - > window 순으로 리스너가 실행되는 것을 볼 수 있다. 또한

window.addEventListener("click", function(e) {
	alert("window");
})
document.querySelector(".root").addEventListener("click", function(e) {
	alert("root");
  	e.stopPropagation();
}, true)

document.querySelector(".parent").addEventListener("click", function(e) {
	alert("parent");
})

document.querySelector(".child").addEventListener("click", function(e) {
	alert("child");
})

위처럼 root에서 전파를 멈추면 child를 클릭해도 root 리스너만 실행되고 전파가 멈추는 것을 볼 수 있다.

마무리

이벤트 위임을 하며 버블링과 캡처링에 대해 듣게 되었고 궁금해서 공부를 해봤다.
버블링은 이벤트 위임을 할 때 잘 사용할 것 같지만 캡처링은 언제 쓰는지 잘 모르겠다.
개인적인 생각으로는 하위 컴포넌트에서 이벤트가 발생했을 때 상위컴포넌트에서 이 이벤트를 하위컴포넌트에서 발생시킬지 말지 결정할 때 사용할 수도 있을것 같다.
끝.

profile
잘하자

0개의 댓글