Выезжающее боковое меню на JS+CSS

Боковая панель сайта на чистом js и jquery

Друзья, я уже писал как о том как сделать мобильное меню для сайта, но время идет и в моде уже другой тип меню – выезжающая панель с боку. Это удобно и красиво смотрится на любых дисплеях.

Сегодня поделюсь опытом создания своего бокового меню для сайта без использования тяжелых фреймворков и плагинов. Это меню будет выезжать по нажатию на кнопку гамбургера с правого бока. Кроме того это меню будет обладать эффектом акордеона – раскрывать подменю по нажатию. Ну а затем я покажу, как можно вывести обычное меню wordpress в виде нашего выезжающего меню.

Протестировать работу и посмотреть как все выглядит можно тут:

Весь процесс мы разобьем на несколько частей:

  1. Напишем на HTML кнопку-гамбургер и сам блок с меню.
  2. Опишем CSS стили как будет все выглядеть
  3. Оживим наше меню при помощи JavaScript
  4. Прикрутим наше меню к шаблону на wordpress

Итак поехали!

Напишем HTML код кнопки-гамбургера и блока с меню

Кнопку можно сделать просто картинкой, но это прошлый век, мы сделаем так чтобы она выглядела достойно и анимировалась при нажатии, это легко. Сам HTML кнопки:

<div id="nav-icon3" class="pushmenu"> <span></span> <span></span> <span></span> <span></span> </div>
Code language: HTML, XML (xml)

Как видим тут самое главное это класс “pushmenu”, его можно добавить любому тегу и он будет срабатывать как триггер.

В моем случае 3 тега span будут как три палки гамбургера, а четвертая нужна для анимации, но об этом чуть позже.

Давайте напишем блок самой выезжающей панели, но пока без меню, чтобы было нагляднее:

<nav class="sidebar"> <div class="text d-flex p-2"> <h4>МЕНЮ САЙТА</h4> <div id="nav-icon3" class="pushmenu opened"> <span></span> <span></span> <span></span> <span></span> </div> </div> <div class="menu-main-menu-container"> // тут будет наше меню </div> </nav> <div class="hidden-overley"></div>
Code language: HTML, XML (xml)

А в указанном выше месте мы поместим само меню:

<ul id="menu-main-menu"> <li class="current-menu-item"><a href="#" >Главная</a></li> <li class="menu-parent-item"><a href="#">Услуги<i></i></a> <ul class="sub-menu"> <li><a href="#">Какая-то услуга 1</a></li> <li><a href="#">Какая-то услуга 2</a></li> <li><a href="#">Какая-то услуга 4</a></li> </ul> </li> <li><a href="#">Клиентам</a></li> <li><a href="#">Контакты</a></li> </ul>
Code language: HTML, XML (xml)

Отлично, теперь нам нужно как-то все разукрасить и задать размеры.

CSS стили для бокового выезжающего меню и кнопки гамбургера

Кнопка гамбургер имеет следующие стили:

<style> #nav-icon3 { width: 40px; height: 30px; position: relative; -webkit-transform: rotate(0deg); -moz-transform: rotate(0deg); -o-transform: rotate(0deg); transform: rotate(0deg); -webkit-transition: .5s ease-in-out; -moz-transition: .5s ease-in-out; -o-transition: .5s ease-in-out; transition: .5s ease-in-out; cursor: pointer; } #nav-icon3 span { display: block; position: absolute; height: 4px; width: 100%; background: #90b5cc; border-radius: 3px; opacity: 1; left: 0; -webkit-transform: rotate(0deg); -moz-transform: rotate(0deg); -o-transform: rotate(0deg); transform: rotate(0deg); -webkit-transition: .25s ease-in-out; -moz-transition: .25s ease-in-out; -o-transition: .25s ease-in-out; transition: .25s ease-in-out; } #nav-icon3 span:nth-child(1) { top: 0px; } #nav-icon3 span:nth-child(2),#nav-icon3 span:nth-child(3) { top: 12px; } #nav-icon3 span:nth-child(4) { top: 24px; } #nav-icon3.open span:nth-child(1),#nav-icon3.opened span:nth-child(1) { top: 12px; width: 0%; left: 50%; } #nav-icon3.open span:nth-child(2),#nav-icon3.opened span:nth-child(2) { -webkit-transform: rotate(45deg); -moz-transform: rotate(45deg); -o-transform: rotate(45deg); transform: rotate(45deg); } #nav-icon3.open span:nth-child(3),#nav-icon3.opened span:nth-child(3) { -webkit-transform: rotate(-45deg); -moz-transform: rotate(-45deg); -o-transform: rotate(-45deg); transform: rotate(-45deg); } #nav-icon3.open span:nth-child(4),#nav-icon3.opened span:nth-child(4) { top: 12px; width: 0%; left: 50%; } </style>
Code language: HTML, XML (xml)

Стили для блока с меню:

<style> .sidebar #nav-icon3 span {background: #fff;} body.sidebar-opened {overflow:hidden;} .hidden-overley { position: fixed; top: 0; left: 0; z-index: 99; background: #000000; opacity:0; width:0; height:0; transition: opacity 1s; } .hidden-overley.show { height: 100%; width: 100%; opacity:0.5; transition: opacity 1s; } .sidebar{ position: fixed; z-index:100; width: 300px; height: 100%; right: -300px; top:0; background: #fff; transition: right 0.4s ease; overflow: auto; } .sidebar .d-flex.p-2 {display:-webkit-box;display:flex;padding: 10px!important;} .sidebar .text{ color: white; font-size: 18px; font-weight: 600; line-height: inherit; text-align: center; background: #90b5cc; letter-spacing: 1px; -webkit-box-pack: justify; -ms-flex-pack: justify; justify-content: space-between; -webkit-box-align: center; -ms-flex-align: center; align-items: center; } .sidebar .side-tel {font-size:0.8rem;} .sidebar .text a {color: white;} .sidebar.show{ right: 0px; } .sidebar ul{ background: none; height: auto; width: 100%; list-style: none; margin: 0; padding:0; } .sidebar ul li{ line-height: 60px; border-top: 1px solid #eee; margin: 0; } .sidebar ul li:last-child{ border-bottom: 1px solid rgba(255,255,255,0.05); } .sidebar ul li a{ box-sizing:border-box; position: relative; color: #757575; text-decoration: none; font-size: 18px; padding-left: 30px; font-weight: 500; display: block; width: 100%; border-left: 3px solid #eee; } .sidebar ul li.current-menu-item a{ color: #90b5cc; background: #F5F5F5; border-left-color: #90b5cc; } .sidebar ul li a:hover{ cursor:pointer; background: #F5F5F5; border-left-color: #2196F3; } .sidebar ul ul{ position: static; display: none; } .sidebar ul .sub-menu.show{ display: block; } .sidebar ul ul li{ line-height: 42px; border-top: none; } .sidebar ul ul li a{ font-size: 17px; color: #333; padding-left: 40px; } .sidebar ul li.current-menu-item ul li a{ color: #333; background: #f9f9f9; border-left-color: transparent; } .sidebar ul li ul li.current-menu-item a {color:#2196F3;} .sidebar ul ul li a:hover{ color: #333!important; background: #F5F5F5!important; } .sidebar ul li a i:before {display:none;} .sidebar ul li.menu-parent-item a i:before{ content: ''; position: absolute; top: 50%; right: 20px; transform: translateY(-50%); font-size: 22px; transition: transform 0.4s; width: 20px; height: 20px; background-repeat:no-repeat; background-position: 0 0; background-image: url("data:image/svg+xml;charset=UTF-8,%3c?xml version='1.0' encoding='iso-8859-1'?%3e%3csvg version='1.1' id='Layer_1' xmlns='http://www.w3.org/2000/svg' xmlns:xlink='http://www.w3.org/1999/xlink' x='0px' y='0px' viewBox='0 0 512.011 512.011' style='enable-background:new 0 0 512.011 512.011;' xml:space='preserve'%3e%3cg%3e%3cg%3e%3cpath d='M505.755,123.592c-8.341-8.341-21.824-8.341-30.165,0L256.005,343.176L36.421,123.592c-8.341-8.341-21.824-8.341-30.165,0 s-8.341,21.824,0,30.165l234.667,234.667c4.16,4.16,9.621,6.251,15.083,6.251c5.462,0,10.923-2.091,15.083-6.251l234.667-234.667 C514.096,145.416,514.096,131.933,505.755,123.592z'/%3e%3c/g%3e%3c/g%3e%3c/svg%3e"); background-size: contain; display: block; } .sidebar ul ul a i:before {display:none !important;} .sidebar ul li a i.rotate:before{ transform: translateY(-50%) rotate(-180deg); } </style>
Code language: HTML, XML (xml)

Обратите внимание что я выделил 27 строку, изначально наше меню имеет отрицательный отступ равный ширине самого меню. Так мы добились его скрытия.

На 128 строке я добавил каретку в виде SVG картинки которая показывается внутри тегов <i></i> и только там где есть подменю, при нажатии на родительский пункт меню каретка поворачивается на 180 градусов.

