216 lines
9.0 KiB
Markdown
216 lines
9.0 KiB
Markdown
# Second-Brain Dashboard UI/UX Design Plan (mobile-first)
|
||
|
||
Basis: `second-brain/templates/dashboard.html`, `second-brain/static/style.css` (aktueller Stand) + neue Graph-Controls aus `/tmp/second-brain-staging/`.
|
||
|
||
## 1) Konkreter Design-Plan
|
||
|
||
### Ziele (UX)
|
||
- **Schnelles Triaging unterwegs:** Pending/Errors sofort sichtbar, 1-Hand-Bedienung.
|
||
- **Konsistentes Design-System:** einheitliche Buttons/Inputs/Panels statt Einzellösungen.
|
||
- **Graph als Diagnose-Tool:** klare Controls, Legende, nachvollziehbares Feedback (Loading/Empty/Errors).
|
||
|
||
### Farbschema (Dark, high-contrast, "indigo + emerald")
|
||
- **Background:** sehr dunkel (nahe #0f1117) für weniger Blendung.
|
||
- **Surface (Cards/Panels):** abgestufte Flächen (Surface-1, Surface-2) für Hierarchie.
|
||
- **Primary:** Indigo/Blue für interaktive Elemente und Highlights (bisher #6c8af5 bleibt als Basis).
|
||
- **Success:** Emerald für Confirm/OK (bisher #3a7d3a → etwas heller/satter).
|
||
- **Danger:** Red für Errors/Reject.
|
||
- **Warning:** Amber für Pending/Match/Attention.
|
||
- **Text:** fast-weiß, sekundär gedimmt.
|
||
|
||
### Typografie
|
||
- Systemfont-Stack (schnell, gut lesbar): `ui-sans-serif, system-ui, -apple-system, Segoe UI, Roboto, Arial`.
|
||
- Skala (mobile-first):
|
||
- `text-xs` 12px (Labels, Meta)
|
||
- `text-sm` 13–14px (secondary)
|
||
- `text-md` 15–16px (Body)
|
||
- `text-lg` 18–20px (Titles)
|
||
- **Ziffern:** optional `font-variant-numeric: tabular-nums;` für Stats.
|
||
|
||
### Spacing/Rhythm
|
||
- 4px Grid; Standard-Gaps: 8/12/16.
|
||
- Container-Padding: 12px (mobile), 16–20px (>=768px).
|
||
- Border-radius: 12–16px (Cards/Modals), 10px (Inputs/Buttons), 999px (Pills).
|
||
|
||
### Komponenten (konkret)
|
||
|
||
#### A) Tabs
|
||
- Tabs bleiben als 3 Buttons, aber:
|
||
- **Active State** deutlicher (background + border + subtle glow).
|
||
- **Touch target** min. 44px Höhe.
|
||
- Sticky bleibt, aber mit leichter **Backdrop-Blurring** (wenn möglich) oder solid surface.
|
||
|
||
#### B) Search
|
||
- Search-Row wird als **kompakte Toolbar** gestaltet:
|
||
- Input + Filter in einer Zeile.
|
||
- Optional Quick-Chips darunter: `All / Pending / Confirmed / Errors` (klickbar) als Alternative zum Select.
|
||
- Clear-Button (×) im Input (per CSS `::-webkit-search-cancel-button` oder eigener Button) für Mobile.
|
||
|
||
#### C) Cards
|
||
- Karte als 3 Zonen: Header (badges/tags/date), Body (content), Footer (actions).
|
||
- Status wird stärker codiert:
|
||
- left-border + kleine **Status-Pill** (OK/Pending/Error) mit eindeutiger Farbe.
|
||
- Body: bessere Lesbarkeit via `line-height: 1.55` und max-height/clamp optional.
|
||
|
||
#### D) Modal
|
||
- Modal als **Bottom Sheet** auf Mobile (>=50vh) + klassisches Center-Modal auf Desktop.
|
||
- Close-Button größer + Tap-Area.
|
||
- Inhalt in Tabs/Sections (History/Meta/Content) optional später.
|
||
|
||
#### E) Graph + Controls (aus Staging)
|
||
- Controls als **Control Bar** oberhalb Canvas:
|
||
- Primary: Physics toggle.
|
||
- Secondary: Fit, Reset, Reload.
|
||
- Text labels kurz (z.B. `Physics` statt `Physics: off`, state als Badge).
|
||
- Canvas passt sich an Viewport an:
|
||
- `width: min(100%, 560px)`; Height: `min(65vh, 560px)` (CSS statt fester HTML Attribute, wenn möglich).
|
||
- Legende als einklappbares Panel (`Details`/`summary`) oder leichtes Panel unter Canvas.
|
||
|
||
#### F) Status Panels
|
||
- Status-View nutzt vorhandene `.panel`/`.kv-*`:
|
||
- Gruppen: System, Storage, Jobs, Insights, Pending Queue.
|
||
- Jede Gruppe als Panel mit klarer Title Row.
|
||
- Kritische Werte (Errors/Pending/Queue) farblich markieren.
|
||
|
||
## 2) CSS-Variablen (Theme-Tokens) + Mapping
|
||
|
||
### Token-Vorschlag (`:root`)
|
||
```css
|
||
:root {
|
||
/* typography */
|
||
--font-sans: ui-sans-serif, system-ui, -apple-system, Segoe UI, Roboto, Arial, sans-serif;
|
||
|
||
/* colors */
|
||
--bg: #0f1117;
|
||
--surface-1: #14151d;
|
||
--surface-2: #1a1b26;
|
||
--border: #2a2d3a;
|
||
|
||
--text: #e8e8ee;
|
||
--text-muted: #8b90a3;
|
||
--text-dim: #5c6276;
|
||
|
||
--primary: #6c8af5; /* existing */
|
||
--primary-2: #8aa1ff;
|
||
--success: #2fbf71;
|
||
--danger: #ef4444;
|
||
--warning: #f7d154; /* existing-ish */
|
||
|
||
/* shadows */
|
||
--shadow-1: 0 1px 0 rgba(0,0,0,.25), 0 8px 24px rgba(0,0,0,.35);
|
||
|
||
/* radius */
|
||
--r-sm: 10px;
|
||
--r-md: 14px;
|
||
--r-lg: 16px;
|
||
|
||
/* spacing */
|
||
--s-1: 4px;
|
||
--s-2: 8px;
|
||
--s-3: 12px;
|
||
--s-4: 16px;
|
||
--s-5: 20px;
|
||
|
||
/* control sizes */
|
||
--tap: 44px;
|
||
}
|
||
```
|
||
|
||
### Mapping auf existierende Selektoren
|
||
- `body`/`.app`
|
||
- `background: var(--bg)` statt `#141419`
|
||
- `font-family: var(--font-sans)`
|
||
- `color: var(--text)`
|
||
- `.stats-bar`, `.tabs-bar`, `.search-box`
|
||
- `background: var(--surface-1)` (Stats ggf. Gradient bleibt, aber auf Tokens)
|
||
- `border-bottom: 1px solid var(--border)`
|
||
- `.panel`, `.card`, `.modal-content`, `.graph-legend`
|
||
- `background: var(--surface-2)`
|
||
- `border: 1px solid var(--border)`
|
||
- `border-radius: var(--r-md)`
|
||
- `.stat-num`, `#pageNum`, `.tab-btn.active`, `#searchInput:focus`
|
||
- `color/border-color: var(--primary)`
|
||
- `.muted`, `.stat-label`, `.kv-key`, `.date`
|
||
- `color: var(--text-muted)` bzw. `var(--text-dim)`
|
||
- Buttons
|
||
- vereinheitlichen über `.btn` + Modifier: `.btn.primary`, `.btn.danger`, `.btn.success`, `.btn.ghost`
|
||
- `min-height: var(--tap)` für Touch
|
||
|
||
## 3) 5–10 priorisierte UI-Änderungen (mit Begründung)
|
||
|
||
1) **Design Tokens (CSS vars) einführen** → reduziert Farbmix, erleichtert spätere Themes/Anpassungen.
|
||
2) **Einheitliche Button-Komponente (`.btn`)** (inkl. `:active`, `:disabled`, `min-height`) → bessere Touch-UX, konsistente Interaktion.
|
||
3) **Graph-Controls + Legende aus Staging in den Main-Template-Stand ziehen** → Graph wird tatsächlich bedienbar/selbsterklärend.
|
||
4) **Responsive Graph-Canvas (CSS gesteuert)** statt fixer `width/height` → bessere Nutzung auf Phones, weniger Scroll.
|
||
5) **Search als Toolbar + Clear-Action** → schnelleres Filtern unterwegs, weniger Friktion.
|
||
6) **Modal als Bottom-Sheet auf Mobile** → angenehmer für längeren Content + History, weniger „winziges Fenster“.
|
||
7) **Status/Health Werte farblich akzentuieren** (pending/errors/warn) → schnelleres Erkennen von Problemen.
|
||
8) **Cards: Status-Pill + typografische Lesbarkeit** (line-height, spacing) → weniger „Textblock“, bessere Scanbarkeit.
|
||
9) **Accessibility-Basics**: Focus-Rings, Kontrast, `prefers-reduced-motion` → weniger „invisible focus“ und bessere Bedienbarkeit.
|
||
10) **Top-level Layout Max-Width für Desktop** (z.B. 560–720px) → verhindert „zu breite“ Zeilen.
|
||
|
||
## 4) Optionale Patch-Vorschläge (Diff-Snippets, NICHT anwenden)
|
||
|
||
> Hinweis: Snippets sind bewusst klein gehalten. Gesamt < 120 Zeilen.
|
||
|
||
### Snippet A — Tokens + Button-System (style.css)
|
||
```diff
|
||
--- a/second-brain/static/style.css
|
||
+++ b/second-brain/static/style.css
|
||
@@
|
||
+:root {
|
||
+ --font-sans: ui-sans-serif, system-ui, -apple-system, Segoe UI, Roboto, Arial, sans-serif;
|
||
+ --bg:#0f1117; --surface-1:#14151d; --surface-2:#1a1b26; --border:#2a2d3a;
|
||
+ --text:#e8e8ee; --text-muted:#8b90a3; --text-dim:#5c6276;
|
||
+ --primary:#6c8af5; --success:#2fbf71; --danger:#ef4444; --warning:#f7d154;
|
||
+ --r-sm:10px; --r-md:14px; --r-lg:16px;
|
||
+ --s-2:8px; --s-3:12px; --s-4:16px;
|
||
+ --tap:44px;
|
||
+}
|
||
+
|
||
+body { font-family: var(--font-sans); background: var(--bg); color: var(--text); }
|
||
+
|
||
+.btn{
|
||
+ min-height: var(--tap);
|
||
+ background: #1e1e28;
|
||
+ border: 1px solid var(--border);
|
||
+ border-radius: var(--r-sm);
|
||
+ padding: 8px 12px;
|
||
+ color: #cfd3ff;
|
||
+ font-weight: 700;
|
||
+}
|
||
+.btn.primary{ border-color: var(--primary); box-shadow: 0 0 0 1px rgba(108,138,245,0.18) inset; }
|
||
+.btn.success{ background: rgba(47,191,113,.18); border-color: rgba(47,191,113,.35); }
|
||
+.btn.danger{ background: rgba(239,68,68,.16); border-color: rgba(239,68,68,.35); }
|
||
+.btn:active{ transform: scale(.98); }
|
||
+.btn:disabled{ opacity: .45; }
|
||
```
|
||
|
||
### Snippet B — Graph Controls + Legend übernehmen (dashboard.html)
|
||
```diff
|
||
--- a/second-brain/templates/dashboard.html
|
||
+++ b/second-brain/templates/dashboard.html
|
||
@@
|
||
- <div class="graph" id="graph" style="display:none;">
|
||
- <canvas id="graphCanvas" width="440" height="520"></canvas>
|
||
- <div class="muted small" id="graphHint">Lade Graph…</div>
|
||
- </div>
|
||
+ <div class="graph" id="graph" style="display:none;">
|
||
+ <div class="graph-controls">
|
||
+ <button class="btn primary" id="btnGraphPhysics" onclick="toggleGraphPhysics()">Physics</button>
|
||
+ <button class="btn" onclick="resetGraphView()">Reset</button>
|
||
+ <button class="btn" onclick="fitGraphView()">Fit</button>
|
||
+ <button class="btn" onclick="reloadGraph()">Reload</button>
|
||
+ </div>
|
||
+ <canvas id="graphCanvas" width="440" height="520"></canvas>
|
||
+ <div class="graph-hint muted small" id="graphHint">Lade Graph…</div>
|
||
+ <div class="graph-legend">
|
||
+ <div><strong>Graph</strong>: Zoom (Wheel/Pinch), Pan (Drag). Klick auf Engram öffnet Details, Klick auf Tag setzt Suche.</div>
|
||
+ <div class="legend-row"><span class="legend-dot engram"></span> Engram</div>
|
||
+ <div class="legend-row"><span class="legend-dot tag"></span> Tag</div>
|
||
+ <div class="legend-row"><span class="legend-dot match"></span> Match</div>
|
||
+ </div>
|
||
+ </div>
|
||
```
|
||
|