Приховане меню на чистому CSS

19

Від автора: Гамбургер-меню, висувне меню, off-canvas меню: як би цей різновид меню не називали, приховування основної навігації на сайті стає шаблоном, які використовуються повсюдно в чуйну веб-дизайні. Все більше і більше сайтів використовують зафіксовану іконку, при натисканні на яку весь сайт зсувається в сторону, щоб відобразити приховане меню.

Незважаючи на те, що існує величезна кількість створених для цього jQuery-плагінів, це досить легко можна реалізувати і зовсім без використання JavaScript. В даній статті розглянуто простий варіант створення прихованого меню і ефекту висування з допомогою одного CSS.

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

Ось демо-приклад на сайті CodePen, показує кінцевий результат:

Почнемо з HTML

Розмітка для прихованого меню буде трохи відрізнятися від варіанту для стандартного меню навігації. Замість того, щоб помістити меню всередині шапки сайту (header), ми помістимо його відразу після відкриваючого тега body. Базова структура виглядає так:

  • Головна
  • Портфоліо
  • Про нас
  • Блог
  • Контакти

Як бачите, розмітка нашого сайту складається з трьох основних елементів: навігація, чекбокс (checkbox) і парний тег label, а також безпосередньо контент сайту. Тут варто відзначити кілька моментів:

Розмітка навігації розміщується в коді в першу чергу, т. к. навігації знаходиться позаду всіх інших елементів сайту. Для створення навігації ви можете використовувати будь-які HTML-теги. В даному випадку я використовую звичний ненумерованний список.

Тригером для висунення нашого меню послужить тег input типу checkbox і тег label. Зазвичай тег label розташовується перед тегом input або тег input обертається тегом label. Але в даному випадку тег input має йти безпосередньо перед тегом label. І далі, при додаванні CSS-стилів, ми побачимо чому.

Всі інші елементи сайту повинні бути обгорнуті в окремий тег div. Це необхідно зробити для того, щоб при відкритті меню все інше вміст з’їжджало трохи за межі екрану, щоб показати приховані елементи навігації.

Тепер, коли у нас є базова структура HTML, ми можемо зайнятися зовнішнім виглядом нашого меню!

CSS-стилі для пунктів меню

Давайте почнемо з додавання стилів для самого меню і його пунктів. Насамперед, нам необхідно переконатися в тому, що наше меню знаходиться під вмістом сторінки і залишається на місці, коли користувач прокручує сторінку:

.navigation {
list-style: none;
background: #111;
width: 100%;
height: 100%;
position: fixed;
top: 0;
right: 0;
bottom: 0;
left: 0;
z-index: 0;
}

Далі, я додав трохи стилів для того щоб наша навігація виглядала привабливіше (фонові кольори, межі, градієнти і т. д.). Не буду наводити тут цей код, ви можете подивитися, як саме я це зробив, в демо-прикладі. Тепер у нас є кілька симпатичних пунктів меню, але в цілому це зовсім не здорово, т. к. наш контент розташувався прямо на нашому меню. Давайте додамо стилів, щоб заховати меню до потрібного моменту.

CSS-стилі для «обгортки» сайту

Для початку, давайте переконаємося в тому, що вміст сайту повністю приховує наше меню. На цьому етапі можна додати кілька абзаців з «lorem ipsum» до нашого елементу з класом .site-wrap, якщо ви ще не додали жодного контенту.

.site-wrap {
min-width: 100%;
min-height: 100%;
background-color: #fff;
position: relative;
top: 0;
bottom: 100%;
left: 0;
z-index: 1;
}

Варто зауважити, що ми зобов’язані вказати фон для елемента з класом .site-wrap, інакше меню буде проглядатися крізь контент. Ви можете, звичайно, встановити будь-який фон, який самі захочете. Особисто я використовував наступний:

.site-wrap {
/* … попередні стилі знаходяться тут … */
padding: 4em;
background-image: linear-gradient(135deg,
rgb(254,255,255) 0%,
rgb(221,241,249) 35%,
rgb(160,216,239) 100%);
background-size: 200%;
}

CSS-стилі для тригера меню

Наступним кроком буде додавання стилів для зміни зовнішнього вигляду тригера меню з звичайного чекбокса на класичну іконку «гамбургер», яку ми всі знаємо і любимо. Спочатку, давайте сховаємо сам чекбокс.

.nav-trigger {
position: absolute;
clip: rect(0, 0, 0, 0);
}

