이벤트 버블링 기법 : 리로드 되는 페이지에서 이벤트 리스너가 끊어지는 문제 해결 방법
상황
- HTML 페이지에 여러 개의 버튼을 달고 그 버튼에서 클릭 이벤트가 발생했을 때 이벤트 리스너를 동작시키기 위해 여러 개의 이벤트 리스너를 달았다.
- 특정 버튼의 기능에서 페이지를 초기화 하는 함수가 있어 페이지가 전부 리로드 된다.
- 페이지가 리로드 되면 각 버튼에 달려있던 이벤트 리스너의 연결이 끊어지면서 버튼을 클릭해도 반응이 없다.
해결
해당 버튼이 아닌 상위 요소에 이벤트리스너를 장착하여, 버튼이 리로드 되더라도 이벤트 리스너가 끊어지지 않도록 한다.
// 기존 코드
document.querySelector(".detail_heart_btn").addEventListener("click", clickHeart);
기존 코드가 있던 HTML의 태그 구성 요소를 보면 아래와 같다.
<button class="detail_heart_btn" id="${movieDetails.id}">
<img class="heartEmpty" src="assets/icon/heartEmpty.svg"></img>
<img class="heartRed" src="assets/icon/heartRed.svg"></img>
</button>
문제는 위 기존코드가 아니라 다른 버튼을 눌렀을 때 페이지가 리로드 되면서 detail_heart_btn에 달려 있던 이벤트 리스너가 끊어지면서 동작을 안 하는 것이 문제였는데, HTML을 보면 button 아래 하트 이미지가 자식요소로 포함이 돼 있음을 알 수 있다. 눈으로 보기엔 버튼으로 보여서 클릭하더라도 img 태그를 클릭한 것과 다를 게 없기 때문에 이벤트 리스너가 동작하지 않는다는 것.
따라서 개선된 코드는 이벤트 리스너를 상위 태그인 detail_main에 달아주었다. 위 태그에서 detail_main은 보이지 않지만, 리로드 되지 않는 영역에 있는 상위 태그이다.
// 개선된 코드
// 기존 코드에서는 언어전환 버튼을 눌러 언어 변경을 했을 때 페이지가 새로 로드되면서 찜하기 하트 버튼에 대한 이벤트 리스너가 새로 연결되지 않아 언어변경 이후 이벤트 리스너가 작동하지 않았음.
// 바꾼 코드는 언어 변경 버튼을 눌러 페이지가 로드될 때 계속 이벤트 리스너가 끊어지는 하트에 이벤트 리스너를 다는 것보다 버튼의 상위 요소인 .detail_main에 이벤트 리스너를 닮.
// 클릭된 요소가 detail_heart_btn(하트버튼)이 맞는지 확인함. closest까지 검사하는 이유는 버튼에 하트 이미지가 자식요소로 들어가 있어서 하트 안쪽을 클릭하면 버튼 클릭으로 인식이 안 되기 때문.
document.querySelector('.detail_main').addEventListener('click', function (event) {
if (event.target.classList.contains('detail_heart_btn') || event.target.closest('.detail_heart_btn')) {
clickHeart(event);
}
});
'Programing > JavaScript' 카테고리의 다른 글
HTML 요소에 단축키로 이벤트 주기 (input으로 포커스 옮기기, 버튼 클릭하기) (0) | 2024.05.11 |
---|---|
구글 스프레드시트를 API 호출하여 실시간으로 fetch하고 JSON으로 파싱하기 (0) | 2024.05.08 |
REST API 직접 JSON 파일로 만들기 (0) | 2024.04.29 |
[모던JS] 022. [기본] 기본 문법 요약 (0) | 2024.03.30 |
[모던JS] 021. [기본] 화살표 함수 기본 (0) | 2024.03.30 |
댓글