---
name: Components
type: architecture-map-page
slice: 01-frontend
last_verified: 2026/05/09
---

# Components

> **Where you are:** [Architecture map](../README.md) → [Frontend](README.md) → Components

**Plain English summary.** All 25 reusable Svelte 5 components, plus `Sidebar.svelte` which is the only component that lives at `src/lib/Sidebar.svelte` rather than under `src/lib/components/`. Grouped by what they do. Where a component is mounted directly by the shell (`+layout.svelte`), that is called out.

## At a glance

- **Path:** `src/lib/components/` (25 files), plus `src/lib/Sidebar.svelte`.
- **LOC:** 3 174 (components) + 178 (sidebar) = 3 352.
- **Conventions:** Svelte 5 runes (`$state`, `$props`, `$derived`, `$effect`). Tailwind v4 utility classes. CSS variables for design tokens. Lucide icons at 16/20/24px with `aria-label` next to or instead of the glyph.

## Shell mounts (always present)

| Component | LOC | Path | Purpose |
|---|---|---|---|
| `Sidebar` | 178 | `src/lib/Sidebar.svelte` | Left nav. Switches `page.current`. Collapsed mode shows tooltips. Renders task badge from `tasks.length`. |
| `Titlebar` | 80 | `src/lib/components/Titlebar.svelte` | Custom window chrome for non Linux (frameless windows). Min/max/close + drag area + sidebar aligned spacer. |
| `ToastViewport` | 143 | `src/lib/components/ToastViewport.svelte` | Bottom right toast stack. Reads from the global `toasts` store. Honours `prefers-reduced-motion`. |
| `ResizeHandles` | 67 | `src/lib/components/ResizeHandles.svelte` | Invisible 5 px margins for frameless resize. Linux uses native, so `+layout.svelte` suppresses this. |
| `FocusTimer` | 298 | `src/lib/components/FocusTimer.svelte` | Floating top right SVG progress ring. Listens for `lumotia:start-timer` window events and delegates to the focus timer store. Cancel hover, success flourish. Hidden on float and viewer windows by URL probe. |
| `MorningTriageModal` | 356 | `src/lib/components/MorningTriageModal.svelte` | Phase 5 modal. Self gated on `settings.ritualsMorning` and time of day. Mounted globally so it appears over any page. |
| `TaskSidebar` | 97 | `src/lib/components/TaskSidebar.svelte` | Optional right side dock that appears when `page.taskSidebarOpen`. Quick add input, top tasks, link out to the full Tasks page. |

## Settings building blocks

| Component | LOC | Purpose |
|---|---|---|
| `SettingsGroup` | 86 | Native `<details>` based progressive disclosure with animated chevron. Handler hooks (`onopen`) are used by SettingsPage to lazy probe expensive state (model lists, paste backends, etc). |
| `Toggle` | 98 | iOS style toggle. ARIA switch role. |
| `SegmentedButton` | 19 | Tiny segmented switch with ARIA radio role. |
| `HotkeyRecorder` | 217 | Captures a key combo. Uses `utils/hotkeyValidity.ts` to check the combo before persisting. |
| `ZonePicker` | 36 | Sensory zone (default / focus / dim / etc) picker that maps to a `data-zone` attribute on `<html>`. |
| `AccessibilityControls` | 112 | Font family, font size, letter spacing, line height, reduce motion, bionic reading. Writes via `updateAccessibility`. |
| `ImplementationRulesEditor` | 266 | Edits the implementation intentions list ("when X happens, do Y"). Persists via the `implementationIntentions` store. |
| `ModelDownloader` | 112 | Standalone download panel used inside Dictation when no model is loaded. Subscribes to `model-download-progress`. |

## Card chrome and empty states

| Component | LOC | Purpose |
|---|---|---|
| `Card` | 35 | Generic container. Border, padding, optional header. The page level "block" primitive. |
| `EmptyState` | 22 | Centred icon + title + body slot. Used widely. |
| `UnicodeSpinner` | 30 | ASCII spinner used while probing or downloading. |

## Tasks

| Component | LOC | Purpose |
|---|---|---|
| `WipTaskList` | 153 | Renders task rows with energy chips, completion checkbox, expansion to show micro steps, and a "start focus timer" button (dispatches `lumotia:start-timer`). |
| `MicroSteps` | 310 | Per task expansion: nudge bus integration, micro step suggestions from the LLM (`lumotia:microstep-generated`), step completion (`lumotia:step-completed`), per task implementation rules. |
| `EnergyChip` | 106 | Low/medium/high energy selector. Used on task rows and in TasksPage quick add. |
| `CompletionSparkline` | 92 | 7 day completion bar chart. Animated entrance with 30 ms stagger, respects `prefers-reduced-motion`. Reads from `recentCompletions` store. |
| `VisualTimer` | 33 | Compact visual timer pill used inside MicroSteps and the float window. |

## Transcripts

| Component | LOC | Purpose |
|---|---|---|
| `VirtualSegmentList` | 234 | Virtualised scroll for transcript segments in the viewer window. Uses `utils/virtualList.ts` and `utils/textMeasure.ts` to compute per row heights from current preferences. |
| `SpeakerButton` | 112 | Trigger TTS playback for a chunk of text. Uses `tts_speak`. Reads from the `speaker` store to debounce concurrent requests. |
| `LlmStatusChip` | 60 | Pill in the sidebar/dictation surface showing LLM state (idle, generating, downloading, unavailable). Reads `llmStatus` store. |

## Where each component is used

- `Sidebar`: `+layout.svelte` shell only.
- `Titlebar`: `+layout.svelte`, `float/+layout@.svelte`, `viewer/+layout@.svelte` (when `useCustomChrome`).
- `ToastViewport`: `+layout.svelte`, `viewer/+layout@.svelte`.
- `ResizeHandles`: `+layout.svelte` (when `useCustomChrome`).
- `FocusTimer`: `+layout.svelte`, `float/+layout@.svelte`.
- `MorningTriageModal`: `+layout.svelte`.
- `TaskSidebar`: `+layout.svelte` (when `page.taskSidebarOpen`).
- `Card`, `EmptyState`, `Toggle`, `SegmentedButton`: SettingsPage, DictationPage, HistoryPage, TasksPage, FilesPage.
- `SettingsGroup`, `HotkeyRecorder`, `ImplementationRulesEditor`, `ZonePicker`, `AccessibilityControls`: SettingsPage.
- `ModelDownloader`: DictationPage.
- `WipTaskList`, `MicroSteps`, `EnergyChip`, `CompletionSparkline`: TasksPage and `WipTaskList` reused inside the float window.
- `VirtualSegmentList`: viewer/+page.svelte.
- `SpeakerButton`: DictationPage, viewer.
- `LlmStatusChip`: Sidebar, DictationPage.
- `UnicodeSpinner`: FirstRunPage, SettingsPage.
- `VisualTimer`: MicroSteps, float window.

## Watch outs

- `Sidebar.svelte` lives outside `components/`. README debt note 1.
- `Titlebar` reads `settings.sidebarCollapsed` to mirror the spacer width. Animation timing is driven by `--duration-ui`.
- `MorningTriageModal` is heavy (356 LOC). Self gates internally; do not move the gate elsewhere or you will pay its cost on every paint.
- `FocusTimer` detects "secondary window" by URL prefix. If you add a fifth window, update the probe.
- `CompletionSparkline` animations are the only place that uses CSS keyframes for entrance. Honour reduced motion.
- Many components receive props with `let { foo = default } = $props();` (Svelte 5 idiom). The minimal `Card`, `EmptyState`, `Toggle`, `SegmentedButton` are good reading order for understanding the runes idiom on this codebase.

## See also

- [Stores](stores.md). The state these components consume.
- [Actions, utils, types](actions-utils-types.md). The bionic reading action and the typography utilities most components use.
- [Design system](design-system.md). The brand reference these components target.
