Ever wanted to create a gorgeous accordion UI that feels premium without using heavy frameworks or libraries? Let's build one from scratch that’s responsive, elegant, and buttery smooth.
DEMO
See the Pen Fun & Funky School Notebook Accordion | Bounce Animation + Handwritten Style by Sohrab zia (@sohrabzia) on CodePen.
🧠 What We'll Cover
✅ Clean HTML structure
✅ CSS animations and transitions
✅ JavaScript for interaction
✅ Advanced UI touches like hover states, shadows, and responsive tweaks
✅ Bonus: Custom clip-path and handwriting-style content area
🔧 The HTML Structure
We start with a simple, semantic layout:
<div class="accordion-container"> <div class="accordion-item"> <button class="accordion-header"> Accordion Title 1 <i class="fa-solid fa-chevron-down icon"></i> </button> <div class="accordion-content"> <div class="accordion-body"> <p>This is the content for the first accordion.</p> </div> </div> </div> <!-- Add more items as needed --> </div>
🎨 The CSS Magic
We give this accordion some real flair — a mix of shadows, gradients, animations, and subtle hover effects:
Key Highlights:
- Smooth max-height transitions
- clip-path for a ribbon effect
- @keyframes for a "slide-up" bounce feel
- Handwritten font + paper-style lines for a whimsical twist
:root { --accordion-duration: 0.3s; --icon-rotate-open: 180deg; } /* Accordion Header */ .accordion-header { background: #f7d794; border-radius: 10px; padding: 15px 20px; font-weight: bold; cursor: pointer; transition: background var(--accordion-duration); box-shadow: 0 4px 6px rgba(0, 0, 0, 0.05); position: relative; } /* Decorative Ribbon */ .accordion-header:before { content: ""; position: absolute; top: -14px; right: 17px; width: 91px; height: 15px; background-color: #f7d794; clip-path: polygon(5% 0%, 95% 0%, 100% 100%, 0% 100%); transition: all 0.3s ease; }
🚀 The JavaScript That Powers It
Here's the JS logic that adds the open/close functionality and ensures only one accordion stays open:
document.addEventListener("DOMContentLoaded", () => { const headers = document.querySelectorAll(".accordion-header"); headers.forEach((header) => { header.addEventListener("click", () => { const openHeader = document.querySelector(".accordion-header.active"); const content = header.nextElementSibling; if (openHeader && openHeader !== header) { openHeader.classList.remove("active"); openHeader.nextElementSibling.style.maxHeight = null; } const isActive = header.classList.contains("active"); header.classList.toggle("active", !isActive); content.style.maxHeight = !isActive ? content.scrollHeight + "px" : null; }); }); });
📱 Responsive Design Ready
@media (max-width: 600px) { .accordion-header { font-size: 15px; padding: 12px 16px; } .accordion-content { padding: 0 16px; } }
💡 Pro Tips
Swap out the font with Google Fonts like 'Patrick Hand' for playful aesthetics.
Adjust the animation timing/distance to match your brand feel.
Replace icons with SVGs if you want more control.
🎁 Bonus: Style Variants You Can Add
Dark mode: Easily tweak with a few color variables.
FAQ style: Pre-load the first item open with a class.
Accordion inside cards: Wrap with .card for extra flair
Bonus Accordion
Top comments (0)