Skip to content

fix(ui): theme select fields and stop their jump on focus - #48

Merged
TheMeinerLP merged 3 commits into
mainfrom
fix/md3-select-fields
Oct 17, 2026
Merged

TheMeinerLP merged 3 commits into
mainfrom
fix/md3-select-fields

Conversation

@TheMeinerLP

Copy link
Copy Markdown

Description

The select fields in the MD3 dashboard had three visible problems in dark mode: the open option list was the browser's own white popup with barely readable options and an OS-blue selection, a focused field showed a purple outline next to a pink label, and the field appeared to jump on focus.

Cause: MdSelect wrapped a native <select>. The browser drew its own option list, and @tailwindcss/forms draws a blue outer ring on a focused <select>, so the outline and the label disagreed.

Fix: MdSelect is now a select-only combobox with an MD3 menu drawn in the body. The menu uses the surface-container and primary roles, opens above the field when there is no room below, and follows the keyboard as a native select does (arrows, Home, End, type-ahead, Enter, Space, Escape, Tab). The focus colour is primary for the outline, the floating label and the trailing icon. The outline is a 1px border plus a 1px inset shadow, so focus never moves the field. Invalid fields keep the error role.

All call sites (search sort and order, audit action, maintenance dialogs, settings forms, repository wizard, the JSON-forms enum and one-of renderers) use MdSelect, so they change without edits. v-model, props and events are unchanged. A visually hidden native <select> stays in the DOM as the form value, so existing code that reads the select by id or name keeps working.

Type of change

  • fix - bug fix
  • feat - new feature
  • refactor - internal change without behaviour change
  • perf - performance improvement
  • docs - documentation only
  • test - tests only
  • build / ci / chore - tooling, dependencies, pipelines
  • Breaking change (configuration, API or behaviour that existing deployments rely on)

How was tested

Frontend only (reposilite-frontend/). Gradle was not run.

  • npx vitest run on MdSelect.test.js (42 tests: keyboard, v-model, ARIA, menu placement, focus classes, error and disabled states), plus the 19 test files of the components that render MdSelect (538 tests in total) with --maxWorkers=2, all green.
  • npm run build: passes.
  • eslint on the two changed files: clean.
  • Manual check in Chromium on the search page in dark mode: the menu renders on the dark surface with readable options and a primary selection; the focused field keeps its box position and label position, and its border, inset outline and label share one primary colour; ArrowDown, ArrowDown, Enter changes sort to artifactId, updates the URL and keeps focus on the field.

Checklist

  • Commit messages follow the Conventional Commits convention documented in CLAUDE.md
  • Tests cover the change
  • ./gradlew build passes locally (not run: no backend change)
  • Documentation and configuration samples are updated if the change is user-facing (no docs changed)
  • Existing copyright headers are preserved; no new files
  • No credentials, tokens or personal data are included in the diff

TheMeinerLP and others added 3 commits October 17, 2026 20:36
The select fields opened the browser's own option list. In dark mode
that list is white, its options are barely readable and the selection
is the OS blue, so it clashed with the theme.

MdSelect now uses a select-only combobox with an MD3 menu drawn in the
body. The menu takes the surface-container and primary roles, opens
above the field when there is no room below, and scrolls when neither
side has room. The keyboard works as on a native select: arrows, Home,
End, type-ahead, Enter, Space, Escape and Tab. The combobox carries the
ARIA attributes for the listbox pattern.

The native select stays in the DOM, hidden, as the form value. v-model,
form names and the call sites are unchanged.
A focused select showed two colours at once. The field's outline was the
theme primary, but @tailwindcss/forms draws a blue outer ring on a
focused select, so the native select also showed a blue-violet line, and
the floating label stayed pink.

The field is now a combobox, and the focus colour is primary for the
outline, the floating label and the trailing icon. The outline is a 1px
border with a 1px inset shadow, so focus never grows the box or moves the
label. Invalid fields keep the error role, focused or not, and disabled
fields take no focus colour.

Tests lock in the focus classes, the 1px border and the error and
disabled states.
@TheMeinerLP
TheMeinerLP merged commit a1d7fbf into main Oct 17, 2026
7 checks passed
@TheMeinerLP
TheMeinerLP deleted the fix/md3-select-fields branch October 17, 2026 19:19
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant