Skip to content

feat(brand): light-mode yellow as a bordered fill, not a dimmed line - #140

Merged
kateebonner merged 2 commits into
mainfrom
kate/light-mode-brand-yellow
Jul 15, 2026
Merged

feat(brand): light-mode yellow as a bordered fill, not a dimmed line#140
kateebonner merged 2 commits into
mainfrom
kate/light-mode-brand-yellow

Conversation

@kateebonner

Copy link
Copy Markdown
Contributor

Why

On dark themes the Harmoniqs lemon (#FFF676) sings (14.8:1 vs the editor bg). On light themes it's invisible (1.1:1 vs white), so the accent solver dimmed it to a muddy gold (#A09829) and used it as a line — losing the brand. The gold also fails as a border: it clears the white page (2.99:1) but not the lemon fill it bounds (2.66:1), so edges read mushy.

The fix isn't a darker yellow — it's the same yellow, given a thin dark edge with dark text on top. A border has to out-contrast two things: the page behind it and the fill it bounds. A 1px dark hairline clears both by ~15:1; a dimmed yellow can't.

What

Reframe the single --color-accent into three honest roles:

token light dark
--color-accent-fill #FFF676 #FFF676
--color-on-accent #000 (never yellow text) #000
--color-accent-edge 1px --vscode-foreground hairline transparent (fill separates itself)
--color-accent-ink neutral foreground #FFF676
  • Solver (brand_accent.ts) — decides light/dark by bg luminance and emits fill/edge/ink; the OKLCH gold binary-search and --border-color-hero are retired.
  • Hero — the Run Inspector's single hero (fidelity) gets an opt-in filled-lemon flag (metric(…, { flag: true })) that appears when the value lands, replacing the washed-out border+tint. The catalog's four hero cards deliberately don't flag, so the brand moment stays singular.
  • Thin lines that can't be fills — sparkline stroke, button hover, catalog "proposed" dashed border, pulseplot focus fallback — move to ink (legible on both themes).

Testing

  • dev/brand_harness/ — new standalone page (pnpm run dev:brand) renders the real components in light/dark through the actual solver, with a live token readout. Mirrors dev/pulseplot_harness.
  • Rewrote brand_accent.test.ts: asserts the light edge clears both the page and the fill, and that dark draws no edge.
  • Fast suite: 574 passed; typecheck + prettier clean.

Follow-up

The opencode chat UI carries the identical light-mode problem in its own theme (oc-2.json light v2-text/icon-accent = gold #857A00). That's a separate PR on harmoniqs/opencode, which then re-vendors the rebuilt binary here.

🤖 Generated with Claude Code

kateebonner and others added 2 commits July 15, 2026 10:47
On light themes the brand lemon (#FFF676, 1.1:1 vs white) was dimmed to a
muddy gold (#A09829) and used as a line — losing the brand. The gold also
failed as a border: it cleared the white page (2.99:1) but not the lemon
fill it bounded (2.66:1), so edges read mushy.

Reframe the single --color-accent into three honest roles:
  • fill — the true brand lemon on EVERY theme, dark ink on top (never yellow text)
  • edge — a 1px dark hairline on light (the theme's own foreground, ~15:1 vs
           both page and fill); transparent on dark (the lemon separates itself)
  • ink  — thin lines that can't be fills: lemon on dark, neutral fg on light

Retire the OKLCH gold binary-search and --border-color-hero. The Run
Inspector hero's brand moment becomes an opt-in filled-lemon flag (metric
flag: true) instead of a washed-out border+tint; the catalog's four hero
cards keep neutral emphasis so the flag stays singular. Migrate button
hover, sparkline stroke, catalog "proposed" border, and pulseplot focus to
the ink token.

Tests rewritten to assert the edge clears BOTH the page and the fill on
light, and that dark draws no edge. Full suite green (574 passed); typecheck
+ prettier clean.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
A standalone browser page (mirrors dev/pulseplot_harness) that mounts the
real components — swatch, flagged/neutral hero metrics, buttons, sparkline,
catalog card — against stubbed VS Code theme vars, driven by the actual
applyBrandAccent solver. Toggle flips light/dark and shows the live
fill/edge/ink readout. Not shipped (dev/ excluded from the VSIX); built
bundle gitignored like the pulseplot harness. Run: pnpm run dev:brand

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
kateebonner added a commit to harmoniqs/opencode that referenced this pull request Jul 15, 2026
…d ink

The default theme's light accent used a dimmed gold (`#857A00`/`#6B6200`) for
`text-accent`/`icon-accent` because raw `#FFF676` is unreadable on a light bg
(1.1:1). But that made every accent text/icon/border read muddy on light and
lost the brand. This mirrors the amicode webview fix (harmoniqs/amicode#140):
yellow is a FILL, never an ink.

- oc-2.json (LIGHT v2Overrides only; dark untouched): text/icon-accent gold →
  neutral dark ink (grey-1000 / grey-900). This turns `icon-accent` into the
  "edge" role — dark on light, lemon on dark — for free.
- amicode.css: the solid brand dots (.amc-livedot, anchored timeline node) now
  fill with `bg-accent` (true lemon) and take `icon-accent` as a 1px edge — a
  dark hairline on light, invisible (lemon-on-lemon) on dark. Dark render is
  byte-for-byte unchanged.

oc-2.json's v2Overrides is hand-maintained for the brand (theme.css is still
upstream blue); do NOT run `generate:v2-oc2` — it would revert every brand
accent to blue. Patch map (AMICODE-PATCHES.md #12) updated.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@kateebonner
kateebonner merged commit cec66de into main Jul 15, 2026
5 checks passed
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