From 01fe03055cbd35871da294ab6275970a110dc398 Mon Sep 17 00:00:00 2001 From: Bandana Laishram Date: Thu, 12 Dec 2024 14:07:22 +0530 Subject: [PATCH] Making localnav auto dismiss on click outside --- .../global-navigation/global-navigation.css | 24 +++++++++---------- .../global-navigation/global-navigation.js | 18 ++++++++------ .../global-navigation/utilities/utilities.js | 14 +++++++---- 3 files changed, 33 insertions(+), 23 deletions(-) diff --git a/libs/blocks/global-navigation/global-navigation.css b/libs/blocks/global-navigation/global-navigation.css index 784c571b5e..132e5267d8 100644 --- a/libs/blocks/global-navigation/global-navigation.css +++ b/libs/blocks/global-navigation/global-navigation.css @@ -1091,27 +1091,27 @@ header.new-nav .feds-breadcrumbs li:first-child:not(:nth-last-child(-n+3)):after border: 0; } -.feds-localnav.active .feds-localnav-items { +.feds-localnav.feds-localnav--active .feds-localnav-items { display: block; width: 100%; position: absolute; overflow: auto; } -.feds-localnav.active .feds-localnav-items .feds-menu-items { +.feds-localnav.feds-localnav--active .feds-localnav-items .feds-menu-items { padding: 0; border-bottom: 0; } -.feds-localnav.active .feds-localnav-items .feds-menu-column > ul { +.feds-localnav.feds-localnav--active .feds-localnav-items .feds-menu-column > ul { padding: 0; } -.feds-localnav.active .feds-localnav-items .feds-menu-column > ul .feds-navLink { +.feds-localnav.feds-localnav--active .feds-localnav-items .feds-menu-column > ul .feds-navLink { padding-left: 38px; } -.feds-localnav.active .feds-localnav-items .feds-menu-items .feds-navLink { +.feds-localnav.feds-localnav--active .feds-localnav-items .feds-menu-items .feds-navLink { padding: 12px 56px; } @@ -1136,16 +1136,16 @@ header.new-nav .feds-breadcrumbs li:first-child:not(:nth-last-child(-n+3)):after padding: 10px 20px; } -.feds-localnav.active .feds-localnav-items { +.feds-localnav.feds-localnav--active .feds-localnav-items { box-sizing: border-box; max-height: calc(100vh - (var(--global-height-nav) + var(--feds-localnav-height))); } -.feds-localnav.active.is-sticky .feds-localnav-items { +.feds-localnav.feds-localnav--active.is-sticky .feds-localnav-items { max-height: calc(100vh - var(--feds-localnav-height)); } -.feds-localnav .feds-dropdown--active::before { +.feds-localnav .feds-localnav--active::before { display: none; } @@ -1153,11 +1153,11 @@ header.new-nav .feds-breadcrumbs li:first-child:not(:nth-last-child(-n+3)):after display: none; } -.feds-localnav.active .feds-localnav-title::after { +.feds-localnav.feds-localnav--active .feds-localnav-title::after { transform: rotateZ(-135deg); } -.feds-localnav.active .feds-localnav-curtain { +.feds-localnav.feds-localnav--active .feds-localnav-curtain { width: 100%; height: calc(100vh - (var(--feds-height-nav) + var(--feds-localnav-height))); position: absolute; @@ -1165,11 +1165,11 @@ header.new-nav .feds-breadcrumbs li:first-child:not(:nth-last-child(-n+3)):after opacity: 0.7; } -.feds-localnav.active.is-sticky .feds-localnav-curtain { +.feds-localnav.feds-localnav--active.is-sticky .feds-localnav-curtain { height: calc(100vh - var(--feds-localnav-height)); } -.feds-localnav.active .feds-localnav-exit { +.feds-localnav.feds-localnav--active .feds-localnav-exit { display: block; } diff --git a/libs/blocks/global-navigation/global-navigation.js b/libs/blocks/global-navigation/global-navigation.js index c76aab3441..55c002962a 100644 --- a/libs/blocks/global-navigation/global-navigation.js +++ b/libs/blocks/global-navigation/global-navigation.js @@ -249,9 +249,10 @@ const getBrandImage = (image, brandImageOnly) => { }; const closeOnClickOutside = (e) => { - if (!isDesktop.matches) return; + const newMobileNav = getMetadata('mobile-gnav-v2') !== 'false'; + if (!isDesktop.matches && !newMobileNav) return; - const openElemSelector = `${selectors.globalNav} [aria-expanded = "true"]`; + const openElemSelector = `${selectors.globalNav} [aria-expanded = "true"], ${selectors.localNav} [aria-expanded = "true"]`; const isClickedElemOpen = [...document.querySelectorAll(openElemSelector)] .find((openItem) => openItem.parentElement.contains(e.target)); @@ -402,10 +403,14 @@ class Gnav { }); localNav.querySelector('.feds-localnav-title').addEventListener('click', () => { - localNav.classList.toggle('active'); - const isActive = localNav.classList.contains('active'); + localNav.classList.toggle('feds-localnav--active'); + const isActive = localNav.classList.contains('feds-localnav--active'); localNav.querySelector('.feds-localnav-title').setAttribute('aria-expanded', isActive); }); + + localNav.querySelector('.feds-localnav-curtain').addEventListener('click', (e) => { + trigger({ element: e.currentTarget, event: e }); + }); this.elements.localNav = localNav; localNavItems[0].querySelector('a').textContent = title.trim(); const isAtTop = () => { @@ -1012,9 +1017,8 @@ class Gnav { if (elements) { elements.innerHTML = template.innerHTML; // Reattach click events, as cloned elem don't retain event listeners - elements.querySelector('button')?.addEventListener('click', (e) => { - trigger({ element: e.currentTarget, event: e, type: 'localNavTitle' }); - setActiveDropdown(e.currentTarget); + elements.querySelector('.feds-localnav-items button')?.addEventListener('click', (e) => { + trigger({ element: e.currentTarget, event: e, type: 'localNavItem' }); }); elements.querySelectorAll('.feds-menu-headline').forEach((elem) => { diff --git a/libs/blocks/global-navigation/utilities/utilities.js b/libs/blocks/global-navigation/utilities/utilities.js index 8cd6b83852..44f3bba415 100644 --- a/libs/blocks/global-navigation/utilities/utilities.js +++ b/libs/blocks/global-navigation/utilities/utilities.js @@ -29,6 +29,7 @@ export const selectors = { gnavPromo: '.gnav-promo', columnBreak: '.column-break', brandImageOnly: '.brand-image-only', + localNav: '.feds-localnav', }; export const icons = { @@ -216,13 +217,18 @@ export function setCurtainState(state) { export const isDesktop = window.matchMedia('(min-width: 900px)'); export const isTangentToViewport = window.matchMedia('(min-width: 900px) and (max-width: 1440px)'); -export function setActiveDropdown(elem) { +export function setActiveDropdown(elem, type) { const activeClass = selectors.activeDropdown.replace('.', ''); + const activeLocalNav = '.feds-localnav--active'; // We always need to reset all active dropdowns at first const resetActiveDropdown = () => { [...document.querySelectorAll(selectors.activeDropdown)] .forEach((activeDropdown) => activeDropdown.classList.remove(activeClass)); + if (type !== 'localNavItem') { + [...document.querySelectorAll(activeLocalNav)] + .forEach((activeDropdown) => activeDropdown.classList.remove('feds-localnav--active')); + } }; resetActiveDropdown(); @@ -286,16 +292,16 @@ export const [hasActiveLink, setActiveLink, isActiveLink, getActiveLink] = (() = })(); export function closeAllDropdowns({ type } = {}) { - const selector = selectorMap[type] || `${selectors.globalNav} [aria-expanded='true']`; + const selector = selectorMap[type] || `${selectors.globalNav} [aria-expanded = "true"], ${selectors.localNav} [aria-expanded = "true"]`; const openElements = document.querySelectorAll(selector); if (!openElements) return; [...openElements].forEach((el) => { - if ('fedsPreventautoclose' in el.dataset) return; + if ('fedsPreventautoclose' in el.dataset || (type === 'localNavItem' && el.classList.contains('feds-localnav-title'))) return; el.setAttribute('aria-expanded', 'false'); }); - setActiveDropdown(); + setActiveDropdown(undefined, type); if (isDesktop.matches) setCurtainState(false); }