How to convert the hamburger icon of navigation menu to X on click ?

The navigation menu is the most important section of a website. It helps in navigating through the website. Having a proper animation not only makes the website look good but also provides a user-friendly interface to the customer. Hence, this animation will make it possible to convert the three lines or the hamburger icon as it is frequently called, into an X upon click and vice versa.

The code will contain 3 different structures which will make it possible to apply this animation. The HTML body, CSS body, and JavaScript body.

Creating the structure: In this section, we will create a basic structure with the help of HTML. We will also add the font-awesome link to generate the lines to create the hamburger icon.

filter_none

edit
close

play_arrow

link
brightness_4
code

<!DOCTYPE html>
<html>
  
<head>
    <meta charset="UTF-8" />
    <meta name="viewport" content=
        "width=device-width" />
  
    <meta http-equiv="X-UA-Compatible"
            content="ie=edge" />
  
    <link rel="stylesheet" href=
  
    <title>
        Converting the hamburger
        icon to X and vice versa
    </title>
</head>
  
<body id="bg-img">
    <header>
        <div class="menu-btn">
            <div class="btn-line"></div>
            <div class="btn-line"></div>
            <div class="btn-line"></div>
        </div>
  
        <nav class="menu">
            <div class="menu-branding">
                <div class="portrait">
                    <img src=
                        alt="" />
                </div>
            </div>
  
            <ul class="menu-nav">
                <li class="nav-item current">
                    <a href="#" class="nav-link">
                        HOME</a>
                </li>
  
                <li class="nav-item">
                    <a href="#" class="nav-link">
                        ABOUT ME</a>
                </li>
  
                <li class="nav-item">
                    <a href="#" class="nav-link">
                        MY WORK</a>
                </li>
  
                <li class="nav-item">
                    <a href="#" class="nav-link">
                        CONTACT ME</a>
                </li>
            </ul>
        </nav>
    </header>
</body>
  
</html>

chevron_right


Designing the structure: In the previous section, we have created the basic structure of the hamburger icon. In this section, we will design the structure with the help of CSS.

filter_none

edit
close

play_arrow

link
brightness_4
code

<style>
    /* Styling the menu button */
    .menu-btn {
        position: absolute;
        z-index: 3;
        right: 35px;
        top: 35px;
        cursor: pointer;
        transition: all 0.5s ease-out;
    }
  
    /* Styling the hamburger lines */
    .menu-btn .btn-line {
        width: 28px;
        height: 3px;
        margin: 0 0 5px 0;
        background: black;
        transition: all 0.5s ease-out;
    }
  
    /* Adding tranform to the X */
    .menu-btn.close {
        transform: rotate(180deg);
    }
  
    /* Styling the three lines 
        to make it an X */
    .menu-btn.close .btn-line:nth-child(1) {
        transform: rotate(45deg) translate(5px, 5px);
    }
  
    .menu-btn.close .btn-line:nth-child(2) {
        opacity: 0;
    }
  
    .menu-btn.close .btn-line:nth-child(3) {
        transform: rotate(-45deg) translate(7px, -6px);
    }
  
    /* Styling the position of the menu icon */
    .menu {
        position: fixed;
        top: 0;
        width: 100%;
        opacity: 0.9;
        visibility: hidden;
    }
  
    .menu.show {
        visibility: visible;
    }
  
    /* Adding a transition delay to the
       4 items in the navigation menu */
    .nav-item:nth-child(1) {
        transition-delay: 0.1s;
    }
  
    .nav-item:nth-child(2) {
        transition-delay: 0.2s;
    }
  
    .nav-item:nth-child(3) {
        transition-delay: 0.3s;
    }
  
    .nav-item:nth-child(4) {
        transition-delay: 0.4s;
    }
</style>

chevron_right


Adding JavaScript: In this section, we will add the javascript which is necessary for us to animate all the three lines of the hamburger icon. It adds an EventListener to the icon. This EventListener toggles the menu that is to be displayed upon click and needs to be hidden upon click. It determines the state of the menu button, whether it is X state or the hamburger state.



filter_none

edit
close

play_arrow

link
brightness_4
code

<script>
    // select dom items
    const menuBtn = 
        document.querySelector(".menu-btn");
  
    const menu = 
        document.querySelector(".menu");
  
    const menuNav = 
        document.querySelector(".menu-nav");
  
    const menuBranding = 
        document.querySelector(".menu-branding");
  
    const navItems = 
        document.querySelectorAll(".nav-item");
  
    // Set the initial state of the menu
    let showMenu = false;
  
    menuBtn.addEventListener("click", toggleMenu);
  
    function toggleMenu() {
        if (!showMenu) {
            menuBtn.classList.add("close");
            menu.classList.add("show");
            menuNav.classList.add("show");
            menuBranding.classList.add("show");
            navItems.forEach((item) =>
                item.classList.add("show"));
  
            // Reset the menu state
            showMenu = true;
        } else {
            menuBtn.classList.remove("close");
            menu.classList.remove("show");
            menuNav.classList.remove("show");
            menuBranding.classList.remove("show");
            navItems.forEach((item) =>
                item.classList.remove("show"));
  
            // Reset the menu state
            showMenu = false;
        }
    }
