$(function () { /* ================================================== Global Variables ================================================== */ let hoverTimer; // PC GNB hover 딜레이 타이머 const HEADER_SCROLL_OFFSET = 50; // 스크롤 시 header 활성 기준 const BREAK_POINT = 1280; // PC / Mobile 분기 기준 const $header = $(".header"); const $pcGnb = $("nav:not(.mobile_nav) .gnb > li"); const $mobileNav = $(".mobile_nav"); const $btnSitemap = $(".btn_sitemap"); const $pcSitemap = $(".sitemap"); /* ================================================== PC GNB (Hover / Focus) - 메뉴 hover 시 header 드롭다운 활성 - header 영역 벗어났을 때만 닫힘 ================================================== */ $pcGnb.on("mouseenter focusin", function () { const $target = $(this); clearTimeout(hoverTimer); hoverTimer = setTimeout(function () { $pcGnb.removeClass("active"); $target.addClass("active"); $header.addClass("active"); }, 120); // hover 딜레이로 자연스러운 UX }); // header 영역을 완전히 벗어났을 때만 전체 닫기 $header.on("mouseleave", function () { $pcGnb.removeClass("active"); // 스크롤을 내리지 않았을 때만 scrolled 제거 if ($(window).scrollTop() <= HEADER_SCROLL_OFFSET) { $header.removeClass("active"); } }); /* ================================================== Header Scroll - 스크롤 위치에 따라 header 상태 제어 ================================================== */ $(window).on("scroll", function () { const y = $(this).scrollTop(); $header.toggleClass("scrolled", y > HEADER_SCROLL_OFFSET && y !== 0); }); /* ================================================== Mobile Navigation (Accordion) - 1depth 클릭 시 해당 메뉴만 열림 ================================================== */ // 초기 상태: 모든 2depth 닫힘 $mobileNav.find(".depth02_ul").hide(); $mobileNav.on("click", ".depth01", function () { const $li = $(this).closest("li"); const $depth02 = $li.find(".depth02_ul"); const $icon = $(this).find(".icon.arrow"); // 다른 메뉴 닫기 $li.siblings().removeClass("active").find(".depth02_ul").stop(true, true).slideUp(300); $li.siblings().find(".icon.arrow").removeClass("top").addClass("bottom"); // 현재 메뉴 토글 if ($li.hasClass("active")) { $li.removeClass("active"); $depth02.stop(true, true).slideUp(300); $icon.removeClass("top").addClass("bottom"); } else { $li.addClass("active"); $depth02.stop(true, true).slideDown(300); $icon.removeClass("bottom").addClass("top"); } }); /* ================================================== Sitemap / Mobile Nav Open & Close - 해상도에 따라 동작 분기 ================================================== */ $btnSitemap.on("click", function () { const isMobile = $(window).width() < BREAK_POINT; if (isMobile) { openMobileNav(); } else { togglePcSitemap(); } }); // 모바일 메뉴 닫기 $mobileNav.find(".btn_close").on("click", function () { $btnSitemap.removeClass("active"); $mobileNav.removeClass("active"); }); // PC sitemap 닫기 $pcSitemap.find(".btn_close").on("click", function () { $btnSitemap.removeClass("active"); $pcSitemap.removeClass("active"); }); /* ================================================== Sitemap / Mobile Nav Functions ================================================== */ // 모바일 메뉴 열기 + 상태 초기화 function openMobileNav() { $btnSitemap.addClass("active"); $mobileNav.addClass("active"); $mobileNav.find(".depth02_ul").hide(); $mobileNav.find("li").removeClass("active"); $mobileNav.find(".icon.arrow") .removeClass("top") .addClass("bottom"); } // PC sitemap 토글 function togglePcSitemap() { $btnSitemap.toggleClass("active"); $pcSitemap.toggleClass("active"); } /* ================================================== Resize 대응 - 화면 전환 시 열려있는 메뉴 정리 ================================================== */ $(window).on("resize", function () { if ($(window).width() < BREAK_POINT) { $pcSitemap.removeClass("active"); } else { $mobileNav.removeClass("active"); } }); /* ================================================== Top Button - 상단 이동 + header 상태 초기화 ================================================== */ $(".btn_top").on("click", function (e) { e.preventDefault(); $("html, body").stop().animate( { scrollTop: 0 }, 400, function () { $header.removeClass("scrolled"); } ); }); });