Accordions

Accordions expand and collapse content sections, helping users focus on relevant information without overwhelming the page. Built on native <details> and <summary> elements for optimal accessibility.


Installation

Copy the accordion CSS from styles/docs.css or include the Standard stylesheet:

<link rel="stylesheet" href="standard.min.css">

Then use accordion classes in your HTML:

<div class="Accordion">
    <details class="Accordion-item">
        <summary class="Accordion-header">Section Title</summary>
        <div class="Accordion-content">
            <p>Content goes here...</p>
        </div>
    </details>
</div>

Usage

The base .Accordion class provides the container styling. Each panel uses native <details> and <summary> elements for built-in accessibility and keyboard support.

What is Standard?

Standard is a framework-agnostic design system built with OKLCH colors and a 4px spacing scale.

How do I install it?

Simply include the CSS file in your project. No JavaScript framework required.

Is it accessible?

Yes! Native elements provide built-in keyboard navigation and screen reader support.


Examples

With Icons

Add chevron indicators that rotate on expand using the .Accordion--icons modifier and .Accordion-icon class.

Account Settings

Manage your account preferences, email notifications, and security settings.

Privacy & Security

Control who can see your profile and manage two-factor authentication.

Billing Information

Update your payment method, view invoices, and manage your subscription.

Bordered

Add visible borders between items with the .Accordion--bordered modifier.

Getting Started

Learn the basics of using Standard in your projects.

Components

Explore the full library of UI components.

Customization

Learn how to customize tokens and extend the system.

Flush

No outer borders for seamless integration into cards or panels.

Order Summary
Subtotal $99.00
Shipping $5.00
Total $104.00
Shipping Address

123 Main Street
San Francisco, CA 94102

Default Open

Use the open attribute to expand an item by default.

This section is open by default

Add the open attribute to the <details> element to have it expanded on page load.

This section is closed

Click to expand this content.

Single Expand (Exclusive)

Use JavaScript to ensure only one item is open at a time. Add data-accordion="exclusive" to enable this behavior.

Panel One

When this opens, other panels close automatically.

Panel Two

Only one panel can be open at a time.

Panel Three

This creates a traditional accordion behavior.

// Exclusive accordion behavior
document.querySelectorAll('[data-accordion="exclusive"]').forEach(accordion => {
  accordion.querySelectorAll('details').forEach(details => {
    details.addEventListener('toggle', () => {
      if (details.open) {
        accordion.querySelectorAll('details').forEach(other => {
          if (other !== details) other.open = false;
        });
      }
    });
  });
});

With Rich Content

Accordions can contain any content, including other components.

Team Members
A
Alice Johnson
Design Lead
Active
B
Bob Smith
Developer
Active

Common Patterns

FAQ Section

Frequently Asked Questions

What payment methods do you accept?

We accept Visa, Mastercard, American Express, and PayPal. All transactions are encrypted and secure.

How do I cancel my subscription?

Go to Settings → Billing → Cancel Subscription. Your access continues until the end of the billing period.

Do you offer refunds?

Yes, we offer a 30-day money-back guarantee for all plans. Contact support to request a refund.

Settings Panel

Profile Settings

Manage your display name, bio, and profile picture.

Notifications

Configure email, push, and in-app notification preferences.

Security

Two-factor authentication, password changes, and active sessions.

Category
Price Range

Customization

Override accordion styles using CSS custom properties:

/* Custom header styling */
.Accordion-header {
  --accordion-padding: var(--space-4);
  --accordion-bg-hover: var(--bg-tertiary);
  padding: var(--accordion-padding);
}

.Accordion-header:hover {
  background-color: var(--accordion-bg-hover);
}

/* Custom border color */
.Accordion--bordered {
  --accordion-border: var(--border-default);
  border-color: var(--accordion-border);
}

/* Custom icon animation */
.Accordion-icon {
  --accordion-icon-rotation: 180deg;
  transition: transform 0.3s ease;
}

details[open] .Accordion-icon {
  transform: rotate(var(--accordion-icon-rotation));
}

/* Compact accordion */
.Accordion--compact .Accordion-header {
  padding: var(--space-2) var(--space-3);
  font-size: 0.875rem;
}

.Accordion--compact .Accordion-content {
  padding: 0 var(--space-3) var(--space-3);
  font-size: 0.875rem;
}

API Reference

Container Classes

Class Description
.Accordion Base accordion container (required)
.Accordion--icons Enables icon rotation animation
.Accordion--bordered Adds borders around accordion and between items
.Accordion--flush Removes horizontal padding for card integration

Item Classes

Class Description
.Accordion-item Wrapper for each accordion panel (use on <details>)
.Accordion-header Clickable header element (use on <summary>)
.Accordion-content Collapsible content container
.Accordion-icon Chevron icon that rotates on expand

Data Attributes

Attribute Value Description
data-accordion "exclusive" Only one panel can be open at a time (requires JS)
open boolean Native attribute to expand panel by default

CSS Reference

/* Base Accordion */
.Accordion {
  width: 100%;
}

.Accordion-item {
  border: none;
}

.Accordion-item + .Accordion-item {
  border-top: 1px solid var(--bd);
}

.Accordion-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  padding: var(--space-3) var(--space-4);
  background: none;
  border: none;
  cursor: pointer;
  font-weight: 500;
  font-size: 0.9375rem;
  color: var(--fg);
  list-style: none;
  transition: background-color 0.15s;
}

.Accordion-header::-webkit-details-marker {
  display: none;
}

.Accordion-header::marker {
  display: none;
  content: "";
}

.Accordion-header:hover {
  background-color: var(--bg-s);
}

.Accordion-header:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: -2px;
}

.Accordion-content {
  padding: 0 var(--space-4) var(--space-4);
  color: var(--fg-3);
  font-size: 0.875rem;
  line-height: 1.6;
}

/* Icon rotation */
.Accordion-icon {
  font-size: 1rem;
  color: var(--fg-3);
  transition: transform 0.2s ease;
  flex-shrink: 0;
}

details[open] > .Accordion-header .Accordion-icon {
  transform: rotate(180deg);
}

/* Bordered variant */
.Accordion--bordered {
  border: 1px solid var(--bd);
  border-radius: var(--r-m);
  overflow: hidden;
}

.Accordion--bordered .Accordion-item + .Accordion-item {
  border-top: 1px solid var(--bd);
}

/* Flush variant */
.Accordion--flush .Accordion-header {
  padding-left: 0;
  padding-right: 0;
}

.Accordion--flush .Accordion-content {
  padding-left: 0;
  padding-right: 0;
}

.Accordion--flush .Accordion-item:first-child .Accordion-header {
  padding-top: 0;
}

Accessibility

Keyboard Support

Key Action
Enter Toggles the focused accordion panel
Space Toggles the focused accordion panel
Tab Moves focus to the next focusable element
Shift + Tab Moves focus to the previous focusable element

Screen Readers

Native <details> and <summary> elements provide excellent accessibility:

<!-- Native accordion — fully accessible out of the box -->
<details class="Accordion-item">
    <summary class="Accordion-header">Section Title</summary>
    <div class="Accordion-content">
        <p>Content is announced when expanded.</p>
    </div>
</details>

<!-- Default expanded state -->
<details class="Accordion-item" open>
    <summary class="Accordion-header">Open Section</summary>
    <div class="Accordion-content">
        <p>Screen readers announce "expanded" state.</p>
    </div>
</details>

Custom Implementation

For non-native implementations, use proper ARIA attributes:

<div class="Accordion">
    <div class="Accordion-item">
        <button id="accordion-header-1" 
                class="Accordion-header"
                aria-expanded="false" 
                aria-controls="accordion-panel-1">
            Section Title
        </button>
        <div id="accordion-panel-1" 
             class="Accordion-content"
             role="region" 
             aria-labelledby="accordion-header-1"
             hidden>
            <p>Content...</p>
        </div>
    </div>
</div>

Best Practices

Do

  • Use clear, descriptive headers — Users decide to expand based on the title
  • Keep content focused — Each section should cover one topic
  • Consider default states — Open the most important section by default
  • Use native elements<details> and <summary> provide built-in accessibility
  • Use for optional content — Hide supplementary info, not critical content

Don’t

  • Hide primary content — Don’t make users hunt for important information
  • Nest accordions deeply — One level is usually enough
  • Use for very short content — If it fits easily, just show it
  • Override keyboard behavior — Let native elements handle interaction
  • Forget visual indicators — Use icons to show expand/collapse state