From 55ee52b213da2446cf4969f47e8ccc658f243485 Mon Sep 17 00:00:00 2001 From: iris Date: Mon, 8 Jun 2026 21:48:08 +0200 Subject: [PATCH 1/2] refactor(frontend): add shared tab-strip base styles (#1464 step 1 foundation) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit First piece of the generic tabs component: @hive/shared/tabs.css carries the base .hive-tabbar / .hive-tab / .hive-tab--active styles (lifted from the logs sub-tab pattern, the most generic of the three tab UIs). Colours use the semantic theme vars so it inherits theme-swap safety. Not yet consumed — the createTabStrip JS helper + the per-call-site migrations (logs, agent window-tabs, dashboard tabbar) follow. Count pills + the dashboard's responsive overflow menu will layer on top in the per-page CSS rather than the shared base. --- frontend/packages/shared/src/tabs.css | 37 +++++++++++++++++++++++++++ 1 file changed, 37 insertions(+) create mode 100644 frontend/packages/shared/src/tabs.css diff --git a/frontend/packages/shared/src/tabs.css b/frontend/packages/shared/src/tabs.css new file mode 100644 index 00000000..06e5417f --- /dev/null +++ b/frontend/packages/shared/src/tabs.css @@ -0,0 +1,37 @@ +/* Shared tab-strip chrome — the generic tab/sub-tab styling used across + the dashboard tabbar, the logs sub-tabs, and the agent stat-window + selector. Behaviour lives in `@hive/shared/tabs.js` (createTabStrip). + + Colours come from the semantic theme layer (theme.css → colors.css), + so this inherits theme-swap safety for free. Call sites keep a thin + variant class for size/spacing deltas; richer affordances (count + pills, the dashboard's responsive overflow ⋮ menu) layer on top in the + per-page CSS. See docs/web-ui/css-vars.md + #1464. */ + +.hive-tabbar { + display: flex; + gap: 0.2em; +} + +.hive-tab { + display: inline-flex; + align-items: center; + padding: 0.35em 0.9em; + border-radius: 4px; + color: var(--subtext0); + text-decoration: none; + font-size: 0.85em; + letter-spacing: 0.05em; + cursor: pointer; + transition: background 100ms, color 100ms; +} + +.hive-tab:hover { + background: var(--border); + color: var(--fg); +} + +.hive-tab--active { + background: var(--border); + color: var(--purple); +} From e1c276a06ec2b4a5c0acd2f5b3784b83d670d183 Mon Sep 17 00:00:00 2001 From: iris Date: Mon, 8 Jun 2026 22:03:39 +0200 Subject: [PATCH 2/2] refactor(frontend): add createTabStrip + migrate logs sub-tabs (#1464 step 1) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Adds @hive/shared/tabs.js — createTabStrip(tabbar, {defaultId, onShow}): a hash-routed tab strip that resolves controls by `[data-tab=""]` inside the passed container and panels by `[data-tab-pane=""]`, toggling `.hive-tab--active` + aria-selected + the panel's `hidden`, and firing onShow(id) for per-tab side-effects. Always hash-routed (deep- linkable + back/forward), no element-resolver callbacks (convention over config), per the #1464 design review. Wires it up: @hive/shared exports `./tabs.js` + `./tabs.css`, and common.css @imports tabs.css (component structure, not a swap target, so inlining is fine — unlike theme.css). Migrates the logs sub-tabs as the first consumer: markup uses `.hive-tab`/`data-tab`/`data-tab-pane`, logs.css drops the duplicated base styles (keeps only its `flex:1` layout delta), and logs.js swaps its activeTab/showTab/hashchange for createTabStrip (onShow lazy-loads the SYSTEM tab). Behaviour-preserving. aria-selected is now standardised. --- frontend/packages/dashboard/src/common.css | 1 + frontend/packages/dashboard/src/logs.css | 22 +------ frontend/packages/dashboard/src/logs.html | 20 +++--- frontend/packages/dashboard/src/logs.js | 45 +++++--------- frontend/packages/shared/package.json | 2 + frontend/packages/shared/src/tabs.css | 2 +- frontend/packages/shared/src/tabs.js | 71 ++++++++++++++++++++++ 7 files changed, 103 insertions(+), 60 deletions(-) create mode 100644 frontend/packages/shared/src/tabs.js diff --git a/frontend/packages/dashboard/src/common.css b/frontend/packages/dashboard/src/common.css index 73f35030..22c6fb37 100644 --- a/frontend/packages/dashboard/src/common.css +++ b/frontend/packages/dashboard/src/common.css @@ -2,6 +2,7 @@ Bundled in front of the page-specific rules via esbuild. */ @import "@hive/shared/base.css"; @import "@hive/shared/terminal.css"; +@import "@hive/shared/tabs.css"; /* ─── global typography ───────────────────────────────────────────── Element-level rules shared across all three pages (index, flow, diff --git a/frontend/packages/dashboard/src/logs.css b/frontend/packages/dashboard/src/logs.css index 8105be9c..ee797a8c 100644 --- a/frontend/packages/dashboard/src/logs.css +++ b/frontend/packages/dashboard/src/logs.css @@ -7,29 +7,13 @@ body.logs-shell { padding: 0; } +/* Base tab styling now lives in @hive/shared/tabs.css (.hive-tab*). The + logs strip only adds a layout delta: fill the header row next to the + ← home back-link. */ .logs-tabbar { - display: flex; - gap: 0.2em; flex: 1; } -.logs-tab { - display: inline-flex; - align-items: center; - padding: 0.35em 0.9em; - border-radius: 4px; - color: var(--subtext0); - text-decoration: none; - font-size: 0.85em; - letter-spacing: 0.05em; - transition: background 100ms, color 100ms; -} -.logs-tab:hover { background: var(--border); color: var(--fg); } -.logs-tab.logs-tab-active { - background: var(--border); - color: var(--purple); -} - .logs-main { padding: 1.2em 1.5em 2em; } diff --git a/frontend/packages/dashboard/src/logs.html b/frontend/packages/dashboard/src/logs.html index 2f6af3dc..60f0eaba 100644 --- a/frontend/packages/dashboard/src/logs.html +++ b/frontend/packages/dashboard/src/logs.html @@ -17,17 +17,17 @@ points to the H0M3 hub (served at /), not the dashboard. -->
← home -