Skip to content

Searchable Select

Accessible Tailwind CSS combobox that filters options as you type, highlights matches and supports full keyboard navigation.

Tailwind CSS Selects Responsive Dark #accessible #combobox #dropdown #form #search #select

Live preview

Open in new tab

Code

A searchable select (combobox) built with Tailwind CSS and vanilla JavaScript, shown as a dark "Choose your stack" form where users filter a list of frameworks by typing. Use it instead of a native select when the list is long enough that scrolling becomes tedious: countries, time zones, team members, tags or product variants.

How it works

The root is .tss-select. Inside the form, [data-tss-combo] wraps a text input with role="combobox", a clear button (data-tss-clear), a chevron toggle (data-tss-toggle) and the floating .tss-panel. The panel holds the #tss-listbox list with role="option" items and a "no results" message marked data-tss-empty. Each option has a data-value, a color dot, the visible name in .tss-text, a short hint and a check icon that appears through the group-aria-selected:opacity-100 utility.

On DOMContentLoaded the script initializes every .tss-select, gives each option a unique id and stores its label. Typing fires the input event: options that do not contain the query get the hidden attribute, the matching part of each label is wrapped in a mark element, and the first match becomes the active option (data-active, styled with data-active:bg-cyan-400/15). The input points to it with aria-activedescendant, so focus never leaves the text field. Choosing an option writes the label into the input, the value into the hidden name="framework" field (data-tss-value) and a line into data-tss-summary. Leaving the field without choosing restores the last committed value. style.css rotates .tss-chevron and adds the tss-drop animation.

Customization

  • Add or remove li role="option" items in #tss-listbox; give each a data-value and a .tss-text label and the filter picks them up.
  • Set aria-selected="true" on one option to preselect it on page load (SvelteKit in the demo).
  • name="framework" on the data-tss-value input: rename it to match your backend field.
  • cyan utilities (focus-within:border-cyan-400, bg-cyan-400 on the submit button, text-cyan-400 on the check icon) and color: #22d3ee on mark in style.css: switch to another color to rebrand.
  • max-h-64 on #tss-listbox: show more or fewer rows before the list scrolls.
  • bg-slate-950 on .tss-select and bg-slate-900 on .tss-panel: swap for bg-white and bg-white with text-slate-900 for a light version.

Accessibility

The field follows the ARIA combobox pattern: role="combobox", aria-autocomplete="list", aria-controls, a live aria-expanded state and aria-activedescendant. The listbox is labelled by the visible label, options expose aria-selected, and a visually hidden role="status" region announces result counts and selections. Keyboard support: ArrowDown and ArrowUp open the list and move through matches, Enter selects, Escape closes (or clears the value when already closed), Tab closes without changing the value. The clear button has an sr-only label, the toggle is mouse-only and hidden from assistive technology, and the drop animation is disabled under prefers-reduced-motion.

Usage notes

The form submit is simulated; replace the handler in script.js with a fetch() call when you connect a backend. For several instances, repeat the .tss-select block with unique id values for the label, input and listbox.

Requirements

Add these to your page (already included in the download):

  • <script src="https://cdn.jsdelivr.net/npm/@tailwindcss/browser@4"></script>

The Tailwind browser build is for prototyping. In production, compile Tailwind with its CLI or your bundler.

Searchable Select – Tailwind CSS selects component screenshot
Searchable Select · Tailwind CSS Selects

More Selects

Styled Native Select – Pure CSS selects preview

Styled Native Select

Pure CSS restyle of the native select element with a custom arrow, focus ring, error, success and disabled states, and three sizes.