From fd6e5f60e9ea12ca8a70481c43d7a4142063bde5 Mon Sep 17 00:00:00 2001 From: Bernardo Magri Date: Sat, 4 Jul 2026 19:08:18 +0100 Subject: [PATCH] fix(theme): generated waybar/rofi CSS invisible on on-surface palettes (item 27) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Follow-on to the swaync fix (a643391): the generated Waybar CSS colored the module row and #window @subtext and dim states @muted, and the generated rofi theme put @fg text on @surface chips — invisible where palettes use those roles as "on-surface" (flexoki-light: subtext==base, surface==text; gruvbox: muted/base = 1.27). flexoki-light has no whole-swap, so it ran this CSS. Generated surfaces only — the summer whole-swaps are hand-authored and untouched. - waybar: secondary text → alpha(@text, 0.85); dim states (inactive workspaces, DND bell, muted volume) → alpha(@text, 0.5). - rofi: @dim → text+"80", @surface → text+"1a" (#RRGGBBAA fg tints). - check-theme-contrast.py pairings/docs now cover all three generated surfaces; status glyphs (good/warn/bad on base, worst 2.05) are deliberately not held to a text ratio — raising them is palette design, a human decision. Verified: V0; V1 (checks.theme-contrast green over 21 themes; downstream-template-home builds; rendered waybar style has zero @subtext/@muted/@surface; rendered custom.rasi shows fg-derived tints). Honesty: NOT visually verified — V3 queued (flexoki-light eyeball + dark-theme regression spot-check). Co-Authored-By: Claude Fable 5 --- agent/BACKLOG.md | 20 -------------------- agent/HARDWARE-QUEUE.md | 5 +++++ agent/JOURNAL.md | 17 +++++++++++++++++ docs/ROADMAP.md | 9 +++++++-- modules/home/rofi.nix | 9 +++++++-- modules/home/waybar.nix | 14 +++++++++----- tools/check-theme-contrast.py | 17 +++++++++-------- 7 files changed, 54 insertions(+), 37 deletions(-) diff --git a/agent/BACKLOG.md b/agent/BACKLOG.md index 2074184..0b154ff 100644 --- a/agent/BACKLOG.md +++ b/agent/BACKLOG.md @@ -25,26 +25,6 @@ next, in what order*. *Items 21–27: real-hardware QA findings from the Latitude 5410 (Bernardo, 2026-07-04) — bugs found on metal outrank the queue.* -### 27. Generated waybar/rofi CSS invisible on on-surface palettes -Found by item 25's audit: the generated Waybar CSS colors `#window` and -the whole module row `@subtext`, and the generated rofi theme puts `@fg` -text on `@surface` backgrounds (inputbar, textbox, `element alternate`). -In palettes where subtext/surface mean "on-surface" (flexoki-light: -subtext==base AND surface==text) those are invisible. summer-day/night -escape via their whole-swap waybar.css/rofi.rasi — **flexoki-light does -not** and runs the generated CSS. Same class of fix as the shipped -swaync one (63136a8-follow-on): move the generated surfaces to pairings -that contrast by construction (alpha(@text) tints; @text for module -text with per-module accents kept), then extend -tools/check-theme-contrast.py's PAIRINGS to cover waybar/rofi so -`checks.theme-contrast` guards them too. Waybar changes must respect -the parity rule (generated bar only — the summer whole-swaps are -hand-authored and unaffected). Alternative worth weighing in-iteration: -normalize the flexoki-light palette itself (make subtext dim-text, -surface elevated-bg) — smaller diff but changes the theme's look -everywhere. **Verify:** V1 + the extended contrast check across all 21 -themes; V2 themed-VM screenshot on flexoki-light if cheap; V3 eyeball. - ### 22. Network menu shows nameless/weird entries Reported: `networkmanager_dmenu` lists entries with no names (likely hidden-SSID APs rendered as blank rows, possibly other adapters/ diff --git a/agent/HARDWARE-QUEUE.md b/agent/HARDWARE-QUEUE.md index b54063a..10cc9fd 100644 --- a/agent/HARDWARE-QUEUE.md +++ b/agent/HARDWARE-QUEUE.md @@ -44,6 +44,11 @@ QA machine), the **T14s** (webcam case). readable body text; open the control centre (SUPER+N), hover a notification row and check the Clear button — all text legible (body/buttons now @text on tinted chips, not subtext/surface). +- [ ] **Bar + rofi legible on flexoki-light** (item 27 fix) — switch to + flexoki-light: every Waybar module readable (window title, tray + row, dimmed inactive workspaces / muted volume visible-but-dim), + rofi inputbar/alternate rows show text. Spot-check one dark theme + (e.g. tokyo-night) for no visual regression in the same spots. - [ ] **Keyboard hotplug picker (re-verify after in-flake graduation)** — plug an external keyboard post-login, pick a layout in rofi, confirm it applies per-device only, persists in `settings.keyboard.devices`, diff --git a/agent/JOURNAL.md b/agent/JOURNAL.md index ee61c0d..936a061 100644 --- a/agent/JOURNAL.md +++ b/agent/JOURNAL.md @@ -17,6 +17,23 @@ Template: --- +## 2026-07-04 — waybar/rofi palette-safe pairings (iteration #10, item 27) +- **Task:** BACKLOG NOW#27 — generated waybar/rofi CSS invisible on + on-surface palettes (flexoki-light runs it; summers whole-swap). +- **Did:** waybar.nix generated CSS: module row + #window → + alpha(@text, 0.85); inactive workspaces / dnd / pulseaudio.muted → + alpha(@text, 0.5) (gruvbox's muted/base was 1.27). rofi.nix: @dim → + text+80, @surface → text+1a (#RRGGBBAA fg tints). Contrast check + docstring/pairings now cover all three generated surfaces. Status + glyphs (good/warn/bad on base, worst 2.05) left as-is — palette + design, human call. Generated bar only; whole-swaps untouched. +- **Verified:** V0; V1 — checks.theme-contrast green (21 themes), + downstream-template-home builds, rendered waybar style has zero + @subtext/@muted/@surface, rendered custom.rasi shows fg-derived + tints. NOT visually verified — V3 queued (flexoki-light eyeball). +- **Pending:** V3 flexoki-light + dark-theme regression spot-check. +- **Next suggestion:** item 22 (network menu rows) — V1-actionable. + ## 2026-07-04 — swaync contrast fix + theme-contrast check (iteration #9, item 25) - **Task:** BACKLOG NOW#25 — swaync text invisible on summer-day. - **Did:** swaync.nix now uses only palette-safe pairings: body/summary diff --git a/docs/ROADMAP.md b/docs/ROADMAP.md index 29dcda7..a1662ec 100644 --- a/docs/ROADMAP.md +++ b/docs/ROADMAP.md @@ -858,8 +858,13 @@ how to override it. Items marked ✓ are shipped. worst ratio 5.18 across 21 themes) and alpha(@text, 0.1) tints for chips/hovers — guarded permanently by `checks.theme-contrast` (tools/check-theme-contrast.py, WCAG ratios over themes/*.json). - The same audit found generated waybar/rofi CSS shares the bug class, - exposed on flexoki-light (BACKLOG item 27). + The same audit found generated waybar/rofi CSS shared the bug class, + exposed on flexoki-light (no whole-swap) — fixed in the follow-on: + waybar dim/secondary shades are alpha(@text) tints, rofi @dim/@surface + are fg-derived #RRGGBBAA tints, and the contrast check's pairings now + cover all three generated surfaces. Status glyph accents + (good/warn/bad on base, 2.0–2.7 in some palettes) were left as-is — + raising them is palette design, a human call. - ✓ **Waybar crash on theme switch left the session bar-less** (Latitude hardware QA, 2026-07-04): exec-once has no supervisor, so any crash orphaned the session until relogin — and the switch path itself was diff --git a/modules/home/rofi.nix b/modules/home/rofi.nix index fa6626c..059fb2b 100644 --- a/modules/home/rofi.nix +++ b/modules/home/rofi.nix @@ -696,8 +696,13 @@ in "*" = { bg = mkLiteral c.base; fg = mkLiteral c.text; - dim = mkLiteral c.subtext; - surface = mkLiteral c.surface; + # @dim/@surface are fg-derived #RRGGBBAA tints, NOT the + # palette's subtext/surface roles — "on-surface" palettes + # (flexoki-light: subtext==base, surface==text) made the + # inputbar, textbox and alternate rows invisible (item 27; + # guarded by tools/check-theme-contrast.py). + dim = mkLiteral (c.text + "80"); + surface = mkLiteral (c.text + "1a"); accent = mkLiteral c.accent; background-color = mkLiteral "transparent"; diff --git a/modules/home/waybar.nix b/modules/home/waybar.nix index a1b0cd9..0dd5276 100644 --- a/modules/home/waybar.nix +++ b/modules/home/waybar.nix @@ -253,9 +253,13 @@ let border-radius: ${toString t.ui.rounding}px; } + /* Dim/secondary shades are alpha(@text) tints, NOT the palette's + subtext/muted roles — those mean "on-surface" in some palettes + (flexoki-light: subtext==base, gruvbox: muted≈base) and vanish + against the bar (item 27; tools/check-theme-contrast.py). */ #workspaces button { padding: 0 8px; - color: @muted; + color: alpha(@text, 0.5); border-radius: ${toString t.ui.rounding}px; } @@ -270,7 +274,7 @@ let } #window { - color: @subtext; + color: alpha(@text, 0.85); padding: 0 12px; } @@ -280,7 +284,7 @@ let } #tray, #pulseaudio, #cpu, #memory, #custom-powerprofile, #custom-nightlight, #custom-updates, #custom-vpn, #language, #battery, #custom-notification { - color: @subtext; + color: alpha(@text, 0.85); padding: 0 10px; } @@ -300,9 +304,9 @@ let /* notifications waiting → accent; Do-Not-Disturb → muted bell-off */ #custom-notification.notification { color: @accent; } #custom-notification.dnd-none, - #custom-notification.dnd-notification { color: @muted; } + #custom-notification.dnd-notification { color: alpha(@text, 0.5); } - #pulseaudio.muted { color: @muted; } + #pulseaudio.muted { color: alpha(@text, 0.5); } #battery.warning { color: @warn; } #battery.critical { color: @bad; } #battery.charging { color: @good; } diff --git a/tools/check-theme-contrast.py b/tools/check-theme-contrast.py index a188857..30cb0d7 100644 --- a/tools/check-theme-contrast.py +++ b/tools/check-theme-contrast.py @@ -1,12 +1,12 @@ #!/usr/bin/env python3 -"""Guard against invisible-text palettes (BACKLOG item 25). +"""Guard against invisible-text palettes (BACKLOG items 25 + 27). Asserts, for every themes/*.json, the WCAG contrast ratio of each -hex-on-hex fg/bg pairing the generated swaync CSS uses. Pairings built -from alpha(@text) tints over @base are contrast-by-construction and -need no assert. Extend PAIRINGS as more generated surfaces are fixed to -palette-safe roles (item 27 tracks waybar/rofi, which still use -subtext/surface and would fail here today). +hex-on-hex fg/bg pairing the generated swaync/waybar/rofi CSS uses. +Pairings built from alpha(@text) / #RRGGBBAA text tints are +contrast-by-construction and need no assert. Status glyph accents +(good/warn/bad on base) are deliberately NOT held to a text ratio — +several palettes sit at 2.0–2.7 there by design. Wired as `checks.theme-contrast` in flake.nix; also runnable directly: python3 tools/check-theme-contrast.py themes/ @@ -19,8 +19,9 @@ from pathlib import Path # borders (@accent/@bad on @base in swaync) are decorative and not held # to a text ratio (miasma's bad-on-base is 2.3, fine for a border). PAIRINGS = [ - ("text", "base", 4.5, "swaync body/summary/titles on the toast"), - ("base", "accent", 3.0, "swaync widget-title button:hover"), + ("text", "base", 4.5, "swaync body / waybar modules / rofi rows"), + # symmetric ratio also covers accent-on-base (waybar updates, rofi prompt) + ("base", "accent", 3.0, "swaync button:hover / waybar active ws / rofi selected row"), ]