Skip to content

Filter

A row of tag buttons that shows only the items that match. It reads tags from the items themselves and announces how many are showing.

CSS
css/components/filter.css
JS
js/components/filter.js

01 — Variants

Filter a list

Items in the target carry data-tags. data-filter="*" shows everything.

Scrolling row

.filter--scroll keeps long tag lists on one row that scrolls sideways, out to the panel’s edges.

02 — Behavior

Script

NameDetail
data-filter-targetA selector for the container of items.
data-filter-nounThe word in the announcement: “3 projects”.
LinksOpening the page at #tag=slug, or following such a link, applies that tag.

03 — Usage

Use it for

  • Narrowing a list or gallery by a handful of categories.
  • Up to about a dozen tags; scroll the row past that.

Avoid

  • Searching. Use search.
  • Switching views. Use tabs.

04 — Accessibility

Notes

  • Pressable tags with aria-pressed, in a labeled group.
  • A polite live region announces the count after each change.

05 — Without Jewel’s JS

What the script does

The script hides items whose tags don’t match the pressed button, announces the count, and keeps the tag in the URL as #tag=slug. The CSS reads only the markup below, so a framework can filter its own list and leave out filter.js and data-component.

StateSet thisNotes
Pressed tagaria-pressed="true" on one .tag--button, aria-pressed="false" on the restFills the pressed tag.
Filtered outhidden on each item that doesn’t matchOr don’t render it. data-filter, data-filter-target and data-tags are only read by the script.
Count“Showing 2 of 3 projects” in .filter__statusA polite live region, so screen readers hear each change.
Disabledaria-disabled="true" on .filterDims the row and stops presses.