Files
mokosh/.planning/intel/design-system.md
Mark f768498b87 docs(intel): unlock creative decisions across brand + design + assets specs
Adds brand-identity.md (Brief #1: name + blurb + creative slate).
Rewrites design-system.md and assets-spec.md to flip aesthetic
prescriptions into options while keeping Chrome MV3 / WCAG /
icon-size floors as binding (marked (FLOOR) inline). Mokosh codename
is the only locked decision; every other creative choice delegated
to brand + design teams with explicit ownership annotations.

Three-file intel pack now consistent:
- brand-identity.md: brand-team primary (naming, voice, blurb)
- design-system.md: design-team primary (palette, type, components)
- assets-spec.md: design-team primary (deliverables + floors)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-17 16:29:57 +02:00

391 lines
18 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Mokosh Design System
Cross-phase visual + interaction reference for the Mokosh extension (internal
codename "Mokosh"; public display name currently `"AI Call Recorder"`
open per `brand-identity.md`). Authored 2026-05-17 in response to Plan 01-09's
notification-icon discovery that the original placeholder PNGs failed Chrome's
notification API.
**This file mixes two kinds of content** and the design team should treat them
differently:
1. **Engineering sketches** — what the extension currently ships in placeholder
builds (colors, fonts, sizes, voice). These exist so the extension *runs*;
they are not direction. Override anything aesthetic.
2. **Technical floors** — what Chrome MV3, the notification API, MV3 CSP, or
WCAG accessibility require. These are binding regardless of creative
direction. Marked explicitly with **(FLOOR)** wherever they appear.
Status: `draft` — engineering sketch + binding floors. Both design and brand
teams have full authority over everything not marked **(FLOOR)**.
---
## What's locked vs what's open
| Decision | Status |
|---|---|
| Codename **"Mokosh"** | **LOCKED** (engineering — wired through code) |
| Public display name | OPEN (brand team) |
| All color hexes + token names | OPEN (design team) |
| Typography face(s) and scale | OPEN (design team) — must cover Cyrillic, must bundle locally **(FLOOR)** |
| Iconography style + mark concept | OPEN (design team) — must ship at 16/48/128 px PNG with file-size floors **(FLOOR)** |
| Spacing scale, corner radii, motion | OPEN (design team) |
| Brand voice, tagline, copy | OPEN (brand team) |
| Welcome-tab layout + treatment | OPEN (design team) |
| WCAG AA contrast | **FLOOR** (legal/accessibility — not creative) |
| Chrome notification API icon ≥ 128 px | **FLOOR** |
| MV3 CSP (no remote fonts/scripts, no `unsafe-eval`) | **FLOOR** |
| Toolbar badge text max 4 chars | **FLOOR** (Chrome truncates) |
| Russian-first audience | **FLOOR** (product, not visual) — visuals must work without depending on language for legibility |
Everything below is engineering's current sketch, framed as starting options,
unless explicitly tagged **(FLOOR)**.
---
## 1. Brand voice *(OPEN — brand team)*
Engineering has no opinion. Axes to decide:
- **Warmth** — clinical / neutral / warm / friendly
- **Formality** — system-terse / professional / conversational / casual
- **Humour** — none / dry / occasional / playful
- **Emoji policy** — never / functional only (✓ × ⚠) / freely
- **Two-register vs single-register** — toolbar/notification copy can match welcome-tab copy, or diverge (e.g. terse system messages vs full-prose onboarding)
Engineering's current placeholder voice in shipped strings is *calm, brief,
operationally serious* — chosen because the product runs for operators under
stress. This is a defensible starting point and equally defensible to replace
entirely.
---
## 2. Identity *(OPEN except codename)*
| | |
|---|---|
| Codename **(LOCKED)** | Mokosh — Slavic goddess of weaving and fate |
| Public display name *(OPEN — brand)* | Currently placeholder `"AI Call Recorder"`. See `brand-identity.md` §2 for options. |
| Tagline *(OPEN — brand)* | Currently placeholder `"Записывает, чтобы вы могли воспроизвести."` ("Records so you can reproduce.") Replace, translate, or drop. |
| Mark concept *(OPEN — design)* | See §5 below — engineering sketches one possible direction; design team picks from anything. |
---
## 3. Color *(OPEN — design team)*
Engineering currently ships the placeholder palette below so the extension
runs. **Every hex is open. Every token name is open. The whole palette
strategy is open.**
### 3.1 Engineering's current placeholder palette
| Token | Hex | Currently used for |
|---|---|---|
| `--mks-rec` | `#00C853` | Toolbar badge background when recording (Material Green A700) |
| `--mks-off` | `#9E9E9E` | Toolbar badge background when idle |
| `--mks-error` | `#FFB300` | Toolbar badge background on recoverable error (Material Amber 600) |
| `--mks-fatal` | `#D32F2F` | Toolbar badge background on unrecoverable state (Material Red 700) |
| `--mks-surface-bg` | `#222222` | Smoke-test page / dark popup surfaces |
| `--mks-surface-text` | `#EEEEEE` | Text on dark surfaces |
| `--mks-popup-bg-light` | `#FFFFFF` | Popup background, light Chrome theme |
| `--mks-popup-bg-dark` | `#1F1F1F` | Popup background, dark Chrome theme |
| `--mks-diag-bg` / `--mks-diag-fg` | `#000000` / `#00FF00` | Smoke-test timer overlay (dev-only — keep monospace + high-contrast for legibility, but recolor freely) |
### 3.2 Palette directions for the design team to choose from
Direction matters more than specific hexes. Options without ranking:
- **Dark-mode-native, monochrome + single accent for "recording"** (current placeholder)
- **Light-mode primary with dark-mode variant**
- **Multi-accent** — separate distinguishing color per state beyond just green/yellow/red
- **Warm / earthy** — browns, ochres, off-whites
- **Cool / clinical** — blues, grays, white
- **High-contrast monochrome** — pure black/white + one accent
- **Whatever the design team coins**
### 3.3 Mechanical hooks the palette has to fill
(Not creative — these are surfaces engineering wires colors into.)
- `chrome.action.setBadgeBackgroundColor(...)` — one color per toolbar badge state
- Popup background + text (two themes if supporting both Chrome light/dark)
- Welcome-tab background + text
- Smoke-test diagnostic overlay (dev-only — design team can ignore)
If the design team lands on N states beyond recording/idle/error, engineering
adapts the badge wiring.
---
## 4. Typography *(OPEN — design team, with one floor)*
Engineering ships system stack as a placeholder. Open to replacement.
### 4.1 Technical floor **(FLOOR — KEEP)**
- **Must cover Cyrillic glyphs.** Russian operators are primary. Latin-only faces are non-starters.
- **Must bundle locally.** MV3 CSP forbids remote `@font-face` from external CDNs. Any custom face ships as a static asset in `dist/`.
- **Should not block the service worker.** The SW has no DOM and renders no text; this only matters for popup + welcome.
### 4.2 Engineering's current placeholder stack
| Family token | Stack | Currently used for |
|---|---|---|
| `--mks-font-ui` | `-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif` | All UI text |
| `--mks-font-mono` | `"SF Mono", Menlo, Consolas, "Courier New", monospace` | Diagnostic overlays, code, timer |
Chosen for zero-load, no FOUT, automatic Cyrillic coverage on every OS.
**Equally valid:** a licensed custom face (Inter, IBM Plex Sans, JetBrains
Mono, or anything), variable fonts, a type pair, a different system fallback
chain.
### 4.3 Engineering's current type scale (placeholder)
| Token | Size | Line-height | Currently used for |
|---|---|---|---|
| `--mks-text-xs` | 11px | 1.3 | Badge labels, footnotes |
| `--mks-text-sm` | 13px | 1.4 | Secondary UI text |
| `--mks-text-base` | 15px | 1.5 | Body text |
| `--mks-text-lg` | 18px | 1.4 | Section headings within popup |
| `--mks-text-xl` | 24px | 1.3 | Welcome page H1 |
| `--mks-text-xxl` | 32px | 1.2 | Diagnostic timer, large status |
Replace freely. Modular scale, fluid type, t-shirt sizes — design team picks.
### 4.4 Engineering's current weight ladder (placeholder)
- 400 (regular), 500 (medium), 700 (bold)
Replace freely.
---
## 5. Iconography *(OPEN — design team, with floors)*
### 5.1 Technical floors **(FLOOR — KEEP)**
- Sized PNGs at **16, 48, 128 px** in `dist/icons/`, declared in `manifest.json:icons` and `manifest.json:action.default_icon`
- The **128 px is required** for `chrome.notifications.create({type:'basic'})` to render an iconUrl
- File-size minimums per `assets-spec.md` (Chrome silently rejects icons below ~200 B / 500 B / 1 KB at the three sizes)
- Optional 192 px variant for hi-DPI notification rendering
- Inline SVG preferred for popup/welcome surfaces where Chrome permits — sharper at all DPIs. Chrome's `notifications.create` REQUIRES PNG `iconUrl` though.
### 5.2 Engineering's current placeholder direction
Solid-filled, 24×24 source grid with 2 px padding, neutral mark + state via
badge (the toolbar icon itself doesn't change between idle/recording — the
`chrome.action.setBadgeBackgroundColor` does the state work).
**This is one of many possible directions.** Equally valid:
- Line-only icons
- Mixed (solid for primary, line for secondary)
- Per-state icon swaps via `chrome.action.setIcon` (adds perf cost — see §7)
- Animated SVG icons
- Illustrated mark (full scene rather than abstract glyph)
### 5.3 Mark concept *(OPEN — design team)*
Engineering's current placeholder is "dark square + green dot" via
ImageMagick. **No mark direction is implied.** Possible directions:
- Recording-dot inside a frame (conventional, immediately readable as "records")
- Thread/spool/weave motif (leans into the Mokosh etymology)
- Abstract geometric mark (no figurative reference)
- Wordmark only (the letterforms are the mark)
- Illustrated mascot
- Whatever the design team coins
Constraints: must resolve at 16 px (a strong silhouette is hard at that size),
must work neutral OR colored (depending on the team's badge-vs-icon-state
decision).
### 5.4 Inline glyphs *(OPEN — design team)*
The popup and welcome surfaces need glyphs for actions and states. Concepts
engineering currently shows:
| Concept | Currently shown as | Design-team-owned |
|---|---|---|
| Save / download | ⬇ filled-arrow-into-tray (Unicode, placeholder) | Replace with custom glyph or icon font |
| Stop | ■ filled-square (placeholder) | — |
| Recording active | ● solid-circle (placeholder) | — |
| Error | ▲ filled-triangle with `!` (placeholder) | — |
| Settings | ⚙ filled-gear (placeholder; not currently surfaced) | — |
| Welcome / intro | 🧵 thread emoji (smoke-test placeholder only) | Replace at design time |
---
## 6. Spacing *(OPEN — design team)*
Engineering currently uses a **4 px base** with the steps below as
placeholders. Replace with any base (8 px, variable, t-shirt sizes,
golden-ratio, etc.).
| Token | Value | Currently used for |
|---|---|---|
| `--mks-space-1` | 4px | Tight padding within badges |
| `--mks-space-2` | 8px | Default padding inside controls |
| `--mks-space-3` | 12px | Padding inside popup containers |
| `--mks-space-4` | 16px | Section separation |
| `--mks-space-6` | 24px | Welcome page section gaps |
| `--mks-space-8` | 32px | Welcome page hero spacing |
### 6.1 Surface sizing — current placeholders + technical floors
| Surface | Engineering's placeholder | Floor / mechanism |
|---|---|---|
| Popup | 320 × 200 (comfortable; Chrome auto-sizes) | Chrome popups auto-size; no hard max |
| Welcome page | full viewport, content max-width 720 px | None — fully open |
| Notification | Chrome-controlled (~360 px wide) | **(FLOOR)** — not styleable |
| Toolbar badge text | max 4 chars | **(FLOOR)** — Chrome truncates beyond |
---
## 7. Motion *(OPEN — design team)*
Engineering currently ships near-zero motion (200300 ms opacity fades, no
bounce) because the product promise is unobtrusiveness. **Equally valid:**
- Lively spring physics
- Fully static (no transitions at all)
- Cinematic entrances on welcome
- Subtle micro-interactions on every state change
Engineering's current placeholder durations:
| Where | Duration | Easing | Notes |
|---|---|---|---|
| Hover transitions | 150ms | `ease-out` | Buttons, links |
| Badge state change | instant | — | No animation (Chrome badge API doesn't support; setIcon swap interval would cost perf) |
| Welcome page CTA hover | 200ms | `ease-out` | Background-color + slight scale |
| Notification slide | Chrome default | — | **(FLOOR)** — not controllable |
Per-state icon swap animation (e.g. recording-pulse) is possible but adds
`setIcon` interval cost; design team picks if worth it.
---
## 8. Component conventions
Two layers per component: **functional contract** (KEEP — comes from PLAN,
not creative direction) and **visual treatment** (OPEN — design team).
### 8.1 Toolbar action (`chrome.action`)
**Functional contract (KEEP):**
- Three states surface to operators: IDLE, REC, ERROR (some teams add OFF as a distinct post-stop state)
- Click behavior depends on state — IDLE click starts recording; REC click opens SAVE popup; ERROR click opens RESTART popup
- Tooltip text changes per state via `chrome.action.setTitle`
**Visual treatment (OPEN):**
- Badge background color per state (currently mapped to `--mks-rec` / `--mks-off` / `--mks-error`)
- Badge text per state (currently `""` / `"REC"` / `"ERR"` / `"OFF"`)
- Tooltip wording (currently Russian, placeholder copy below — brand team rewrites)
- IDLE: `"Mokosh — щёлкните, чтобы начать запись"`
- REC: `"Mokosh — идёт запись (00:42)"`
- ERROR: `"Mokosh — ошибка записи, щёлкните для восстановления"`
### 8.2 Notification
**Functional contract (KEEP):**
- Fired via `chrome.notifications.create({type:'basic', iconUrl, title, message, priority})`
- `iconUrl` must be a ≥128 px PNG via `chrome.runtime.getURL` **(FLOOR)**
- Fires on startup (until operator dismisses), on recovery (after user-stopped-sharing), optionally on save-complete (Phase 5 candidate)
- One notification per state transition (no spam)
**Visual treatment (OPEN):**
- Title text (currently `"Mokosh"`)
- Message text (brand team rewrites)
- `priority` (1 default, 2 for urgent — design team can pick when to escalate)
### 8.3 Popup (current scope: SAVE-only per Plan 01-09)
**Functional contract (KEEP):**
- Represents the current toolbar state (REC / ERROR; IDLE shouldn't normally surface here)
- REC state offers a single primary action: save the buffered archive
- ERROR state offers a single primary action: restart recording
- No secondary actions in either state (Plan 01-09 scope decision)
**Visual treatment (OPEN):**
- Sizing (current placeholder 320 × 200)
- CTA wording (current placeholder Russian; brand team rewrites)
- Layout (CTA position, status line, footer)
- Status messaging copy
- Dark/light theme handling (current placeholder: auto via `prefers-color-scheme`)
### 8.4 Welcome page (Plan 01-10)
**Functional contract (KEEP):**
- Opens via `chrome.tabs.create` on first install
- Static HTML/CSS/JS in `dist/` (no remote loads **(FLOOR)**)
- Must communicate: what Mokosh does, how the operator triggers a save, privacy story
**Visual treatment (OPEN — design team owns entirely):**
- Layout (hero + steps, scrolling story, modal, video walkthrough, anything)
- Tone (welcome cheer vs sober briefing — brand team)
- Hero treatment (wordmark-only, mark + wordmark, illustrated scene, video)
- Primary CTA wording + placement
- Whether there's a CTA at all (some onboarding flows just inform)
---
## 9. Accessibility & internationalization *(FLOORS — KEEP)*
These are functional/legal floors, not creative:
- **Contrast: WCAG AA** (4.5:1 normal text, 3:1 large text). Any palette the design team lands on must validate against this for all state pairings. Engineering's current placeholder palette is pre-validated; new palettes need re-validation.
- **Focus indicators:** visible focus rings on all interactive elements (popup buttons, welcome CTA). Chrome's default `outline` works; custom focus styles welcome as long as they remain visible.
- **Color-independence:** every color-coded state must pair with text or shape. Color alone is not an accessible state indicator — pairs with badge labels, glyphs, or copy.
- **Russian-first localization:** all user-facing strings ship in Russian as the default locale. UI scaffolding must support future locales via Chrome's `_locales/` mechanism.
- **Reduced motion:** if any animation is enabled, honor `prefers-reduced-motion: reduce` by falling back to static.
---
## 10. Open creative decisions
Non-exhaustive list for both teams. None block engineering today
(placeholders ship); each unlocks a polish pass when answered.
1. Public display name (`brand-identity.md` §2)
2. Design system name (`brand-identity.md` §3)
3. Voice register — one tone or two (system-terse vs welcome-prose)
4. Tagline final wording (currently `"Записывает, чтобы вы могли воспроизвести."`)
5. Palette direction (§3.2) + specific hexes
6. Token naming convention (`--mks-rec` placeholder pattern)
7. Typography face(s) — system stack vs custom
8. Type scale + weight ladder
9. Spacing base + steps
10. Corner radii — sharp / soft / mixed
11. Iconography style — solid / line / mixed
12. Mark concept (§5.3)
13. Per-state icon swaps vs fixed mark + dynamic badge
14. Motion vocabulary — minimal / lively / static
15. Welcome-tab layout + treatment (§8.4)
16. Popup layout treatment (§8.3 visual)
17. Notification copy + tone (§8.2)
18. Tooltip wording per state (§8.1)
19. Dark/light theme strategy — auto-detect, follow-Chrome, force one, user-toggle
---
## 11. Implementation notes *(TECHNICAL — KEEP)*
- All extension contexts (SW, offscreen, popup, welcome page) share the same CSP. No external font/asset loads. Everything bundled or `chrome.runtime.getURL`. **(FLOOR)**
- Icons must be in `dist/icons/` and declared in both `manifest.json:icons` AND `manifest.json:action.default_icon`. **(FLOOR)**
- Notification iconUrl uses `chrome.runtime.getURL('icons/icon128.png')` — at least 128 × 128, ideally 192 × 192 for retina. Smaller icons silently fail Chrome's `imageUtil` validation. **(FLOOR)**
- All popup HTML/CSS lives in `src/popup/`. All welcome HTML/CSS lives in `src/welcome/` (Plan 01-10). **(file convention — easy to change)**
- Inline SVG preferred over PNG where the surface permits — sharper at all DPIs. Notification API requires PNG. **(FLOOR for notification only)**
---
## 12. Related
- `brand-identity.md` — naming + blurb + voice (Brief #1)
- `assets-spec.md` — concrete file deliverables + technical floors
- `src/background/index.ts` — implements toolbar action + notification per §8
- `src/popup/index.html` — implements popup per §8.3
- `src/welcome/welcome.html` — implements welcome per §8.4 (Plan 01-10)
- `.planning/phases/01-stabilize-video-pipeline/01-CONTEXT.md` D-15/D-16/D-17 amendments — interaction model this design language sits inside