This JavaScript code provides an off-canvas menu functionality for your website. When a user clicks the navigation icon, the menu slides in from the right side. This feature is helpful for creating a clean and organized mobile-friendly navigation experience.
It offers a compact and user-friendly navigation solution. You can integrate this code on your website to implement an off-canvas menu, which is perfect for mobile and responsive designs.
How to Create Off Canvas Menu Using JavaScript
1. First of all, load the Normalize CSS and Google Fonts by adding the following CDN links into the head tag of your HTML document.
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/normalize/5.0.0/normalize.min.css"> <link rel='stylesheet' href='https://fonts.googleapis.com/css?family=Raleway|Spectral'>
2. After that, create the HTML structure for the off-canvas menu. Include a navigation icon and the menu content. For instance, create a div with a unique class for the navigation icon and a nav element for the menu content.
<div class="navicon" id="navicon"><span></span></div> <nav class="main-nav" id="main-nav" role="navigation"> <ul class="main-nav__list"> <li><a class="main-nav__link" href="#!0">Úvod</a></li> <li><a class="main-nav__link" href="#!0">Produkty</a></li> <li><a class="main-nav__link" href="#!0">Informácie</a></li> <li><a class="main-nav__link" href="#!0">Kontakt</a></li> <!--<li><a class="main-nav__link" href="#!0">Cart <span>(5)</span></a></li> --> </ul> <div class="main-nav__info"> <p>Aktuálne novinky o nových motívoch svadobných oznamení, pozvánok a etikiet, nájdete aj na týchto sociálnych sieťach:</p> </div> <div class="main-nav__social"> <a href="#!0" target="_blank"><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" width="64px" height="64px" viewBox="0 0 64 64"><path d="M64,12.2c-2.4,1-4.9,1.8-7.5,2.1c2.7-1.6,4.8-4.2,5.8-7.3c-2.5,1.5-5.3,2.6-8.3,3.2C51.5,7.6,48.1,6,44.3,6 c-7.3,0-13.1,5.9-13.1,13.1c0,1,0.1,2,0.3,3C20.6,21.6,10.9,16.3,4.5,8.4c-1.1,1.9-1.8,4.2-1.8,6.6c0,4.6,2.3,8.6,5.8,10.9 c-2.2-0.1-4.2-0.7-5.9-1.6c0,0.1,0,0.1,0,0.2c0,6.4,4.5,11.7,10.5,12.9c-1.1,0.3-2.3,0.5-3.5,0.5c-0.8,0-1.7-0.1-2.5-0.2 c1.7,5.2,6.5,9,12.3,9.1c-4.5,3.5-10.2,5.6-16.3,5.6c-1.1,0-2.1-0.1-3.1-0.2C5.8,55.8,12.7,58,20.1,58c24.2,0,37.4-20,37.4-37.4 c0-0.6,0-1.1,0-1.7C60,17.1,62.2,14.8,64,12.2z"></path></svg></a> <a href="#!0" target="_blank"><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" width="64px" height="64px" viewBox="0 0 64 64"><path d="M32,5.766c8.544,0,9.556,0.033,12.931,0.187c3.642,0.166,7.021,0.895,9.621,3.496 c2.6,2.6,3.329,5.979,3.496,9.621c0.154,3.374,0.187,4.386,0.187,12.931s-0.033,9.556-0.187,12.931 c-0.166,3.642-0.895,7.021-3.496,9.621c-2.6,2.6-5.98,3.329-9.621,3.496c-3.374,0.154-4.386,0.187-12.931,0.187 s-9.557-0.033-12.931-0.187c-3.642-0.166-7.021-0.895-9.621-3.496c-2.6-2.6-3.329-5.979-3.496-9.621 C5.798,41.556,5.766,40.544,5.766,32s0.033-9.556,0.187-12.931c0.166-3.642,0.895-7.021,3.496-9.621 c2.6-2.6,5.979-3.329,9.621-3.496C22.444,5.798,23.456,5.766,32,5.766 M32,0c-8.691,0-9.78,0.037-13.194,0.193 c-5.2,0.237-9.768,1.511-13.436,5.178C1.705,9.037,0.43,13.604,0.193,18.806C0.037,22.22,0,23.309,0,32 c0,8.691,0.037,9.78,0.193,13.194c0.237,5.2,1.511,9.768,5.178,13.436c3.666,3.666,8.234,4.941,13.436,5.178 C22.22,63.963,23.309,64,32,64s9.78-0.037,13.194-0.193c5.199-0.237,9.768-1.511,13.436-5.178c3.666-3.666,4.941-8.234,5.178-13.436 C63.963,41.78,64,40.691,64,32s-0.037-9.78-0.193-13.194c-0.237-5.2-1.511-9.768-5.178-13.436 c-3.666-3.666-8.234-4.941-13.436-5.178C41.78,0.037,40.691,0,32,0L32,0z"></path><path d="M32,15.568c-9.075,0-16.432,7.357-16.432,16.432c0,9.075,7.357,16.432,16.432,16.432 S48.432,41.075,48.432,32C48.432,22.925,41.075,15.568,32,15.568z M32,42.667c-5.891,0-10.667-4.776-10.667-10.667 c0-5.891,4.776-10.667,10.667-10.667c5.891,0,10.667,4.776,10.667,10.667C42.667,37.891,37.891,42.667,32,42.667z"></path><circle cx="49.082" cy="14.918" r="3.84"></circle></svg></a> </div> <ul class="main-nav__legal"> <li><a class="main-nav__link" href="#!0">FAQ & Shipping</a></li> <li><a class="main-nav__link" href="#!0">Obchodné podmienky</li> </ul> </nav> <div class="overlay"></div>
3. Now, utilize CSS to style the off-canvas menu. Apply styles to hide the menu off-screen initially and to manage its appearance and animations. Use classes like .main-nav
, .navicon
, and .overlay
to structure and style your elements. These classes will handle animations, transitions, and positioning.
.squares { fill: none !important; } .is-hidden { display: none !important; visibility: hidden !important; } .visuallyhidden { position: absolute !important; clip: rect(0 0 0 0); -webkit-clip-path: inset(50%); clip-path: inset(50%); margin: -1px !important; padding: 0 !important; width: 1px !important; height: 1px !important; border: 0 !important; overflow: hidden; white-space: nowrap; } .visuallyhidden.is-focusable:active, .visuallyhidden.is-focusable:focus { position: static; clip: auto; -webkit-clip-path: none; clip-path: none; margin: 0; width: auto; height: auto; overflow: visible; white-space: inherit; } .is-invisible { visibility: hidden; } body{ font-family: -apple-system, BlinkMacSystemFont, "avenir next", avenir, "Segoe UI", "lucida grande", "helvetica neue", helvetica, "Fira Sans", roboto, noto, "Droid Sans", cantarell, oxygen, ubuntu, "franklin gothic medium", "century gothic", "Liberation Sans", sans-serif; font-size: 1rem; font-weight: 400; line-height: 1.5; text-rendering: optimizeLegibility; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; font-smoothing: antialiased; box-sizing: border-box; position: relative; } *, *:after, *:before { box-sizing: inherit; } html, body { margin: 0; padding: 0; width: 100%; } img { display: block; width: 100%; height: auto; border: 0; } figure { margin: 0; } .navicon { overflow: auto; position: absolute; top: 1rem; right: 1rem; width: 2.25rem; height: 2.25rem; border-radius: 0.25rem; background-color: whitesmoke; z-index: 10; transition: all 680ms; } .navicon:hover { cursor: pointer; background-color: rgba(0, 0, 0, 0.05); } .navicon span { position: relative; margin-top: 6.75px; margin-bottom: 6.75px; -webkit-user-select: none; -moz-user-select: none; -ms-user-select: none; user-select: none; position: absolute; top: 50%; left: 50%; margin-top: -1.125px; transform: translateX(-50%); } .navicon span, .navicon span::before, .navicon span::after { display: block; width: 1.5rem; height: 2.25px; background-color: #767676; outline: 1px solid transparent; transition-property: background-color, transform; transition-duration: 0.34s; } .navicon span::before, .navicon span::after { position: absolute; content: ""; } .navicon span::before { top: -6.75px; } .navicon span::after { top: 6.75px; } .js_is-active { background-color: crimson; } .js_is-active:hover { background-color: crimson; } .js_is-active span { background-color: transparent; } .js_is-active span::before { transform: translateY(6.75px) rotate(45deg); } .js_is-active span::after { transform: translateY(-6.75px) rotate(-45deg); } .js_is-active span::before, .js_is-active span::after { background-color: #fff; } .main-nav { z-index: 9; position: fixed; top: 0; right: 0; width: 100%; max-width: 515px; height: 100%; padding: 4rem 4rem 1rem 4rem; overflow-y: auto; background-color: #2a2a2a; transform: translateX(100%); transition: transform 0.55s cubic-bezier(0.785, 0.135, 0.15, 0.86); } .main-nav__list li { opacity: 0; transform: translateX(4rem); transition: all 0.3s ease; } .main-nav__link { display: block; padding: 1rem 0; color: #fff; font-family: "Raleway", sans-serif; font-size: 1.5rem; font-weight: 600; letter-spacing: 0.25rem; text-decoration: none; text-transform: uppercase; transition: all 0.3s ease; } .main-nav__link:hover { color: #b7ac7f; } .main-nav__link span { color: #b7ac7f; } .main-nav__info { opacity: 0; margin: 1rem 0 2rem; color: #fff; font-family: "Spectral", serif; font-size: 1.05rem; letter-spacing: 0.0625rem; transform: translateY(30px); transition: all 0.4s ease; } .main-nav__social { opacity: 0; overflow: hidden; position: relative; margin-top: 2rem; padding-bottom: 2rem; transform: translateY(2rem); transition: all 0.4s ease; } .main-nav__social::after { content: ""; position: absolute; bottom: 0; left: -100%; width: 100%; height: 0.125rem; background-color: #b7ac7f; } .main-nav__social a { display: inline-block; width: 2rem; height: 2rem; } .main-nav__social a:not(:first-of-type) { margin-left: 2rem; } .main-nav__social a:hover path, .main-nav__social a:hover circle { fill: #b7ac7f; } .main-nav__social svg { width: 100%; height: 100%; } .main-nav__social svg path, .main-nav__social svg circle { fill: #fff; transition: all 0.3s ease; } .main-nav__legal { opacity: 0; margin-top: 2rem; transform: translateY(2rem); transition: all 0.4s ease; } .main-nav__legal li a { font-size: 0.9rem; transition: all 0.3s ease; } .main-nav__legal li a:hover { color: #b7ac7f; } .overlay { z-index: 1; opacity: 0; visibility: hidden; position: fixed; top: 0; right: 0; bottom: 0; left: 0; width: 100%; height: 100%; background-color: rgba(42, 42, 42, 0.75); transition: all 0.3s ease-in-out; } .js_show-menu { transform: translateX(0); } .js_show-menu .main-nav__list li { transform: translateX(0); opacity: 1; } .js_show-menu .main-nav__list li:nth-child(1) { transition-delay: 0.15s; } .js_show-menu .main-nav__list li:nth-child(2) { transition-delay: 0.3s; } .js_show-menu .main-nav__list li:nth-child(3) { transition-delay: 0.45s; } .js_show-menu .main-nav__list li:nth-child(4) { transition-delay: 0.6s; } .js_show-menu .main-nav__list li:nth-child(5) { transition-delay: 0.75s; } .js_show-menu .main-nav__list li:nth-child(6) { transition-delay: 0.9s; } .js_show-menu .main-nav__list li:nth-child(7) { transition-delay: 1.05s; } .js_show-menu .main-nav__list li:nth-child(8) { transition-delay: 1.2s; } .js_show-menu .main-nav__list li:nth-child(9) { transition-delay: 1.35s; } .js_show-menu .main-nav__list li:nth-child(10) { transition-delay: 1.5s; } .js_show-menu .main-nav__list li:nth-child(11) { transition-delay: 1.65s; } .js_show-menu .main-nav__list li:nth-child(12) { transition-delay: 1.8s; } .js_show-menu .main-nav__list li:nth-child(13) { transition-delay: 1.95s; } .js_show-menu .main-nav__list li:nth-child(14) { transition-delay: 2.1s; } .js_show-menu .main-nav__list li:nth-child(15) { transition-delay: 2.25s; } .js_show-menu .main-nav__list li:nth-child(16) { transition-delay: 2.4s; } .js_show-menu .main-nav__list li:nth-child(17) { transition-delay: 2.55s; } .js_show-menu .main-nav__list li:nth-child(18) { transition-delay: 2.7s; } .js_show-menu .main-nav__list li:nth-child(19) { transition-delay: 2.85s; } .js_show-menu .main-nav__list li:nth-child(20) { transition-delay: 3s; } .js_show-menu .main-nav__info, .js_show-menu .main-nav__social, .js_show-menu .main-nav__legal { opacity: 1; transform: translateY(0); transition-delay: 0.85s; } .js_show-menu .main-nav__social::after { transform: translateX(100%); transition-property: transform; transition-duration: 340ms; transition-timing-function: ease-in; transition-delay: 0.95s; } .js_show-overlay { opacity: 0.8; visibility: visible; } ul { margin: 0; padding: 0; list-style-type: none; } p { margin: 0; }
4. Finally, implement JavaScript functionalities for toggling the menu. The following code includes functions for adding, removing, and toggling classes. When the navigation icon is clicked, these functions are used to display or hide the menu by adding or removing specific classes.
// jQuery-style functions in pure JS // hasClass, addClass, removeClass, toggleClass // @author: Todd Motto // @link: http://bit.ly/pure-js-jquery-style-functions // @link: https://toddmotto.com/labs/reusable-js/ // hasClass function hasClass(elem, className) { return new RegExp(' ' + className + ' ').test(' ' + elem.className + ' '); } // addClass function addClass(elem, className) { if (!hasClass(elem, className)) { elem.className += ' ' + className; } } // removeClass function removeClass(elem, className) { var newClass = ' ' + elem.className.replace( /[\t\r\n]/g, ' ') + ' '; if (hasClass(elem, className)) { while (newClass.indexOf(' ' + className + ' ') >= 0 ) { newClass = newClass.replace(' ' + className + ' ', ' '); } elem.className = newClass.replace(/^\s+|\s+$/g, ''); } } // toggleClass function toggleClass(elem, className) { var newClass = ' ' + elem.className.replace( /[\t\r\n]/g, " " ) + ' '; if (hasClass(elem, className)) { while (newClass.indexOf(" " + className + " ") >= 0 ) { newClass = newClass.replace( " " + className + " " , " " ); } elem.className = newClass.replace(/^\s+|\s+$/g, ''); } else { elem.className += ' ' + className; } } //document.getElementById('navicon').onclick = function() { //toggleClass(this, 'js_is-active'); //} var menu = document.querySelector('.main-nav'), navicon = document.querySelector('.navicon'), overlay = document.querySelector('.overlay'); navicon.onclick = function() { toggleClass(this, 'js_is-active'); toggleClass(menu, 'js_show-menu'); toggleClass(overlay, 'js_show-overlay'); }; overlay.onclick = function() { removeClass(navicon, 'js_is-active'); removeClass(menu, 'js_show-menu'); removeClass(this, 'js_show-overlay'); }
That’s all! hopefully, you have successfully created the Off-Canvas Menu Using JavaScript. If you have any questions or suggestions, feel free to comment below.
Similar Code Snippets:
I code and create web elements for amazing people around the world. I like work with new people. New people new Experiences.
I truly enjoy what I’m doing, which makes me more passionate about web development and coding. I am always ready to do challenging tasks whether it is about creating a custom CMS from scratch or customizing an existing system.
This is a great tutorial! I’m going to try it out.