jQuery & CSS3 меню акордеон з допомогою CSS Menu Maker

49

Ще зовсім недавно, працюючи над черговим шаблоном, мені доводилося перелопачувати купу коду, підбирати кольорову гаму, щоб зробити оригінальне меню навігації. Упевнений, ви проробляли тужу роботу і не раз. Зараз, на просторах глобальної мережі з’являються різні онлайн-генератори і цілі конструктори, за допомогою яких можна за кілька хвилин забабахати цілком собі гідне меню будь-якого типу, горизонтальне, вертикальне, багаторівневе і повністю адаптивне.

Якісь сервіси пропонують працювати з чистого аркуша, надаючи лише вибір різних інструментів і візуальний перегляд результату, а більш просунуті, пропонують готові шаблони меню, які ви з легкістю можете підлаштувати згідно вашому смаку і вимогам дизайну вашого проекту.
CSS Menu Maker як раз і є таким онлайн-конструктором, загляньте на дозвіллі, і я впевнений, ваша обойма інструментів, обов’язково поповниться.
На підтвердження всього вищевикладеного, хочу продемонструвати вам меню створене з допомогою цієї онлайн-конструктора.

CSS & jQuery Меню Аккордеон

Якщо ви дорожите кожним пікселем вільного місця в боковій колонці свого сайту, то це компактне меню стилі «акордеон» саме для вас! Подивіться живий приклад роботи цього чудового меню, а потім без суєти, розберемо його на складові.

DemoСкачать

CSS Menu Maker відмінно справляється зі своєю справою, на вихлопі ми отримуємо пристойно структуированную розмітку і добре читається, упорядкований код css, всі необхідні бібліотеки підключені, розклад гранично зрозумілий.

HTML-Розмітка

<ul id="menu">
<ul>
<li><a href="#"><i class="fa fa-home fa-fw></i> <span>Головна</span></a></li>
<li class="active has-sub"><a href="#"><i class="fa fa-sitemap"></i>  <span>Категорії</span></a>
<ul>
<li class="has-sub"><a href="#"><span>Категорія 1</span></a>
<ul>
<li><a href="#"><span>Підкатегорія 1</span></a></li>
<li><a href="#"><span>Підкатегорія 2</span></a></li>
<li class="last"><a href="#"><span>Підкатегорія 3</span></a></li>
</ul>
</li>
<li class="has-sub"><a href="#"><span>Категорія 2</span></a>
<ul>
<li><a href="#"><span>Підкатегорія 1</span></a></li>
<li class="last"><a href="#"><span>Підкатегорія 2</span></a></li>
</ul>
</li>
</ul>
</li>
<li><a href="#"><i class="fa fa-life-ring"></i>  <span>Про Сайт</span></a></li>
<li class="last"><a href="#"><i class="fa fa-envelope"></i>  <span>
Контакти</span></a></li>
</ul>
</ul>

Як бачите, меню побудовано у вигляді неупорядкованого списку із вкладеннями. Основними пунктами додані іконки з колекції Font Awesome, тег з назвою значка в конкретному CSS класі:

<i class="fa fa-home fa-fw>

Іконки завантажуються з бібліотеки Bootstrap, яку ми завчасно підключили розділі … нашого документа:

<link href="http://maxcdn.bootstrapcdn.com/font-awesome/4.1.0/css/font-awesome.min.css" rel="stylesheet">

Виникне потреба змінити іконки, дізнатися клас тій чи іншій шрифт-іконки, можна безпосередньо на сайті розробника: Тынц>>.
Каркас збудований, залишилося найцікавіше, сформувати стилі CSS, щоб наш «акордеон», візуально виглядав, як треба.

Стилі CSS