Красота! Подошло время вдохнуть жизнь в наше меню с помощью JS

JS для бокового выезжающего сайдбара

Если у вас уже установлен фреймворк jQuery, то весь код будет таким:

<script> jQuery(document).ready(function($){ // Клик по кнопке-гамбургеру открывает меню, повторный клик закрывает $('.pushmenu').click(function(){ $('.pushmenu').toggleClass("open"); $('.sidebar').toggleClass("show"); $('.hidden-overley').toggleClass("show"); $('body').toggleClass("sidebar-opened") }); // Когда панель открыта, клик по облсти вне панели закрывает ее $('.hidden-overley').click(function(){ $(this).toggleClass("show"); $('.sidebar').toggleClass("show"); $('.pushmenu').toggleClass("open"); $('body').toggleClass("sidebar-opened") }); // меняем активность пункта меню по клику (НЕОБЯЗАТЕЛЬНО) $('.sidebar ul li').click(function(){ $(this).addClass("current-menu-item").siblings().removeClass("current-menu-item"); }); // Для анимации поворота каретки $('.menu-parent-item a:first-child').click(function(){ $(this).siblings().toggleClass("show"); $(this).find("i").toggleClass("rotate"); }); }); </script>
Code language: HTML, XML (xml)

Но если у вас не подключен jQuery, то вот код который будет делать тоже самое на чистом JavaScript:

<script> document.addEventListener('DOMContentLoaded', () => { // получаем все элементы с классом pushmenu const pushmenu = document.getElementsByClassName('pushmenu'); // получаем элемент с классом hidden-overley const hiddenOverley = document.querySelector('.hidden-overley'); // отслеживаем клик клика по оверлею hiddenOverley.addEventListener('click', (e) => { e.currentTarget.classList.toggle('show'); document.querySelector('.sidebar').classList.toggle('show'); document.querySelector('body').classList.toggle('sidebar-opened'); for( i=0; i < pushmenu.length; i++ ){ pushmenu[i].classList.toggle('open'); } }); const pushmenuFunction = function() { document.querySelector('.pushmenu').classList.toggle('open'); document.querySelector('.sidebar').classList.toggle('show'); document.querySelector('.hidden-overley').classList.toggle('show'); document.body.classList.toggle('sidebar-opened') }; // Отслеживаем клики кнопок с классом pushmenu for( i=0; i < pushmenu.length; i++ ){ pushmenu[i].addEventListener('click', pushmenuFunction, false); } // Получим все родительские элементы в меню const sidebarAccordeon = document.querySelectorAll('.sidebar .menu-parent-item a:first-child'); const accordeonFunction = function() { this.parentNode.querySelector('ul').classList.toggle('show'); this.querySelector('i').classList.toggle('rotate'); } // Отслеживаем клики родительских пунктов меню for( i=0; i < sidebarAccordeon.length; i++ ){ sidebarAccordeon[i].addEventListener('click', accordeonFunction, false); } }); </script>
Code language: HTML, XML (xml)

Итак мы получили рабочий выезжающий сайдбар с акордеонным меню. Я специально сделал названия классов и структуру похожую на ту которую генерирует движок WP, это я сделал на тот случай если мне нужно будет использовать этот сайдбар именно там. Далее об этом детальнее.

Настаиваем вывод WP меню в выезжающем сайдбаре

Для этого в файле шаблона вашей темы WP в том месте где вы будете выводить сайдбар нам нужно не прописывать код HTML меню вручную, а вызвать функцию wp_nav_menu(), которая отвечает за вывод меню, в нее мы може передать какие-то аргументы, чтобы она показывала меню так как нам нужно. Я писал о том как ее использовать здесь

В частности, например мы передадим в нее нужное меню, название класса меню, глубину вложенности, и тег <i> для отображения каретки у родителей:

<?php wp_nav_menu( array( 'theme_location' => 'menu-1', 'depth' => 2, 'menu_class' => '', 'link_after' => '<i></i>', ) ); ?>
Code language: HTML, XML (xml)

Этот код нужно вставить на том месте где у нас было меню <ul>. В результате мы получим точно такое же меню как у нас было раньше, только теперь оно генерируется автоматом движком.

Пишите в комментариях получилось ли у вас сделать такое меню, и задавайте вопросы если не получается

Понравилась статья? Поделиться с друзьями:
Добавить комментарий

63 + = 65

;-) :| :x :twisted: :smile: :shock: :sad: :roll: :razz: :oops: :o :mrgreen: :lol: :idea: :grin: :evil: :cry: :cool: :arrow: :???: :?: :!:

Открыть чат
1
Здравствуйте! Чем могу помочь?