Progressively enhanced accordion powered by the CSS
grid-template-rows
trick for smooth, paint-free animations. Auto-initializes from
data-wf-accordion
. Full keyboard navigation, ARIA wiring, and a clean programmatic API.
Basic
Default collapse mode – opening one item closes the others. Add
data-wf-accordion
to any
.wf-accordion
element to auto-init.
Wojo Framework is a lightweight, utility-first CSS and JavaScript component system designed for rapid UI development. It provides a set of composable primitives that work together without requiring a build step.
Yes - the accordion JavaScript handles ARIA attributes, keyboard navigation, and the open/close state. The CSS file handles the visual animation via the grid-template-rows technique.
Yes. Each accordion instance only manages its own direct
.wf-accordion-item
children, so nested accordions operate independently.
Add the native
disabled
attribute to a trigger button to prevent it from being toggled.
This item works normally.
This content is inaccessible while the trigger is disabled.
The disabled item is also skipped during Arrow Up / Down keyboard navigation.
HTML
<!-- Trigger with disabled attribute -->
<button class="wf-accordion-trigger" type="button" disabled>
<span>Unavailable section</span>
<i class="icon chevron down wf-accordion-icon" aria-hidden="true"></i>
</button>
Data Attributes
Attribute
Element
Values
Description
data-wf-accordion
.wf-accordion
-
Required for auto-init. Presence alone triggers initialization on
DOMContentLoaded
.
data-wf-mode
.wf-accordion
"collapse" | "open"
collapse
(default) closes others when one opens.
open
allows any number of items open simultaneously.
data-wf-variant
.wf-accordion
"flush" | "card"
Applies a visual style variant. See CSS for details.
data-wf-size
.wf-accordion
"sm" | "lg"
Adjusts trigger padding and font size.
data-wf-open
.wf-accordion-item
-
Present in HTML to start the item expanded (no animation). Added/removed by JS to track the open state.
Events & Public API
Events
Dispatched on the
.wf-accordion
element and bubble to
document
.
Event
detail
Description
wf:accordion-open
{ id, item, trigger, body }
Fired after an item opens.
wf:accordion-close
{ id, item, trigger, body }
Fired after an item closes.
JavaScript
import { WojoAccordion } from './src/js/components/wf-accordion.js'
// Auto-init runs on DOMContentLoaded - manual init:
const acc = new WojoAccordion(el, {
mode: 'collapse', // 'collapse' | 'open'
}).init()
// Instance accessed from the element after init:
const acc = document.querySelector('[data-wf-accordion]')._wfAccordion
// Public API
acc.open('wf-acc-b1') // Open by body element id
acc.close('wf-acc-b1') // Close by body element id
acc.toggle('wf-acc-b1') // Toggle by id
acc.openAll() // Open all non-disabled items
acc.closeAll() // Close all items
acc.destroy() // Detach event listeners
// Events
el.addEventListener('wf:accordion-open', e => {
const { id, item, trigger, body } = e.detail
console.log('Opened:', id)
})
el.addEventListener('wf:accordion-close', e => {
console.log('Closed:', e.detail.id)
})
// Keyboard navigation (built-in)
// Space / Enter → toggle focused trigger
// Arrow Down → focus next enabled trigger
// Arrow Up → focus previous enabled trigger
// Home → focus first enabled trigger
// End → focus last enabled trigger
Class Reference
All modifier classes available on
.wf-accordion
Class
Type
Description
wf-accordion
Base
Container element. Add
data-wf-accordion
to auto-init.
wf-accordion-item
Structure
Individual panel wrapper. Add
data-wf-open
to start expanded.
wf-accordion-heading
Structure
Semantic heading wrapper (
h2–h6
). Resets font-size so it inherits from the trigger.
wf-accordion-trigger
Interactive
The
<button>
that toggles the panel. Add
disabled
to prevent toggling.
wf-accordion-icon
Optional
Chevron icon inside the trigger. Rotates 180° when the panel is open.
wf-accordion-body
Structure
Animated reveal wrapper. Uses
grid-template-rows: 0fr → 1fr
for the slide animation.
wf-accordion-content
Structure
Inner content wrapper. Provides padding and clips overflow during the animation.