В оформленні зовнішнього вигляду задіяні сучасні властивості CSS3, легка зовнішня тінь з допомогою box-shadow, м’який наліт градієнта через background: linear-gradient і додамо трішки тіні для тексту. Як ви розумієте, в старих версіях браузера IE, наш чудовий акордеон, буде виглядати, м’яко кажучи, трохи інакше (((.

/*
* Стилі меню акордеон
*/
@import url(http://fonts.googleapis.com/css?family=Open+Sans:400,300,700&subset=latin,cyrillic);
#menu,
#menu ul,
#menu ul li,
#menu ul li a {
 position: relative;
display: block;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
margin: 0;
padding: 0;
border: 0;
list-style: none;
line-height: 1;
}
#menu {margin: 0 auto;
 width: 200px;
box-shadow: 2px 2px 10px rgba(0, 0, 0, 0.45);
color: #ffffff;
 font-family: 'Open Sans', Calibri, Arial, sans-serif;
}
#menu ul ul {
 display: none;
}
.align-right {
float: right;
}
#menu > ul > li > a {
 z-index: 2;
padding: 15px 20px;
border-top: 1px solid #1682ba;
 border-right: 1px solid #1682ba;
 border-left: 1px solid #1682ba;
 background: #36aae7;
 background: -webkit-linear-gradient(#36aae7, #1fa0e4);
 background: -moz-linear-gradient(#36aae7, #1fa0e4);
 background: -o-linear-gradient(#36aae7, #1fa0e4);
 background: -ms-linear-gradient(#36aae7, #1fa0e4);
 background: linear-gradient(#36aae7, #1fa0e4);
 box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.15);
color: #fff;
 text-decoration: none;
text-shadow: 0 1px 1px rgba(0, 0, 0, 0.35);
font-weight: 400;
font-size: 14px;
cursor: pointer;
}
#menu > ul > li > a:hover,
#menu > ul > li.active > a,
#menu > ul > li.open > a {
 background: #1fa0e4;
 background: -webkit-linear-gradient(#1fa0e4, #1992d1);
 background: -moz-linear-gradient(#1fa0e4, #1992d1);
 background: -o-linear-gradient(#1fa0e4, #1992d1);
 background: -ms-linear-gradient(#1fa0e4, #1992d1);
 background: linear-gradient(#1fa0e4, #1992d1);
 color: #eeeeee;
}
#menu > ul > li.open > a {
 border-bottom: 1px solid #1682ba;
 box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.15), 0 1px 1px rgba(0, 0, 0, 0.15);
}
#menu > ul > li:last-child > a,
#menu > ul > li.last > a {
 border-bottom: 1px solid #1682ba;
}
.holder {
position: absolute;
top: 0;
right: 0;
width: 0;
height: 0;
}
.holder::after,
.holder::before {
position: absolute;
right: 20px;
z-index: 10;
display: block;
width: 6px;
height: 6px;
content: "";
-webkit-transform: rotate(-135deg);
-moz-transform: rotate(-135deg);
-ms-transform: rotate(-135deg);
-o-transform: rotate(-135deg);
transform: rotate(-135deg);
}
.holder::after {
top: 17px;
border-top: 2px solid #ffffff;
 border-left: 2px solid #ffffff;
}
#menu > ul > li > a:hover > span::after,
#menu > ul > li.active > a > span::after,
#menu > ul > li.open > a > span::after {
 border-color: #eeeeee;
}
.holder::before {
top: 18px;
border-top: 2px solid;
border-top-color: inherit;
border-left: 2px solid;
border-left-color: inherit;
}
#menu ul ul li a {
 z-index: 1;
padding: 10px 20px;
border-right: 1px solid #32373e;
 border-bottom: 1px solid #32373e;
 border-left: 1px solid #32373e;
 background: #49505a;
 box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);
color: #eeeeee;
 text-decoration: none;
font-size: 13px;
cursor: pointer;
}
#menu ul ul li:hover > a,
#menu ul ul li.open > a,
#menu ul ul li.active > a {
 background: #424852;
 color: #fff;
}
#menu ul ul li:first-child > a {
 box-shadow: none;
}
#menu ul ul ul li:first-child > a {
 box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);
}
#menu ul ul ul li a {
 padding-left: 30px;
}
#menu > ul > li > ul > li:last-child > a,
#menu > ul > li > ul > li.last > a {
 border-bottom: 0;
}
#menu > ul > li > ul > li.open:last-child > a,
#menu > ul > li > ul > li.last.open > a {
 border-bottom: 1px solid #32373e;
}
#menu > ul > li > ul > li.open:last-child > ul > li:last-child > a {
 border-bottom: 0;
}
#menu ul ul li.has-sub > a::after {
 position: absolute;
