JSP 프로젝트로 마켓컬리 클론코딩을 진행하던 중 헤더 드롭다운메뉴를 구현하면서 생긴 문제를 해결했던 내용을 기록하기위해서 쓰는 글이다. 사실 헤더부분은 내 역할이 아니였는데, 팀원이 헤더부분 골격은 잡았지만 세부적인 부분 구현에 어려움이 있어보여 내가 하겠다고했다.
마켓컬리에서는 드롭다운메뉴를 js를 통해서 구현하는 것으로 보인다. 드롭다운메뉴 영역의 display를 none으로 해서 숨겨놨다가 영역안에 마우스가 진입하면 display를 block으로 해서 드롭다운메뉴가 보이도록 처리하는 메커니즘인 것 같다.
사실 구현하는데 있어서 큰 문제는 없었다. 사용자의 마우스가 전체카테고리 영역으로 올 경우에 드롭다운 메뉴의 display: block으로 설정, 벗어날 때는 display: none 해서 보여주기만하면 되는 간단한 로직이지만 막상 구현해보니 매끄럽게 되지가 않았다.
전체카테고리 영역에 마우스를 올리면 드롭다운메뉴가 나타나게되는데, 영역 안에있는 텍스트로 마우스가 이동하면 mouseleave 이벤트가 실행되서 드롭다운메뉴가 사라지게되는 문제였다. 자식태그에도 당연히 이벤트가 적용되는 줄 알았는데 처리가 안되니 난감했다. 그렇다고 자식태그까지 싹다 mouseenter 이벤트를 넣는 것은 효율적인 코드작성이 될 것 같지 않았다.
자식태그에서 이벤트가 발생하면 부모태그에서도 이벤트를 감지하는 버블링만 알고 있었는데, 반대개념인 캡처링을 사용해야하는 경우도 생긴다는 점을 이번 문제해결을 통해 알게되었다.
전체카테고리 영역의 구조를 보면 li태그안에 자식태그로 a태그, span태그가 있다. 이 중에 li태그에 mouseenter와 mouseleave 이벤트를 넣었다. 영역 안으로 마우스를 넣으면 드롭다운 메뉴가 나오지만 span 태그 영역에 접근하면 드롭다운메뉴가 사라지게되는 이상한 상황이 발생했다.
열심히 공식문서를 뒤지는 중에 mouseover라는 이벤트를 발견했다. mouseenter와의 차이점은 부모태그에 mouseover 이벤트를 넣으면 자식태그에 이벤트를 지정하지 않았더라도 자동으로 자식태그도 해당 이벤트가 실행된다는 것이다. mouseenter는 무조건 자기자신만 이벤트가 작동되도록 되어있다. 반대 이벤트는 mouseout을 사용하면 된다.
mouseover 이벤트를 적용하니 span영역으로 이동해도 드롭다운메뉴가 나타나는게 유지되었다.
잘 안되는 부분이 나올 때는 공식문서를 찾아보는 것이 가장 큰 도움이 되는 것 같다.
또한 이벤트를 넣었을 때 부모태그와 자식태그의 이벤트처리여부 까지 고려해서 코드를 작성해야된다는 점을 상기시켜주었다.
댓글