Loading core/modules/system/tests/modules/olivero_test/olivero_test.links.menu.yml +10 −0 Original line number Diff line number Diff line Loading @@ -32,3 +32,13 @@ olivero_test.anchor_link: url: "internal:#footer" menu_name: main weight: 200 olivero_test.long_item_1: title: Long long long long route_name: <front> menu_name: main weight: 200 olivero_test.long_item_2: title: Long long long long route_name: <front> menu_name: main weight: 200 core/tests/Drupal/Nightwatch/Tests/Olivero/oliveroDesktopMenuTest.js +15 −2 Original line number Diff line number Diff line Loading @@ -66,7 +66,7 @@ module.exports = { .waitForElementVisible(headerNavSelector) .assert.visible(headerNavSelector) .assert.not.visible(`#${linkSubMenuId}`) .moveToElement(`[aria-controls="${linkSubMenuId}"]`, 0, 0) .moveToElement(`[aria-controls="${linkSubMenuId}"]`, 1, 1) .assert.visible(`#${linkSubMenuId}`) .assert.attributeEquals( `[aria-controls="${linkSubMenuId}"]`, Loading @@ -74,7 +74,7 @@ module.exports = { 'true', ) .assert.not.visible(`#${buttonSubMenuId}`) .moveToElement(`[aria-controls="${buttonSubMenuId}"]`, 0, 0) .moveToElement(`[aria-controls="${buttonSubMenuId}"]`, 1, 1) .assert.visible(`#${buttonSubMenuId}`) .assert.attributeEquals( `[aria-controls="${buttonSubMenuId}"]`, Loading @@ -82,4 +82,17 @@ module.exports = { 'true', ); }, 'Verify desktop menu converts to mobile if it gets too long': (browser) => { browser .drupalRelativeURL('/node') .waitForElementVisible('body') .assert.not.elementPresent('body.is-always-mobile-nav') .setWindowSize(1220, 800) .execute(() => { // Directly modify the width of the site branding name so that it causes // the primary navigation to be too long, and switch into mobile mode. document.querySelector('.site-branding__name').style.width = '350px'; }, []) .assert.elementPresent('body.is-always-mobile-nav'); }, }; core/themes/olivero/js/nav-resize.es6.js 0 → 100644 +86 −0 Original line number Diff line number Diff line /** * @file * This script watches the desktop version of the primary navigation. If it * wraps to two lines, it will automatically transition to a mobile navigation * and remember where it wrapped so it can transition back. */ ((Drupal, once) => { /** * Handles the transition from mobile navigation to desktop navigation. * * @param {Element} navWrapper - The primary navigation's top-level <ul> element. * @param {Element} navItem - The first item within the primary navigation. */ function transitionToDesktopNavigation(navWrapper, navItem) { document.body.classList.remove('is-always-mobile-nav'); // Double check to see if the navigation is wrapping, and if so, re-enable // mobile navigation. This solves an edge cases where if the amount of // navigation items always causes the primary navigation to wrap, and the // page is loaded at a narrower viewport and then widened, the mobile nav // may not be enabled. if (navWrapper.clientHeight > navItem.clientHeight) { document.body.classList.add('is-always-mobile-nav'); } } /** * Callback from Resize Observer. This checks if the primary navigation is * wrapping, and if so, transitions to the mobile navigation. * * @param {ResizeObserverEntry} entries - Object passed from ResizeObserver. */ function checkIfDesktopNavigationWraps(entries) { const navItem = document.querySelector('.primary-nav__menu-item'); if ( Drupal.olivero.isDesktopNav() && entries[0].contentRect.height > navItem.clientHeight ) { const navMediaQuery = window.matchMedia( `(max-width: ${window.innerWidth + 15}px)`, // 5px adds a small buffer before switching back. ); document.body.classList.add('is-always-mobile-nav'); // In the event that the viewport was resized, we remember the viewport // width with a one-time event listener ,so we can attempt to transition // from mobile navigation to desktop navigation. navMediaQuery.addEventListener( 'change', () => { transitionToDesktopNavigation(entries[0].target, navItem); }, { once: true }, ); } } /** * Set up Resize Observer to listen for changes to the size of the primary * navigation. * * @param {Element} primaryNav - The primary navigation's top-level <ul> element. */ function init(primaryNav) { const resizeObserver = new ResizeObserver(checkIfDesktopNavigationWraps); resizeObserver.observe(primaryNav); } /** * Initialize the automatic navigation transition. * * @type {Drupal~behavior} * * @prop {Drupal~behaviorAttach} attach * Attach context and settings for navigation. */ Drupal.behaviors.automaticMobileNav = { attach(context) { once( 'olivero-automatic-mobile-nav', '[data-drupal-selector="primary-nav-menu--level-1"]', context, ).forEach(init); }, }; })(Drupal, once); core/themes/olivero/js/nav-resize.js 0 → 100644 +42 −0 Original line number Diff line number Diff line /** * DO NOT EDIT THIS FILE. * See the following change record for more information, * https://www.drupal.org/node/2815083 * @preserve **/ ((Drupal, once) => { function transitionToDesktopNavigation(navWrapper, navItem) { document.body.classList.remove('is-always-mobile-nav'); if (navWrapper.clientHeight > navItem.clientHeight) { document.body.classList.add('is-always-mobile-nav'); } } function checkIfDesktopNavigationWraps(entries) { const navItem = document.querySelector('.primary-nav__menu-item'); if (Drupal.olivero.isDesktopNav() && entries[0].contentRect.height > navItem.clientHeight) { const navMediaQuery = window.matchMedia(`(max-width: ${window.innerWidth + 15}px)`); document.body.classList.add('is-always-mobile-nav'); navMediaQuery.addEventListener('change', () => { transitionToDesktopNavigation(entries[0].target, navItem); }, { once: true }); } } function init(primaryNav) { const resizeObserver = new ResizeObserver(checkIfDesktopNavigationWraps); resizeObserver.observe(primaryNav); } Drupal.behaviors.automaticMobileNav = { attach(context) { once('olivero-automatic-mobile-nav', '[data-drupal-selector="primary-nav-menu--level-1"]', context).forEach(init); } }; })(Drupal, once); No newline at end of file core/themes/olivero/olivero.libraries.yml +4 −0 Original line number Diff line number Diff line Loading @@ -214,6 +214,10 @@ navigation-primary: js: js/navigation.js: {} js/second-level-navigation.js: {} js/nav-resize.js: {} dependencies: - core/drupal - core/once navigation-secondary: version: VERSION Loading Loading
core/modules/system/tests/modules/olivero_test/olivero_test.links.menu.yml +10 −0 Original line number Diff line number Diff line Loading @@ -32,3 +32,13 @@ olivero_test.anchor_link: url: "internal:#footer" menu_name: main weight: 200 olivero_test.long_item_1: title: Long long long long route_name: <front> menu_name: main weight: 200 olivero_test.long_item_2: title: Long long long long route_name: <front> menu_name: main weight: 200
core/tests/Drupal/Nightwatch/Tests/Olivero/oliveroDesktopMenuTest.js +15 −2 Original line number Diff line number Diff line Loading @@ -66,7 +66,7 @@ module.exports = { .waitForElementVisible(headerNavSelector) .assert.visible(headerNavSelector) .assert.not.visible(`#${linkSubMenuId}`) .moveToElement(`[aria-controls="${linkSubMenuId}"]`, 0, 0) .moveToElement(`[aria-controls="${linkSubMenuId}"]`, 1, 1) .assert.visible(`#${linkSubMenuId}`) .assert.attributeEquals( `[aria-controls="${linkSubMenuId}"]`, Loading @@ -74,7 +74,7 @@ module.exports = { 'true', ) .assert.not.visible(`#${buttonSubMenuId}`) .moveToElement(`[aria-controls="${buttonSubMenuId}"]`, 0, 0) .moveToElement(`[aria-controls="${buttonSubMenuId}"]`, 1, 1) .assert.visible(`#${buttonSubMenuId}`) .assert.attributeEquals( `[aria-controls="${buttonSubMenuId}"]`, Loading @@ -82,4 +82,17 @@ module.exports = { 'true', ); }, 'Verify desktop menu converts to mobile if it gets too long': (browser) => { browser .drupalRelativeURL('/node') .waitForElementVisible('body') .assert.not.elementPresent('body.is-always-mobile-nav') .setWindowSize(1220, 800) .execute(() => { // Directly modify the width of the site branding name so that it causes // the primary navigation to be too long, and switch into mobile mode. document.querySelector('.site-branding__name').style.width = '350px'; }, []) .assert.elementPresent('body.is-always-mobile-nav'); }, };
core/themes/olivero/js/nav-resize.es6.js 0 → 100644 +86 −0 Original line number Diff line number Diff line /** * @file * This script watches the desktop version of the primary navigation. If it * wraps to two lines, it will automatically transition to a mobile navigation * and remember where it wrapped so it can transition back. */ ((Drupal, once) => { /** * Handles the transition from mobile navigation to desktop navigation. * * @param {Element} navWrapper - The primary navigation's top-level <ul> element. * @param {Element} navItem - The first item within the primary navigation. */ function transitionToDesktopNavigation(navWrapper, navItem) { document.body.classList.remove('is-always-mobile-nav'); // Double check to see if the navigation is wrapping, and if so, re-enable // mobile navigation. This solves an edge cases where if the amount of // navigation items always causes the primary navigation to wrap, and the // page is loaded at a narrower viewport and then widened, the mobile nav // may not be enabled. if (navWrapper.clientHeight > navItem.clientHeight) { document.body.classList.add('is-always-mobile-nav'); } } /** * Callback from Resize Observer. This checks if the primary navigation is * wrapping, and if so, transitions to the mobile navigation. * * @param {ResizeObserverEntry} entries - Object passed from ResizeObserver. */ function checkIfDesktopNavigationWraps(entries) { const navItem = document.querySelector('.primary-nav__menu-item'); if ( Drupal.olivero.isDesktopNav() && entries[0].contentRect.height > navItem.clientHeight ) { const navMediaQuery = window.matchMedia( `(max-width: ${window.innerWidth + 15}px)`, // 5px adds a small buffer before switching back. ); document.body.classList.add('is-always-mobile-nav'); // In the event that the viewport was resized, we remember the viewport // width with a one-time event listener ,so we can attempt to transition // from mobile navigation to desktop navigation. navMediaQuery.addEventListener( 'change', () => { transitionToDesktopNavigation(entries[0].target, navItem); }, { once: true }, ); } } /** * Set up Resize Observer to listen for changes to the size of the primary * navigation. * * @param {Element} primaryNav - The primary navigation's top-level <ul> element. */ function init(primaryNav) { const resizeObserver = new ResizeObserver(checkIfDesktopNavigationWraps); resizeObserver.observe(primaryNav); } /** * Initialize the automatic navigation transition. * * @type {Drupal~behavior} * * @prop {Drupal~behaviorAttach} attach * Attach context and settings for navigation. */ Drupal.behaviors.automaticMobileNav = { attach(context) { once( 'olivero-automatic-mobile-nav', '[data-drupal-selector="primary-nav-menu--level-1"]', context, ).forEach(init); }, }; })(Drupal, once);
core/themes/olivero/js/nav-resize.js 0 → 100644 +42 −0 Original line number Diff line number Diff line /** * DO NOT EDIT THIS FILE. * See the following change record for more information, * https://www.drupal.org/node/2815083 * @preserve **/ ((Drupal, once) => { function transitionToDesktopNavigation(navWrapper, navItem) { document.body.classList.remove('is-always-mobile-nav'); if (navWrapper.clientHeight > navItem.clientHeight) { document.body.classList.add('is-always-mobile-nav'); } } function checkIfDesktopNavigationWraps(entries) { const navItem = document.querySelector('.primary-nav__menu-item'); if (Drupal.olivero.isDesktopNav() && entries[0].contentRect.height > navItem.clientHeight) { const navMediaQuery = window.matchMedia(`(max-width: ${window.innerWidth + 15}px)`); document.body.classList.add('is-always-mobile-nav'); navMediaQuery.addEventListener('change', () => { transitionToDesktopNavigation(entries[0].target, navItem); }, { once: true }); } } function init(primaryNav) { const resizeObserver = new ResizeObserver(checkIfDesktopNavigationWraps); resizeObserver.observe(primaryNav); } Drupal.behaviors.automaticMobileNav = { attach(context) { once('olivero-automatic-mobile-nav', '[data-drupal-selector="primary-nav-menu--level-1"]', context).forEach(init); } }; })(Drupal, once); No newline at end of file
core/themes/olivero/olivero.libraries.yml +4 −0 Original line number Diff line number Diff line Loading @@ -214,6 +214,10 @@ navigation-primary: js: js/navigation.js: {} js/second-level-navigation.js: {} js/nav-resize.js: {} dependencies: - core/drupal - core/once navigation-secondary: version: VERSION Loading