top: 11.5px;
right: 20px;
z-index: 10;
display: block;
width: 5px;
height: 5px;
border-top: 2px solid #eeeeee;
 border-left: 2px solid #eeeeee;
 content: "";
-webkit-transform: rotate(-135deg);
-moz-transform: rotate(-135deg);
-ms-transform: rotate(-135deg);
-o-transform: rotate(-135deg);
transform: rotate(-135deg);
}
#menu ul ul li.active > a::after,
#menu ul ul li.open > a::after,
#menu ul ul li > a:hover::after {
 border-color: #ffffff;
}

/*
* Стилі меню акордеон
*/
@import url(http://fonts.googleapis.com/css?family=Open+Sans:400,300,700&subset=latin,cyrillic);
#menu,
#menu ul,
#menu ul li,
#menu ul li a {
position: relative;
display: block;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
margin: 0;
padding: 0;
border: 0;
list-style: none;
line-height: 1;
}
#menu {margin: 0 auto;
width: 200px;
box-shadow: 2px 2px 10px rgba(0, 0, 0, 0.45);
color: #ffffff;
font-family: ‘Open Sans’, Calibri, Arial, sans-serif;
}
#menu ul ul {
display: none;
}
.align-right {
float: right;
}
#menu > ul > li > a {
z-index: 2;
padding: 15px 20px;
border-top: 1px solid #1682ba;
border-right: 1px solid #1682ba;
border-left: 1px solid #1682ba;
background: #36aae7;
background: -webkit-linear-gradient(#36aae7, #1fa0e4);
background: -moz-linear-gradient(#36aae7, #1fa0e4);
background: -o-linear-gradient(#36aae7, #1fa0e4);
background: -ms-linear-gradient(#36aae7, #1fa0e4);
background: linear-gradient(#36aae7, #1fa0e4);
box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.15);
color: #fff;
text-decoration: none;
text-shadow: 0 1px 1px rgba(0, 0, 0, 0.35);
font-weight: 400;
font-size: 14px;
cursor: pointer;
}
#menu > ul > li > a:hover,
#menu > ul > li.active > a,
#menu > ul > li.open > a {
background: #1fa0e4;
background: -webkit-linear-gradient(#1fa0e4, #1992d1);
background: -moz-linear-gradient(#1fa0e4, #1992d1);
background: -o-linear-gradient(#1fa0e4, #1992d1);
background: -ms-linear-gradient(#1fa0e4, #1992d1);
background: linear-gradient(#1fa0e4, #1992d1);
color: #eeeeee;
}
#menu > ul > li.open > a {
border-bottom: 1px solid #1682ba;
box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.15), 0 1px 1px rgba(0, 0, 0, 0.15);
}
#menu > ul > li:last-child > a,
#menu > ul > li.last > a {
border-bottom: 1px solid #1682ba;
}
.holder {
position: absolute;
top: 0;
right: 0;
width: 0;
height: 0;
}
.holder::after,
.holder::before {
position: absolute;
right: 20px;
z-index: 10;
display: block;
width: 6px;
height: 6px;
content: “”;
-webkit-transform: rotate(-135deg);
-moz-transform: rotate(-135deg);
-ms-transform: rotate(-135deg);
-o-transform: rotate(-135deg);
transform: rotate(-135deg);
}
.holder::after {
top: 17px;
border-top: 2px solid #ffffff;
border-left: 2px solid #ffffff;
}
#menu > ul > li > a:hover > span::after,
#menu > ul > li.active > a > span::after,
#menu > ul > li.open > a > span::after {
border-color: #eeeeee;
}
.holder::before {
top: 18px;
border-top: 2px solid;
border-top-color: inherit;
border-left: 2px solid;
border-left-color: inherit;
}
#menu ul ul li a {
z-index: 1;
padding: 10px 20px;
border-right: 1px solid #32373e;
border-bottom: 1px solid #32373e;
border-left: 1px solid #32373e;
background: #49505a;
box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);
color: #eeeeee;
text-decoration: none;
font-size: 13px;
cursor: pointer;
}
#menu ul ul li:hover > a,
#menu ul ul li.open > a,
#menu ul ul li.active > a {
background: #424852;
color: #fff;
}
#menu ul ul li:first-child > a {
box-shadow: none;
}
#menu ul ul ul li:first-child > a {
box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);
}
#menu ul ul ul li a {
padding-left: 30px;
}
#menu > ul > li > ul > li:last-child > a,
#menu > ul > li > ul > li.last > a {
border-bottom: 0;
}
#menu > ul > li > ul > li.open:last-child > a,
#menu > ul > li > ul > li.last.open > a {
border-bottom: 1px solid #32373e;
}
#menu > ul > li > ul > li.open:last-child > ul > li:last-child > a {
border-bottom: 0;
}
#menu ul ul li.has-sub > a::after {
position: absolute;
top: 11.5 px;
right: 20px;
z-index: 10;
display: block;
width: 5px;
height: 5px;
border-top: 2px solid #eeeeee;
border-left: 2px solid #eeeeee;
content: “”;
-webkit-transform: rotate(-135deg);
-moz-transform: rotate(-135deg);
-ms-transform: rotate(-135deg);
-o-transform: rotate(-135deg);
transform: rotate(-135deg);
}
#menu ul ul li.active > a::after,
#menu ul ul li.open > a::after,
#menu ul ul li > a:hover::after {
border-color: #ffffff;
}

