A Bootstrap 5 "active filters" bar made of dismissible chips, with a Clear all button, a counter badge, a simulated result count and a "Recently removed" row that brings filters back with one click. Use it above product listings, search results, data tables or job boards.
How it works
The root is section.fch-bar inside the .fch-wrap container. The header holds the h2.fch-heading with a .fch-total badge and the .fch-clear button. The chips are list items in ul.fch-chips: each .fch-chip shows a small .fch-chip__group label, the .fch-chip__value and a .fch-remove close button. Below the list sit the .fch-empty message, the hidden .fch-recent section with its .fch-restore-list, and the .fch-results line whose .fch-count reads its starting number from data-base.
On DOMContentLoaded the script sets up every .fch-bar. One delegated click listener on the list removes a chip when its .fch-remove button is pressed; a keydown listener does the same for Backspace and Delete. The chip gets the fch-out class, fades and shrinks for EXIT_MS (200 ms), and is then detached. A .fch-restore button with the chip value is added to the "Recently removed" row; clicking it puts the original chip back. update() refreshes the badge, disables Clear all when nothing is left, toggles the empty message and recalculates the demo result count by dividing data-base by NARROWING for every active filter. Clear all moves every chip to the restore row at once.
Customization
--fch-chip-bg,--fch-chip-borderand--fch-inkin.fch-wrap: change the chip fill, outline and text color (mint and forest green by default).--fch-radiusin.fch-wrap: use999pxfor fully rounded pills or0.25remfor square tags; the close button follows.--fch-accentin.fch-wrap: recolors the Clear all link and the dashed restore buttons.data-baseon.fch-count: sets the unfiltered result count used by the demo calculation.EXIT_MSinscript.js: lengthen or shorten the removal animation; keep it in sync with thetransitionon.fch-chip.- The
update()function inscript.js: replace the simulated count with afetch()call to your search API that sends the remaining chips. - Delete the
.fch-recentblock from the markup if you do not want an undo row; the script skips it safely.
Accessibility
The chips form a labelled list. Every close button has an explicit aria-label such as "Remove filter Size: EU 42", and the visible "×" is aria-hidden. After removing a chip, focus moves to the next chip's button, or to the previous one, or to the heading (which has tabindex="-1") when the list is empty, so keyboard users never lose their place. Clear all also sends focus to the heading. The .fch-status live region announces each change and the remaining number of filters. All buttons have a visible :focus-visible outline, and the fade is disabled under prefers-reduced-motion: reduce.
Usage notes
Requires only Bootstrap 5 (added automatically). Each .fch-bar is independent, so several filter bars can share a page; give each heading its own id and update the matching aria-labelledby.