Bootstrap 5 Dropdown JS (Popper.js) vs Native Popover API + CSS Anchor Positioning
Uses bootstrap.Dropdown + Popper.js — calculates position via createPopper() on every open, manages click-outside listeners, keyboard navigation.
Uses Popover API (popover="auto") + CSS Anchor Positioning — browser handles positioning, light-dismiss, and top-layer stacking. Zero JS.
| Metric | Bootstrap Dropdown | Native Popover API |
|---|---|---|
| Initialization time (20 instances) | - | - |
| Toggle time (100 cycles × 20 items) | - | - |
| Instance memory cost | - | - |
| JS code size | - | - |
|
CSS output size
_dropdown.scss (7.9 KB)
|
- | - |
data-bs-toggle="dropdown"
popover="auto" + CSS Anchor
createPopper() on every open, running JavaScript to calculate
offsets, detect overflow, and apply inline transform styles.
Native Popover API + CSS Anchor Positioning does this entirely in the browser’s
layout engine — zero JavaScript for positioning. The browser also provides
light-dismiss (click outside to close) and top-layer stacking natively.
<!-- Trigger button -->
<button style="anchor-name: --my-trigger"
popovertarget="my-menu">
Toggle menu
</button>
<!-- Menu (Bootstrap utility classes for styling) -->
<ul popover="auto" id="my-menu"
class="m-0 py-2 border rounded bg-white shadow list-unstyled"
style="position-anchor: --my-trigger;">
<li><a class="dropdown-item" href="#">Action</a></li>
<li><a class="dropdown-item" href="#">Another action</a></li>
</ul>
[popover] {
inset: auto; /* reset UA default */
position-area: bottom span-right; /* place below trigger */
}