캡처링과 버블링, 이벤트 흐름이란?

Taehee Kim·2022년 8월 9일
0

기술 면접 스터디

목록 보기
4/8
post-thumbnail

❓ 이벤트 흐름

우리가 자바스크립트에서 동적으로 웹을 만들기 위해서 가장 많이 사용하는 addEventListener 메소드를 사용했을때, 이벤트가 작용하는 대상을 찾아가는 과정
이벤트 흐름에는 두 가지 흐름이 있는데 그게 바로 캡처링과 버블링 단계임


📷 캡처링 단계 (상위 > 하위)

  • window 객체 > document > body > ... > 타겟
  • 상위 요소에서 이벤트가 발생하는 타겟까지 가는 동안 만나는 요소들이 이벤트가 발생함
  • 이벤트 매소드 사용시, true를 사용해야 발생하는 흐름 (기본은 버블링)
window.addEventListener('click', () => {
            console.log("window capture!");
        }, true);

🛁 버블링 단계 (하위 > 상위)

  • 타겟 > ... > body > document > window
  • 타겟에서 상위 요소로 가는 동안 만나는 요소들의 이벤트를 발생시킴
  • default 값(false)
window.addEventListener('click', () => {
            console.log("window bubble!");
        }, false); // false는 생략 가능

event.stopPropagation()

  • 버블링 이벤트 흐름을 막아줌
  • 언제 사용? 내가 원하는 이벤트 타겟만을 정확하게 집어서 사용할 때!! 즉, 불필요하게 상위요소에도 이벤트가 작동하지 않도록 할 때 아주 유용하게 사용할 수 있다.

여기서 잠깐! event.preventDefault()와 혼돈 X 개념 꽉 잡자
event.preventDefault()는 태그 요소가 작동하는 기본 이벤트 자체를 아예 중지하는 역할이다.

예를 들면, a태그를 사용하면 해당 주소 페이지로 렌더링해줘야 하지만, event.preventDefault()를 사용하면 페이지가 넘어가지 않는다.

✔ target, currentTarget, this

  • target: 이벤트 발생의 원인 요소
  • currentTarget: target 이벤트 발생에 의해 참조되는 요소
  • this: 이벤트가 연결된 노드 참조, currentTarget과 비슷

* 버튼을 누르면 target은 버튼, currenTarget/ this는 article을 참조

<body>
    <article class="parent">
      <button type="button">버튼임</button>
    </article>

    <script>
      const parent = document.querySelector(".parent");
      parent.addEventListener("click", function (event) {
        console.log(event.target, "target"); // <button>
        console.log(event.currentTarget, "currnetTarget"); // <article>
        console.log(this, "this"); // <article>
      });
    </script>
  </body>

✨ 이벤트 위임

부모 요소에 이벤트를 '한 번만' 걸어서, 하위 요소들 전체에 이벤트를 발생시킬 수 있는 방법

<body>
    <article class="parent">
      <button type="button">버튼 1</button>
      <button type="button">버튼 2</button>
    </article>
  
  <script>
    const $parent = document.querySelector('.parent');
    $parent.addEventListener('click',() => {
    	if(event.target.nodeName === "BUTTON") {
        	event.target.innerHTML = "hello world"
        }
    })
  </script>
</body>

article에 이벤트를 주었지만 두 버튼 모두 이벤트 발생

0개의 댓글