How to Create a Neumorphism Toggle Button with HTML and CSS

Aarzoo IslamAarzoo Islam
7 min read

Overview

In today's fast-paced digital world, user interface design plays a pivotal role in captivating user attention and enhancing user experience. One of the latest trends in UI design is neumorphism, a design style that combines skeuomorphism with minimalism to create visually appealing and user-friendly interfaces. In this tutorial, we'll explore how to create a neumorphic toggle button using HTML and CSS, perfect for adding a modern touch to your web projects.

Getting Started: Understanding Neumorphism

Before diving into the coding process, let's understand what neumorphism is and how it differs from other design styles.

Neumorphism, also known as soft UI, is a design trend that emerged as a response to the flat design trend. Unlike flat design, which focuses on minimalism and simplicity, neumorphism adds depth and realism to elements by using subtle shadows and highlights. The goal is to mimic the appearance of physical objects, creating a tactile and immersive user experience.

Setting Up the HTML Structure

To create our neumorphic toggle button, we'll start by setting up the HTML structure. This will include defining the container, toggle switch, and button elements.

<!DOCTYPE html>
<html lang="en">

<head>
    <!-- Character encoding for the HTML document -->
    <meta charset="UTF-8">
    <!-- Ensures proper rendering and touch zooming on mobile devices -->
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <!-- Link to the external stylesheet -->
    <link rel="stylesheet" href="style.css">
    <!-- Title of the webpage -->
    <title>Neumorphism Toggle Button</title>
</head>

<body>
    <!-- Main container for the toggle button -->
    <div class="container">
        <!-- Toggle switch label -->
        <label class="switch">
            <!-- Hidden checkbox to control the toggle state -->
            <input class="togglesw" type="checkbox" checked>
            <!-- Left indicator for the toggle button -->
            <div class="indicator left"></div>
            <!-- Right indicator for the toggle button -->
            <div class="indicator right"></div>
            <!-- Actual toggle button -->
            <div class="button"></div>
        </label>
    </div>
</body>

</html>

Styling with CSS

Now that we have our HTML structure in place, let's add styles to achieve the neumorphic effect. We'll use CSS to define the appearance of the toggle button, including shadows, gradients, and transitions.

/* Styling for the body to center content and set background */
body {
    display: flex;
    /* Enables flexbox layout */
    align-items: center;
    /* Vertically centers the content */
    justify-content: center;
    /* Horizontally centers the content */
    min-height: 100vh;
    /* Sets the minimum height to full viewport height */
    background-image: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
    /* Background gradient */
}

/* Container for the toggle switch with custom properties for styling */
.container {
    display: flex;
    /* Enables flexbox layout */
    align-items: center;
    /* Vertically centers the content */
    justify-content: center;
    /* Horizontally centers the content */
    --hue: 220deg;
    /* Base hue for colors */
    --width: 15rem;
    /* Width of the toggle switch */
    --accent-hue: 260deg;
    /* Accent hue for the left indicator */
    --duration: 0.6s;
    /* Duration for transitions */
    --easing: cubic-bezier(1, 0, 1, 1);
    /* Easing function for transitions */
}

/* Hides the checkbox element */
.togglesw {
    display: none;
}

/* Styling for the toggle switch */
.switch {
    --shadow-offset: calc(var(--width) / 20);
    /* Shadow offset calculation */
    position: relative;
    /* Positions elements relative to this container */
    cursor: pointer;
    /* Changes cursor to pointer on hover */
    display: flex;
    /* Enables flexbox layout */
    align-items: center;
    /* Vertically centers the content */
    width: var(--width);
    /* Sets the width */
    height: calc(var(--width) / 2.5);
    /* Sets the height */
    border-radius: var(--width);
    /* Makes the switch fully rounded */
    box-shadow: inset 10px 10px 10px hsl(var(--hue) 20% 80%),
        /* Inner shadow on the left */
        inset -10px -10px 10px hsl(var(--hue) 20% 93%);
    /* Inner shadow on the right */
}

/* Common styling for the indicators */
.indicator {
    content: '';
    position: absolute;
    /* Positions the element absolutely */
    width: 40%;
    /* Sets the width */
    height: 60%;
    /* Sets the height */
    transition: all var(--duration) var(--easing);
    /* Transition effects */
    box-shadow: inset 0 0 2px hsl(var(--hue) 20% 15% / 60%),
        /* Inner shadows for 3D effect */
        inset 0 0 3px 2px hsl(var(--hue) 20% 15% / 60%),
        inset 0 0 5px 2px hsl(var(--hue) 20% 45% / 60%);
}

/* Specific styling for the left indicator */
.indicator.left {
    --hue: var(--accent-hue);
    /* Uses accent hue */
    overflow: hidden;
    /* Hides overflow */
    left: 10%;
    /* Positions the left indicator */
    border-radius: 100px 0 0 100px;
    /* Rounds left side */
    background: linear-gradient(180deg,
            /* Gradient background */
            hsl(calc(var(--accent-hue) + 20deg) 95% 80%) 10%,
            hsl(calc(var(--accent-hue) + 20deg) 100% 60%) 30%,
            hsl(var(--accent-hue) 90% 50%) 60%,
            hsl(var(--accent-hue) 90% 60%) 75%,
            hsl(var(--accent-hue) 90% 50%));
}

/* Additional styling for the left indicator */
.indicator.left::after {
    content: '';
    position: absolute;
    /* Positions the element absolutely */
    opacity: 0.6;
    /* Sets opacity */
    width: 100%;
    /* Full width */
    height: 100%;
    /* Full height */
}

/* Specific styling for the right indicator */
.indicator.right {
    right: 10%;
    /* Positions the right indicator */
    border-radius: 0 100px 100px 0;
    /* Rounds right side */
    background-image: linear-gradient(180deg,
            /* Gradient background */
            hsl(var(--hue) 20% 95%),
            hsl(var(--hue) 20% 65%) 60%,
            hsl(var(--hue) 20% 70%) 70%,
            hsl(var(--hue) 20% 65%));
}

/* Styling for the toggle button */
.button {
    position: absolute;
    /* Positions the element absolutely */
    z-index: 1;
    /* Places the element on top */
    width: 55%;
    /* Sets the width */
    height: 80%;
    /* Sets the height */
    left: 5%;
    /* Initial position */
    border-radius: 100px;
    /* Fully rounds the button */
    background-image: linear-gradient(160deg,
            /* Gradient background */
            hsl(var(--hue) 20% 95%) 40%,
            hsl(var(--hue) 20% 65%) 70%);
    transition: all var(--duration) var(--easing);
    /* Transition effects */
    box-shadow: 2px 2px 3px hsl(var(--hue) 18% 50% / 80%),
        /* Shadows for 3D effect */
        2px 2px 6px hsl(var(--hue) 18% 50% / 40%),
        10px 20px 10px hsl(var(--hue) 18% 50% / 40%),
        20px 30px 30px hsl(var(--hue) 18% 50% / 60%);
}

/* Additional styling for the button */
.button::before,
.button::after {
    content: '';
    position: absolute;
    /* Positions the elements absolutely */
    top: 10%;
    /* Positions from the top */
    width: 41%;
    /* Sets the width */
    height: 80%;
    /* Sets the height */
    border-radius: 100%;
    /* Fully rounds the elements */
}

/* Specific styling for the button before element */
.button::before {
    left: 5%;
    /* Positions the element from the left */
    box-shadow: inset 1px 1px 2px hsl(var(--hue) 20% 85%);
    /* Inner shadow */
    background-image: linear-gradient(-50deg,
            /* Gradient background */
            hsl(var(--hue) 20% 95%) 20%,
            hsl(var(--hue) 20% 85%) 80%);
}

/* Specific styling for the button after element */
.button::after {
    right: 5%;
    /* Positions the element from the right */
    box-shadow: inset 1px 1px 3px hsl(var(--hue) 20% 70%);
    /* Inner shadow */
    background-image: linear-gradient(-50deg,
            /* Gradient background */
            hsl(var(--hue) 20% 95%) 20%,
            hsl(var(--hue) 20% 75%) 80%);
}

/* Moves the button when the checkbox is checked */
.togglesw:checked~.button {
    left: 40%;
    /* New position when checked */
}

/* Adds shadow to the indicators based on the checkbox state */
.togglesw:not(:checked)~.indicator.left,
.togglesw:checked~.indicator.right {
    box-shadow: inset 0 0 5px hsl(var(--hue) 20% 15% / 100%),
        /* Inner shadow effects */
        inset 20px 20px 10px hsl(var(--hue) 20% 15% / 100%),
        inset 20px 20px 15px hsl(var(--hue) 20% 45% / 100%);
}

Step-by-Step Explanation

Now, let's break down the key elements of our HTML and CSS code to understand how the neumorphic toggle button is created:

  1. HTML Structure: We begin by setting up the basic HTML structure, including the container, label, input checkbox, and button elements. The container holds the entire toggle button, while the label serves as the switch.

  2. CSS Styling: With CSS, we define the appearance of our toggle button. This includes setting the background color, dimensions, border radius, and box shadow to achieve the neumorphic effect. We use gradients and shadows to create depth and realism.

  3. Toggle Functionality: By utilizing the checkbox input's :checked pseudo-class, we can dynamically adjust the position and appearance of the button based on its state. When the checkbox is checked, the button moves to the right, simulating a toggled state.

  4. Transition Effects: To add smoothness to the toggle animation, we apply transition effects to the button and indicators. This ensures that the movement is gradual and visually appealing.

Conclusion

In this tutorial, we've learned how to create a neumorphic toggle button using HTML and CSS. By combining subtle shadows, gradients, and transitions, we've achieved a modern and stylish UI element that enhances user interaction. Feel free to customize the colors and dimensions to fit your project's aesthetic. Download the full source code from here to implement the neumorphic toggle button in your web projects.

If you found this tutorial helpful, consider supporting me so I can create more free prompts like this one. Your support means the world to me!

Keep coding, and stay creative! ๐Ÿš€

10
Subscribe to my newsletter

Read articles from Aarzoo Islam directly inside your inbox. Subscribe to the newsletter, and don't miss out.

Written by

Aarzoo Islam
Aarzoo Islam

Founder of AroNus ๐Ÿš€ | Full-stack web developer ๐Ÿ‘จ๐Ÿปโ€๐Ÿ’ป | Sharing web development tips and showcasing projects ๐Ÿ“‚ | Transforming ideas into digital realities ๐ŸŒŸ