Шрифт тексту пунктів меню, використовуємо з сімейства Open Sans з підтримкою кирилиці, підключивши його до CSS через @import, безпосередньо з величезної бібліотеки шрифтів Google. Вам ніщо не заважає використовувати будь-який інший шрифт, лише б в радість і на користь справи.

От і все! Ми збудували каркас, обернули його в красиву обгортку, тепер необхідно «вдарити по хутру», завести наш акордеон. Для цього нам знадобиться допомога jQuery. Якщо у вас ще не підключена актуальна версія цієї популярної javscript бібліотеки, сміливо підключайте, додавши в кінець документа, перед тегом наступне:

<script src="http://code.jquery.com/jquery-latest.min.js" type="text/javascript">

І тут же слід за цим рядком, залишається підключити сам виконуючий плагін, завчасно упакований в окремий файл і поміщений в папочку з js.

<script src="js/script.js">

Хочете подивитися на js в розгорнутому вигляді? Будь ласка:

( function( $ ) {
$( document ).ready(function() {
$('#menu li.has-sub>a').on('click', function(){
$(this).removeAttr('href');
var element = $(this).parent('li');
if (element.hasClass('open')) {
element.removeClass('open');
element.find('li').removeClass('open');
element.find('ul').slideUp();
}
else {
element.addClass('open');
element.children('ul').slideDown();
element.siblings('li').children('ul').slideUp();
element.siblings('li').removeClass('open');
element.siblings('li').find('li').removeClass('open');
element.siblings('li').find('ul').slideUp();
}
});
$('#menu>ul>li.has-sub>a').append('');
(function getColor() {
var r, g, b;
var textColor = $('#menu').css('color');
textColor = textColor.slice(4);
r = textColor.slice(0, textColor.indexOf(','));
textColor = textColor.slice(textColor.indexOf(' ') + 1);
g = textColor.slice(0, textColor.indexOf(','));
textColor = textColor.slice(textColor.indexOf(' ') + 1);
b = textColor.slice(0, textColor.indexOf(')'));
var l = rgbToHsl(r, g, b);
if (l > 0.7) {
$('#menu>ul>li>a').css('text-shadow', '0 1px 1px rgba(0, 0, 0, .35)');
$('#menu>ul>li>a>span').css('border-color', 'rgba(0, 0, 0, .35)');
}
else
{
$('#menu>ul>li>a').css('text-shadow', '0 1px 0 rgba(255, 255, 255, .35)');
$('#menu>ul>li>a>span').css('border-color', 'rgba(255, 255, 255, .35)');
}
})();
function rgbToHsl(r, g, b) {
r /= 255, g /= 255, b /= 255;
var max = Math.max(r, g, b), min = Math.min(r, g, b);
var h, s, l = (max + min) / 2;
if(max == min){
h = s = 0;
}
else {
var d = max - min;
s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
switch(max){
case r: h = (g - b) / d + (g < b ? 6 : 0); break;
case g: h = (b - r) / d + 2; break;
case b: h = (r - g) / d + 4; break;
}
h /= 6;
}
return l;
}
});

( function( $ ) {
$( document ).ready(function() {
$(‘#menu li.has-sub>a’).on(‘click’, function(){
$(this).removeAttr(‘href’);
var element = $(this).parent(‘li’);
if (element.hasClass(‘open’)) {
element.removeClass(‘open’);
element.find(‘li’).removeClass(‘open’);
element.find(‘ul’).slideUp();
}
else {
element.addClass(‘open’);
element.children(‘ul’).slideDown();
element.siblings(‘li’).children(‘ul’).slideUp();
element.siblings(‘li’).removeClass(‘open’);
element.siblings(‘li’).find(‘li’).removeClass(‘open’);
element.siblings(‘li’).find(‘ul’).slideUp();
}
});$(‘#menu>ul>li.has-sub>a’).append(‘‘);(function getColor() {
var r, g, b;
var textColor = $(‘#menu’).css(‘color’);
textColor = textColor.slice(4);
r = textColor.slice(0, textColor.indexOf(‘,’));
textColor = textColor.slice(textColor.indexOf(‘ ‘) + 1);
g = textColor.slice(0, textColor.indexOf(‘,’));
textColor = textColor.slice(textColor.indexOf(‘ ‘) + 1);
b = textColor.slice(0, textColor.indexOf(‘)’));
var l = rgbToHsl(r, g, b);
if (l > 0.7) {
$(‘#menu>ul>li>a’).css(‘text-shadow’, ‘0 1px 1px rgba(0, 0, 0, .35)’);
$(‘#menu>ul>li>a>span’).css(‘border-color’, ‘rgba(0, 0, 0, .35)’);
}
else
{
$(‘#menu>ul>li>a’).css(‘text-shadow’, ‘0 1px 0 rgba(255, 255, 255, .35)’);
$(‘#menu>ul>li>a>span’).css(‘border-color’, ‘rgba(255, 255, 255, .35)’);
}
})();function rgbToHsl(r, g, b) {
r /= 255, g /= 255, b /= 255;
var max = Math.max(r, g, b), min = Math.min(r, g, b);
var h, s, l = (max min) / 2;if(max == min){
h = s = 0;
}
else {
var d = max – min;
s = l > 0.5 ? d / (2 – max – min) : d / (max min);
switch(max){
case r: h = (g – b) / d + (g < b ? 6 : 0); break;
case g: h = (b – r) / d + 2; break;
case b: h = (r – g) / d + 4; break;
}
h /= 6;
}
return l;
}
});

Наявністю великої кількості параметрів плагін не блищить, але все то під що він заточений, виконує справно. При бажанні, ви зможете поекспериментувати з деякими значеннями, головне не перестаратися. )))

Ось тетерь вже точно все. Компактне меню в стилі «акордеон», повністю готове до роботи. Це був всього лише маленький приклад того, які горизонти і можливості відкривають нам сучасні веб-інструменти. А у зв’язці з невгамовною фантазією і величезним бажанням, можна творити, творити і творити…

З повагою, Андрій.

Удачі! Буду дуже вдячний, якщо поділитеся посиланням на запис у своїх соц. мережах: