Skip to content

[ux-settings-general-theme-buries-save] Theme gallery hides Timezone Save #6948

Description

@atomantic

Screen / route: /settings/general — audited 2026-09-11 at 1440×900 and 375×812
Checklist failed: 1 (primary action above the fold) and 7 (hierarchy matches the task)

Problem

The user opens General to set timezone (cron / briefings) or home coordinates (weather). Those are the only fields that need Save. The entire first screen is the theme gallery, which applies instantly on click and does not use Save.

Live CDP:

  • 1440×900: headings are Interface Theme at y=140 and Timezone at y=804. Timezone Save is at y=884 (last pixels of the fold). Location Save is at y=1140, below the fold.
  • 375×812: fold actions are only theme family cards (Classic / Lumen / Black ICE / Blueprint). Both Save buttons are below the fold (y=1367 timezone, y=1781 location). Inner scroller 1716px vs 674px pane.

client/src/components/settings/GeneralTab.jsx:168-171 mounts <ThemePickerPanel /> first, then Timezone (:173-231, Save at :193-200), then Location (:233-290, Save at :272-279). ThemePickerPanel.jsx:8 already has a compact prop, but General does not pass it — and even compact would only shave descriptions (ThemePickerPanel.jsx:48-52); four family cards still fill a phone screen.

Theme changes call setTheme immediately (ThemePickerPanel.jsx:30). Burying the Save-gated settings under an instant-apply gallery is the wrong hierarchy.

Impact

A returning user who needs to fix timezone (so scheduled jobs fire at the right local time) must scroll past a theme catalog. On a phone they never see Save without scrolling. Unsaved timezone/location changes are easy to miss because the control is off-screen (timezoneDirty / locationDirty warnings live next to those Saves).

Fix

Decision: reorder, don’t restyle the theme picker. Keep swatches at full size below the Save-gated fields.

In GeneralTab.jsx, render the Timezone card and the Location card above the Interface Theme card. Leave ThemePickerPanel at its default (non-compact) presentation so theme choice stays visual. Do not add a page-level sticky Save — each field group already has its own Save, which is correct once those groups are in the fold.

model:light — reorder three existing cards in one file. effort:low — no new persistence; tests in GeneralTab.test.jsx already cover save guards and only need a “Timezone heading precedes Interface Theme” assertion.

Files: client/src/components/settings/GeneralTab.jsx, client/src/components/settings/GeneralTab.test.jsx

Scope: small

Acceptance criteria

  • At 1440×900, Timezone and its Save are in the viewport on first paint of /settings/general.
  • At 375×812, Timezone Save is in the viewport on first paint; Location Save is in the fold or immediately under Timezone without scrolling past theme cards.
  • Interface Theme remains on the page, below those two cards, and still applies on click.
  • Existing unsaved-changes guards for timezone and location still fire.
  • A test asserts the Timezone heading appears before the Interface Theme heading in the document.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

effort:lowLow reasoning budget per stepmodel:lightMechanical single-file changeplanTracked by /do:replanplanner:grok-4-6Plan authored by the grok-4-6 modeluxProposed from a UX/design audit

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions