webdevpuneet.com

Collapsible Sidebar — Free HTML CSS JS Icon-Only Toggle Sidebar Snippet

Collapsible Sidebar · Layouts · Plain HTML, CSS & JS · Live preview

CategoryLayouts

Copy & paste

Source Code

<div class="app-shell">
  <aside class="sidebar" id="sidebar">
    <div class="sidebar-header">
      <span class="logo-dot"></span>
      <span class="logo-text">Acme</span>
      <button class="collapse-btn" id="collapseBtn" onclick="toggleSidebar()" aria-label="Collapse sidebar" aria-expanded="true">
        <svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M15 18l-6-6 6-6"/></svg>
      </button>
    </div>
    <nav class="nav-list">
      <a href="#" class="nav-item active"><span class="nav-icon">D</span><span class="nav-label">Dashboard</span></a>
      <a href="#" class="nav-item"><span class="nav-icon">P</span><span class="nav-label">Projects</span></a>
      <a href="#" class="nav-item"><span class="nav-icon">T</span><span class="nav-label">Team</span></a>
      <a href="#" class="nav-item"><span class="nav-icon">S</span><span class="nav-label">Settings</span></a>
    </nav>
  </aside>
  <main class="main-content">
    <h3>Main Content Area</h3>
    <p>Toggle the sidebar using the arrow button in its header.</p>
  </main>
</div>

Extend with AI

Take This Snippet Further With AI

The AI prompt for this one is for Patreon supporters ($3 a month, 7 days free), along with a site with no ads. Supporters enter the passcode once and it is remembered in this browser.

· Become a supporter

What's included

Features

Single .collapsed class toggle drives the entire width animation and icon-only state
Explicit pixel widths on both states so the CSS width transition animates smoothly
Labels fade via opacity before their space collapses, avoiding an abrupt text pop
Toggle button chevron rotates 180 degrees to indicate direction using one SVG asset
aria-expanded and aria-label update dynamically to reflect current state for screen readers
Active nav item highlighted with a solid background and lightened icon tile
Sidebar and icon tiles both use flex-shrink: 0 to avoid squeezing during the transition
Ready to persist the collapsed preference via localStorage with one added line

About this UI Snippet

Collapsible Sidebar — HTML, CSS & JavaScript Icon Rail Toggle

Screenshot of the Collapsible Sidebar snippet rendered live

Dashboards and admin panels almost always need a navigation sidebar, and power users almost always want the option to shrink it down once they've learned the icons and want more room for content. This snippet implements the classic "icon-only rail" collapse pattern used by tools like VS Code and Notion, built with a single boolean class toggle and a CSS width transition.

How the width animation works

The .sidebar has an explicit width: 220px and a transition: width 0.25s ease. Toggling the .collapsed class swaps that to width: 64px — just enough room for the icon column. Because both states are explicit pixel widths (not auto), the browser can smoothly animate between them; animating to/from width: auto is not reliably transitionable in CSS, which is a common trap when building this pattern from scratch.

How labels disappear without causing layout jumps

Simply hiding the .nav-label and .logo-text elements with display: none would make them disappear instantly, out of sync with the slower width animation, which looks broken. Instead, both fade via opacity (a separate, faster 0.15s transition) *and* collapse via width: 0; overflow: hidden, so the text visually fades away first and its space collapses in sync with the sidebar's own shrink, rather than the text abruptly vanishing or wrapping awkwardly mid-animation.

How the toggle button flips

The collapse button's chevron icon is rotated 180 degrees via transform: rotate(180deg) when .collapsed is active, which turns a "point left" icon into a "point right" icon using the same SVG — no separate icon asset needed for the two directions.

Accessibility handling

toggleSidebar() updates both aria-expanded and aria-label on the toggle button every time it's clicked, so assistive technology always announces the sidebar's current state and the action the button will perform next ("Expand sidebar" vs. "Collapse sidebar") rather than a static, potentially stale label.

Step by step

How to Use

  1. 1
    Load the snippetClick "Collapsible Sidebar" in the sidebar Library tab to load the app shell layout.
  2. 2
    Toggle the sidebarClick the arrow button in the sidebar header in the preview to collapse and expand it.
  3. 3
    Adjust the widthsChange the 220px and 64px values on .sidebar and .sidebar.collapsed in the CSS panel to fit your icon size.
  4. 4
    Add navigation itemsCopy a .nav-item anchor in the HTML panel and update its icon letter/label text.
  5. 5
    Persist the collapsed stateStore the collapsed boolean in localStorage inside toggleSidebar and read it back on page load to remember the user's preference.
  6. 6
    Export and saveExport as HTML/JSX/Tailwind or click "Save as" to reuse this shell across projects.

Real-world uses

Common Use Cases

Admin dashboards and internal tools
Give power users more horizontal room for tables and charts by collapsing the nav to icons only.
Developer tool layouts
Mimic the VS Code / IDE-style collapsible activity bar pattern for a code-adjacent product.
SaaS app shells
Use as the base navigation shell for a multi-page SaaS product, wiring each nav-item href to a real route.
Learn width-transition animation pitfalls
See why explicit pixel widths (not width:auto) on both states are required for a smooth CSS transition.
Accessible collapse/expand toggles
Study how aria-expanded and aria-label should update dynamically rather than staying static across state changes.
Mobile-adaptive navigation
Extend the collapsed state to auto-trigger below a breakpoint, giving mobile users an icon rail by default.
Related: CSS light-dark() Theme Demo
See the CSS light-dark() Theme Demo for a related layouts pattern worth pairing with this one.

Got questions?

Frequently Asked Questions

CSS transitions cannot reliably animate to or from width: auto because the browser cannot interpolate an unknown target size. Using explicit values like 220px and 64px on both states lets the transition animate smoothly between two known numbers.

display: none changes instantly with no animation, which would make the text disappear abruptly out of sync with the slower sidebar width transition. Fading opacity first, then collapsing width, keeps the whole collapse feeling like one cohesive animation.

Inside toggleSidebar, save the new collapsed state to localStorage (e.g. localStorage.setItem('sidebarCollapsed', collapsed)). On page load, read that value and apply the .collapsed class immediately, before the user interacts with the toggle.

Copy an existing .nav-item anchor element inside .nav-list, update its icon letter (or swap in an SVG) and its .nav-label text, and update the href to point at the real route.

Yes — add a media query or a resize listener that adds the .collapsed class automatically below a chosen viewport width, while still letting the user manually toggle it back if there is room.

Rotating a single chevron SVG 180 degrees produces the mirrored "point the other way" icon without needing a second SVG asset or an icon font, keeping the markup smaller and the two states visually consistent.

Yes — the icon tiles remain fully sized and clickable in the collapsed state; only the text label collapses. Consider adding a title attribute or tooltip on each icon so users can identify items by hovering while collapsed.