Building a Bootstrap Accordion with the details/summary HTML tags in 2025
A few years ago I wrote a short post about building a Bootstrap accordion using the <details> and <summary> HTML tags. The idea was to create a collapsible accordion without needing any JavaScript, relying solely on CSS for styling and the native functionality of the <details> element.
At the time it wasn’t possible to animate the opening and closing of the accordion (with CSS), but thanks to the relatively new ::details-content CSS pseudo-element with transitions we can do that now. So I’m revisiting that solution with an update with no need for JavaScript at all.
Note that the transition for now are only in Chrome/Edge, but I think support for Firefox and Safari is planned. If you’d prefer a more consistent experience across browsers, you might consider using the JavaScript-based solution in my original post.
Accordion Title 1
Accordion body content goes here.
Accordion Title 2
Accordion body content goes here.
Accordion Title 3
Accordion body content goes here.
<div class="accordion border-bottom-0">
<details class="accordion-item border-bottom-0">
<summary class="accordion-button rounded-top">
<div class="accordion-header user-select-none">Accordion Title 1</div>
</summary>
<div class="accordion-body border-bottom">
<p>Accordion body content goes here.</p>
</div>
</details>
<details class="accordion-item border-bottom-0">
<summary class="accordion-button">
<div class="accordion-header user-select-none">Accordion Title 2</div>
</summary>
<div class="accordion-body border-bottom">
<p>Accordion body content goes here.</p>
</div>
</details>
<details class="accordion-item">
<summary class="accordion-button">
<div class="accordion-header user-select-none">Accordion Title 3</div>
</summary>
<div class="accordion-body">
<p>Accordion body content goes here.</p>
</div>
</details>
</div>
<style>
details.accordion-item:not([open]) .accordion-button {
background-color: var(--bs-accordion-bg);
}
details.accordion-item:not([open]):last-of-type .accordion-button {
border-bottom-right-radius: var(--bs-accordion-border-radius);
border-bottom-left-radius: var(--bs-accordion-border-radius);
}
details.accordion-item:not([open]) .accordion-button::after {
background-image: var(--bs-accordion-btn-active-icon);
transform: unset;
}
details.accordion-item[open] .accordion-button::after {
background-image: var(--bs-accordion-btn-icon);
transform: var(--bs-accordion-btn-icon-transform);
}
/* Hide the default disclosure triangle on Safari */
summary.accordion-button::-webkit-details-marker {
display: none;
}
@media (prefers-reduced-motion: no-preference) {
details.accordion-item {
interpolate-size: allow-keywords;
}
}
details.accordion-item::details-content {
block-size: 0;
overflow-y: clip;
transition: content-visibility 0.2s allow-discrete, block-size 0.2s;
}
details.accordion-item[open]::details-content {
block-size: auto;
}
</style>