Макет сайта с двумя фиксированными сайдбарами по краям окна
<!DOCTYPE html> <html lang="ru"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width,initial-scale=1"> <link rel="stylesheet" href="style.css"> <link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet"> <link rel="canonical" href="https://site.com"> <title>Title</title> <meta name="description" content="Description of the page content."> </head> <body> <header id="header"> <button id="button-left" onclick="navMainOpen()"><i class="material-icons md-light">apps</i></button> <a href="/" title="To main page"> <img src="logo.png" alt="Logo of the website" width="30" height="30"> <span>Site Name</span> <span id="subtitle">Short description of the website</span> </a> <button id="button-right" onclick="navSectionOpen()"><i class="material-icons md-light">menu</i></button> </header> <div id="main-overlay" onclick="navMainClose()"></div> <div id="section-overlay" onclick="navSectionClose()"></div> <nav id="main-sidebar" style="background:lightsteelblue;"> <p>Теория</p> <ul> <li><a href="#">Начала программирования</a></li> <li><a href="#">Функции</a></li> <li><a href="#">...</a></li> </ul> <p>Задачи по темам</p> <ul> <li><a href="#">Линейные алгоритмы</a></li> <li><a href="#">Условные операторы</a></li> <li>...</li> </ul> <p>...</p> </nav> <main style="background:#f0f0f0;"> <h1>Title of Article</h1> <p>Line 1</p><p>...</p> </main> <nav id="section-sidebar" style="background:lightgoldenrodyellow;"> <header class="center"> Задачи на массивы </header> <ul> <li><a href="#">Сумма и произведение элементов одномерного массива</a></li> <li><a href="#">Сумма положительных элементов массива</a></li> <li><a href="#">...</a></li> </ul> </nav> <footer style="background:lightskyblue;height:40px;text-align:center;padding-top:20px;">Flask.Website © 2025</footer> <script src="script.js"></script> </body> </html>
body { margin: 0; } #header { position: fixed; top: 0px; width: 100%; height: 48px; padding: 2px; background: dodgerblue; transition: top 0.3s ease 0s; text-align: center; } #header a { text-decoration: none; } #header span { font-size: 24px; color: white; } #header #subtitle { display: none; } #header img { padding-right: 5px; padding-top: 7px; vertical-align: -5px; } #button-right, #button-left { cursor: pointer; margin-top: 6px; width: 36px; height: 36px; font-size: 32px; background: white; border: none; } #button-right { float: right; margin-right: 10px; } #button-left { float: left; margin-left: 5px; } @media (min-width: 1351px) { #button-left, #button-right { display: none; } #header { text-align: left; padding: 0; width: 300px; height: 100px; } #header img { padding: 15px 10px 10px 30px; vertical-align: -15px; } #header #subtitle { display: block; font-size: 18px; padding-left: 30px; } }
На больших экранах заголовок имеет ширину левого сайдбара и окажется над ним. И на широких, и на узких экранах заголовку задается фиксированная позиция с помощью css-свойства position
. Однако на узких экранах заголовок будет исчезать при прокрутке вниз и появляться сразу при небольшой прокрутке вверх, отображая тем самым расположенные на нем кнопки, открывающие сайдбары. Такое поведение задается с помощью JS.
function checkMedia(media) { var header = document.getElementById("header"); var prevScrollpos = window.pageYOffset; window.onscroll = function() { var currentScrollPos = window.pageYOffset; if (prevScrollpos > currentScrollPos) { header.style.top = "0"; } else { if (media.matches) { header.style.top = "-95px"; } else { header.style.top = "0"; } } prevScrollpos = currentScrollPos; } } var m = window.matchMedia("(max-width: 1350px)"); checkMedia(m); m.addListener(checkMedia);
#main-sidebar { display: none; position: fixed; top: 0; bottom: 0; width: 300px; overflow: auto; } @media (min-width: 1351px) { #main-sidebar { display: block!important; top: 100px; } }
На широких экранах сверху делается отступ в ширину заголовка (100px).
#section-sidebar { display: none; position: fixed; top: 0; bottom: 0; right: 0; width: 300px; } #section-sidebar header { border-bottom: 1px solid lightgray; height: 50px; display: flex; justify-content: center; align-items: center; } #section-sidebar ul { position: fixed; top: 50px; bottom: 0px; overflow: auto; margin-top: 0; padding-top: 10px; } @media (min-width: 1351px) { #section-sidebar { display: block!important; } #section-sidebar header { height: 100px; font-size: 1.5em; } #section-sidebar ul { top: 100px; } }
В данном случае все немного сложнее, потому что внутри фиксированного сайдбара мы делаем фиксированный хэдер (заголовок меню). Он не будет исчезать при скроллинге меню, и правая панель будет похожа на левую.
Если раскрытие сайдбаров на узких экранах обеспечивается с помощью кнопок, то закрытие - с помощью "оверлеев".
#main-overlay, #section-overlay { display: none; position: fixed; width: 100%; height: 100%; background: rgba(0,0,0,0.5); }
function navMainOpen() { document.getElementById("main-sidebar").style.display = "block"; document.getElementById("main-overlay").style.display = "block"; } function navMainClose() { document.getElementById("main-sidebar").style.display = "none"; document.getElementById("main-overlay").style.display = "none"; } function navSectionOpen() { document.getElementById("section-sidebar").style.display = "block"; document.getElementById("section-overlay").style.display = "block"; } function navSectionClose() { document.getElementById("section-sidebar").style.display = "none"; document.getElementById("section-overlay").style.display = "none"; }
main
:main { padding: 55px 15px; } @media (min-width: 871px) { main { max-width: 840px; margin: 0 auto; } } @media (min-width: 1351px) { main { margin-left: 310px; margin-right: 310px; padding-top: 5px; } footer { margin-left: 300px; margin-right: 300px; } } @media (min-width: 1500px) { main { margin: 0 auto; } }
Основное содержимое начинается сразу у верха страницы. Поэтому на узких экранах мы должны сделать отступ сверху на высоту заголовка, так как там он растянут на всю ширину окна.
#main-sidebar p { margin-left: 20px; font-size: 1.2em; } #main-sidebar ul { list-style-type: none; line-height: 1.7em; } #main-sidebar a { color: darkblue; text-decoration: none; } #section-sidebar ul { padding-inline-start: 30px; } #section-sidebar ul li { padding-bottom: 15px; } #main-sidebar::-webkit-scrollbar-track { background: lightsteelblue; } #main-sidebar::-webkit-scrollbar-thumb { background: lightgrey; } #main-sidebar::-webkit-scrollbar-thumb:hover { background: lightgrey;} #main-sidebar::-webkit-scrollbar, #section-sidebar ul::-webkit-scrollbar { width: 7px; } #section-sidebar ul::-webkit-scrollbar-track { background: lightgoldenrodyellow;} #section-sidebar ul::-webkit-scrollbar-thumb { background: lightgray; } #section-sidebar ul::-webkit-scrollbar-thumb:hover { background: lightgray; }