</script>

chevron_right


Final solution: The final solution is the combination of the HTML, CSS, and the JavaScript codes to get the desired animation result.

filter_none

edit
close

play_arrow

link
brightness_4
code

<!DOCTYPE html>
<html>
  
<head>
    <meta charset="UTF-8" />
    <meta name="viewport" content=
            "width=device-width" />
  
    <meta http-equiv="X-UA-Compatible" 
            content="ie=edge" />
  
    <link rel="stylesheet" href=
  
    <title>
        Converting the hamburger icon
        to X and vice versa
    </title>
      
    <style>
        /* Styling the menu button */
        .menu-btn {
            position: absolute;
            z-index: 3;
            right: 35px;
            top: 35px;
            cursor: pointer;
            transition: all 0.5s ease-out;
        }
  
        /* Styling the hamburger lines */
        .menu-btn .btn-line {
            width: 28px;
            height: 3px;
            margin: 0 0 5px 0;
            background: black;
            transition: all 0.5s ease-out;
        }
  
        /* Adding tranform to the X */
        .menu-btn.close {
            transform: rotate(180deg);
        }
  
        /* Styling the three lines to make it an X */
        .menu-btn.close .btn-line:nth-child(1) {
            transform: rotate(45deg) translate(5px, 5px);
        }
  
        .menu-btn.close .btn-line:nth-child(2) {
            opacity: 0;
        }
  
        .menu-btn.close .btn-line:nth-child(3) {
            transform: rotate(-45deg) translate(7px, -6px);
        }
  
        /* Styling the position of the menu icon */
        .menu {
            position: fixed;
            top: 0;
            width: 100%;
            opacity: 0.9;
            visibility: hidden;
        }
  
        .menu.show {
            visibility: visible;
        }
  
        /* Adding a transition delay 
          to the 4 items in the 
          navigation menu */
        .nav-item:nth-child(1) {
            transition-delay: 0.1s;
        }
  
        .nav-item:nth-child(2) {
            transition-delay: 0.2s;
        }
  
        .nav-item:nth-child(3) {
            transition-delay: 0.3s;
        }
  
        .nav-item:nth-child(4) {
            transition-delay: 0.4s;
        }
    </style>
</head>
  
<body id="bg-img">
    <header>
        <div class="menu-btn">
            <div class="btn-line"></div>
            <div class="btn-line"></div>
            <div class="btn-line"></div>
        </div>
  
        <nav class="menu">
            <div class="menu-branding">
                <div class="portrait">
                    <img src=
                        alt="" />
                </div>
            </div>
  
            <ul class="menu-nav">
                <li class="nav-item current">
                    <a href="#" class="nav-link">
                        HOME
                    </a>
                </li>
  
                <li class="nav-item">
                    <a href="#" class="nav-link">
                        ABOUT ME
                    </a>
                </li>
  
                <li class="nav-item">
                    <a href="#" class="nav-link">
                        MY WORK
                    </a>
                </li>
  
                <li class="nav-item">
                    <a href="#" class="nav-link">
                        CONTACT ME
                    </a>
                </li>
            </ul>
        </nav>
    </header>
  
    <script>
        // Select dom items
        const menuBtn = 
            document.querySelector(".menu-btn");
  
        const menu = 
            document.querySelector(".menu");
  
        const menuNav = 
            document.querySelector(".menu-nav");
  
        const menuBranding = 
            document.querySelector(".menu-branding");
  
        const navItems = 
            document.querySelectorAll(".nav-item");
  
        // Set the initial state of the menu
        let showMenu = false;
  
        menuBtn.addEventListener("click", toggleMenu);
  
        function toggleMenu() {
            if (!showMenu) {
                menuBtn.classList.add("close");
                menu.classList.add("show");
                menuNav.classList.add("show");
                menuBranding.classList.add("show");
                navItems.forEach((item) =>
                    item.classList.add("show"));
  
                // Reset the menu state
                showMenu = true;
            } else {
                menuBtn.classList.remove("close");
                menu.classList.remove("show");
                menuNav.classList.remove("show");
                menuBranding.classList.remove("show");
                navItems.forEach((item) =>
                    item.classList.remove("show"));
  
                // Reset the menu state
                showMenu = false;
            }
        }
    </script>
</body>
  
</html>

chevron_right


Output:

full-stack-img




My Personal Notes arrow_drop_up

Check out this Author's contributed articles.

If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please Improve this article if you find anything incorrect by clicking on the "Improve Article" button below.