Примітка редактора: спочатку, в даному коді використовувалося властивість display: block разом із зазначенням нульового значення ширини та висоти самого чекбокса, щоб зробити його невидимим, але доступним (активним). Але виявилося, що таке поєднання стилів в операційній системі iOS призводило до збою в роботі браузера і його закриття, кожен раз, коли меню відкривалося. Я змінив цю техніку і став використовувати замість цього властивість clip, яка, схоже, має такий же рівень доступності.

Отже, ми ховаємо чекбокс, використовуючи властивість clip, яка вимагає застосування властивості position: absolute для заданого елемента. Тепер ми задаємо стилі для елемента label:

label[for=»nav-trigger»] {
position: fixed;
top: 15px;
left: 15px;
z-index: 2;
}

Насамперед, ми задаємо властивість position: fixed, щоб елемент залишався на колишньому місці при прокручуванні сторінки користувачем. Властивості top і left визначають, як далеко від краю вікна браузера буде знаходитися іконка. Ми також повинні переконатися в тому, що значення для властивості z-index тригера вище хоча б на одиницю, ніж значення цього властивості елемента з класом .site-wrap. Потім, ми додаємо ще стилів для того, щоб зробити з елемента label іконку «гамбургер».

label[for=»nav-trigger»] {
/* … попередні стилі знаходяться тут … */
width: 30px;
height: 30px;
cursor: pointer;
background-image: url(«data:image/svg+xml;utf8,»);
background-size: contain;
}

Я використовував в якості фонового зображення вбудований елемент SVG, але ви можете використовувати будь-яку іншу іконку, включаючи використання псевдо-елементів :before :after, щоб переробити іконку «гамбургер» на чистому CSS. Зверніть увагу, що я також додав властивість cursor: pointer;, щоб візуально виділити іконку при наведенні.

CSS-стилі, щоб тригер став активним

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

.nav-trigger:checked + label {
left: 215px;
}
.nav-trigger:checked ~ .site-wrap {
left: 200px;
box-shadow: 0 0 5px 5px rgba(0,0,0,0.5);
}

Друга частина з вищенаведеного блоку зі стилями гарантує нам те, що «обгортка» сайту разом з вмістом буде відсунута на 200 пікселів. Я також додав тінь (властивість box-shadow) для «обгортки» сайту, що надасть додаткове відчуття того, що вона знаходиться зверху меню.

Перший селектор (.nav-trigger:checked + label) контролює розташування тригера при відкритті меню. Вам потрібно буде додати число, яке ми використовували раніше для label[for=»nav-trigger»], до того значення, яке відповідає за те, на яку відстань «обгортка» сайту буде відсуватися. В даному випадку це: 15px + 200px = 215px.

Ось коли стає важливим порядок слідування елементів тригера в коді. Другий селектор використовує символ ~ для управління спорідненими елементами, щоб вказати на елемент з класом .site-wrap, коли елемент з класом .nav-trigger буде активним. Порядок проходження в коді тега input типу checkbox тут не так важливий.

Однак, ми повинні вказати і на елемент з класом .site-wrap і на наш тег label, грунтуючись на тому, буде наш чекбокс активним чи ні. Для цього ми використовуємо + (селектор сусідніх елементів), щоб вказати на елемент label, який слідує за активним чекбоксів. Якби ми спочатку вказали тег label, тоді у нас би не було ніякої можливості пересувати його разом з «обгорткою» сайту при активації тригера.

В якості завершального штриха ми можемо додати CSS-перехід (transition) і для тригера і для «обгортки» сайту, щоб відкриття нашого меню супроводжувалося плавною анімацією. Тільки переконайтеся, що ви вказали в вашому варіанті необхідні вендорные префікси або використовували щось на зразок плагіна Autoprefixer.

.nav-trigger + label .site-wrap {
transition: left 0.2 s;
}

Один останній момент: використовуйте властивість overflow, щоб уникнути виходу контенту в елементі body за межі вікна перегляду по осі x. Якщо ви цього не зробите, тоді у користувачів з’явиться горизонтальна смуга прокручування при відкритті меню.

body {
overflow-x: hidden;
}

Кінцевий результат

От і все! Ми успішно створили ковзне приховане меню без використання JavaScript. І знову даю посилання на демо-приклад на сайті CodePen, щоб продемонструвати вам кінцевий результат:

Тепер, коли ви знаєте, як це робиться, не соромтеся експериментувати з цією ідеєю. Створити меню, яке буде висуватися праворуч, або ж зробіть сайт з двома меню (ліворуч і праворуч).
Мені б дуже хотілося побачити, що у вас вийшло, тому поділіться посиланням на сайт CodePen з вашим прикладом в коментарях, або посилання на інші приклади прихованого меню на чистому CSS.