diff --git a/opentech/static_src/src/javascript/components/mobile-menu.js b/opentech/static_src/src/javascript/components/mobile-menu.js index 04bf23232c0828dc804708442eb812aec29c4647..3c01a858d4da328331185a40c02c893a7650e6a7 100644 --- a/opentech/static_src/src/javascript/components/mobile-menu.js +++ b/opentech/static_src/src/javascript/components/mobile-menu.js @@ -3,40 +3,40 @@ class MobileMenu { return '.js-mobile-menu-toggle'; } - constructor(node, openCb = () => {}, closeCb = () => {}) { + constructor(node, closeButton, mobileMenu, search) { this.node = node; - - // Any callbacks to be called on open or close. - this.openCb = openCb; - this.closeCb = closeCb; - - this.state = { - open: false, - }; + this.closeButton = closeButton; + this.mobileMenu = mobileMenu; + this.search = search; this.bindEventListeners(); } bindEventListeners() { this.node.click(this.toggle.bind(this)); + this.closeButton.click(this.toggle.bind(this)); } toggle() { - this.state.open ? this.close() : this.open(); - } - - open() { - this.node.addClass('is-open'); - this.openCb(); - - this.state.open = true; - } - - close() { - this.node.removeClass('is-open'); - this.closeCb(); - - this.state.open = false; + // toggle mobile menu + this.mobileMenu[0].classList.toggle('is-visible'); + + // toggle modifier to change position of the search div when the mobile menu is open + this.search[0].classList.toggle('header__search--mobile-menu-open'); + + // reset the search whenever the mobile menu is toggled + if(this.search[0].classList.contains('is-visible')){ + this.search[0].classList.toggle('is-visible'); + document.querySelector('.header__inner--menu-open').classList.toggle('header__inner--search-open'); + } + + // reset the search show/hide icons + if(this.mobileMenu[0].classList.contains('is-visible')){ + document.querySelector('.header__icon--open-search-menu-open').classList.remove('is-hidden'); + document.querySelector('.header__icon--close-search-menu-open').classList.remove('is-unhidden'); + document.querySelector('.header__icon--open-search-menu-closed').classList.remove('is-hidden'); + document.querySelector('.header__icon--close-search-menu-closed').classList.remove('is-unhidden'); + } } } diff --git a/opentech/static_src/src/javascript/main.js b/opentech/static_src/src/javascript/main.js index 08d93db51810a33ec5db7ef8b6799baca898d067..743ab06f115464241b2deac4872de0bb7b7da5d2 100755 --- a/opentech/static_src/src/javascript/main.js +++ b/opentech/static_src/src/javascript/main.js @@ -1,24 +1,10 @@ import $ from './globals'; import MobileMenu from './components/mobile-menu'; - -// Open the mobile menu callback -function openMobileMenu() { - document.querySelector('body').classList.add('no-scroll'); - document.querySelector('.header__menus--mobile').classList.add('is-visible'); -} - -// Close the mobile menu callback. -function closeMobileMenu() { - document.querySelector('body').classList.remove('no-scroll'); - document.querySelector('.header__menus--mobile').classList.remove('is-visible'); -} import Search from './components/search'; $(function () { $(MobileMenu.selector()).each((index, el) => { - new MobileMenu($(el), openMobileMenu, closeMobileMenu); - }); - + new MobileMenu($(el), $('.js-mobile-menu-close'), $('.header__menus--mobile'), $('.header__search')); }); $(Search.selector()).each((index, el) => { diff --git a/opentech/static_src/src/sass/components/_icon.scss b/opentech/static_src/src/sass/components/_icon.scss index 00dc7ee7c51f70dc475bf9f592cd879f5fff5ccf..f41decdf526900cafc92ffc14cfb6ba27f5a9bd1 100644 --- a/opentech/static_src/src/sass/components/_icon.scss +++ b/opentech/static_src/src/sass/components/_icon.scss @@ -13,7 +13,7 @@ height: 15px; margin-right: 5px; fill: $color--primary; - } + } &--footer-social { @include media-query(tablet-portrait) { @@ -21,6 +21,11 @@ } } + &--mobile-menu { + width: 32px; + height: 28px; + } + &--footer-credit { width: 70px; height: 45px; diff --git a/opentech/static_src/src/sass/layout/_header.scss b/opentech/static_src/src/sass/layout/_header.scss index 6fe7b3df7b436029ac6fe26eeca066504d39a3b2..070358a2d2dafb34726fa9ce43bf451536904a6e 100644 --- a/opentech/static_src/src/sass/layout/_header.scss +++ b/opentech/static_src/src/sass/layout/_header.scss @@ -32,40 +32,55 @@ align-items: center; justify-content: space-between; width: 100%; - } - &__inner--top { - display: flex; - align-items: center; - justify-content: flex-end; + &--mobile-buttons { + justify-content: flex-end; + + @include media-query(tablet-portrait) { + display: none; + } + } + + &--menu-open { + padding: 10px; + background: transparent; + transition: background $transition; + } + + &--search-open { + background: $color--dark-blue; + } } &__menus { - &--desktop { display: none; @include media-query(tablet-portrait) { display: flex; - flex-direction: column; - justify-content: space-between; + align-items: center; } } &--mobile { position: fixed; - top: 87px; + top: 0; left: 0; - display: flex; + z-index: 10; width: 100%; height: 100%; - padding-top: 20px; - background: rgba($color--white, 0.95); - transform: translate3d(100%, 0%, 0); - transition: transform 250ms cubic-bezier(0.24, 0.26, 0.2, 1) 0ms; + background: $color--dark-grey; + opacity: 0; + transform: translate3d(0, -100%, 0); + transition: opacity, transform, 250ms cubic-bezier(0.65, 0.05, 0.36, 1) 0ms; &.is-visible { - transform: translate3d(0%, 0%, 0); + opacity: 1; + transform: translate3d(0, 0%, 0); + + @include media-query(tablet-portrait) { + display: none; + } } nav { @@ -98,23 +113,13 @@ } &__menu-toggle { - @include font-size(milli); - z-index: 10; - display: flex; - align-items: flex-end; - flex-direction: column; - width: 100%; - font-weight: $weight--bold; - color: $color--secondary; - text-transform: uppercase; - @include media-query(tablet-portrait) { display: none; } } &__icon { - &--cross { + &--close-search { @extend %is-hidden; } @@ -144,18 +149,22 @@ } &__search { - &--desktop { - @extend %is-invisible; - position: absolute; - top: 0; - left: 0; - display: flex; - align-items: flex-end; - justify-content: center; - width: 100%; - height: 180px; - padding-bottom: 50px; - background: $color--dark-blue; + @extend %is-invisible; + position: absolute; + top: 0; + left: 0; + display: flex; + align-items: flex-end; + justify-content: center; + width: 100%; + height: 180px; + padding-bottom: 50px; + background: $color--dark-blue; + + &--mobile-menu-open { + top: 80px; + z-index: 12; + height: 120px; } } } diff --git a/opentech/templates/base.html b/opentech/templates/base.html index 5ae3aef8177d8f0340f75ef7a3606f69b30cc06a..7a83d3948ca76f730a4da76af4d771a735bd3cb0 100644 --- a/opentech/templates/base.html +++ b/opentech/templates/base.html @@ -81,28 +81,40 @@ <svg class="header__logo header__logo--mobile"><use xlink:href="#logo-mobile"></use></svg> </a> - <div class="header__menu-toggle"> - <span>Menu</span> - <button class="button button-menu-toggle js-mobile-menu-toggle" aria-haspopup="true"> - <span class="button-menu-toggle__line"></span> - <span class="button-menu-toggle__line"></span> - <span class="button-menu-toggle__line"></span> - <span class="button-menu-toggle__line"></span> + <div class="header__inner header__inner--mobile-buttons"> + <button class="button button--left-space js-search-toggle"> + <svg class="header__icon header__icon--open-search header__icon--open-search-menu-closed icon icon--mobile-menu"><use xlink:href="#magnifying-glass"></use></svg> + <svg class="header__icon header__icon--close-search header__icon--close-search-menu-closed icon icon--mobile-menu"><use xlink:href="#cross"></use></svg> + </button> + <button class="button js-mobile-menu-toggle" aria-haspopup="true" > + <svg class="icon icon--mobile-menu"><use xlink:href="#mobile-menu-toggle"></use></svg> </button> </div> <section class="header__menus header__menus--desktop"> - <div class="header__inner--top"> - {% primarynav %} + {% primarynav %} - <button class="button js-desktop-search-toggle"> - <svg class="header__icon header__icon--magnifying-glass icon"><use xlink:href="#magnifying-glass"></use></svg> - <svg class="header__icon header__icon--cross icon"><use xlink:href="#cross"></use></svg> - </button> - </div> + <button class="button button--left-space js-search-toggle"> + <svg class="header__icon header__icon--open-search icon"><use xlink:href="#magnifying-glass"></use></svg> + <svg class="header__icon header__icon--close-search icon"><use xlink:href="#cross"></use></svg> + </button> </section> <section class="header__menus header__menus--mobile"> + <div class="header__inner header__inner--menu-open"> + <a href="{% slugurl 'home' %}"> + <svg class="header__logo header__logo--mobile"><use xlink:href="#logo-mobile"></use></svg> + </a> + <div class="header__inner header__inner--mobile-buttons"> + <button class="button js-search-toggle"> + <svg class="header__icon header__icon--open-search header__icon--open-search-menu-open icon icon--mobile-menu"><use xlink:href="#magnifying-glass"></use></svg> + <svg class="header__icon header__icon--close-search header__icon--close-search-menu-open icon icon--mobile-menu"><use xlink:href="#cross"></use></svg> + </button> + <button class="button js-mobile-menu-close"> + <svg class="header__icon header__icon--cross icon icon--mobile-menu"><use xlink:href="#cross"></use></svg> + </button> + </div> + </div> {% primarynav %} </section>