# Milestone v1.1: UI Overhaul

**Status:** ✅ SHIPPED 2026-02-28
**Phases:** 4–6
**Total Plans:** 6 (2 per phase)

## Overview

Complete rebuild of the main screen as a flat item list, replacing the drill-down rooms→containers→items state machine. Added splash screen, persistent top bar, stats bar, item detail panel, terminal-native theme colors, and VIM-style keyboard filter pickers for Room, Container, and Category.

## Phases

### Phase 4: Foundation — Flat List + Visual Chrome

**Goal**: The drill-down state machine is gone; users see all items in a flat list immediately, with top bar, splash screen, and corrected quick-add label.
**Depends on**: Phase 3
**Requirements**: VIEW-01, TOPBAR-01, THEME-01, QADD-04, SPSH-01
**Plans**: 2 plans

Plans:
- [x] 04-01: Remove drill-down state machine, add flat list and Possession top bar (VIEW-01, TOPBAR-01)
- [x] 04-02: Add splash screen, transparent flag, and QuickAddBar format label (SPSH-01, THEME-01, QADD-04)

**Details:**
- Removed five-variable drill-down state machine (`_view_mode`, `_current_room_id`, `_current_room_name`, `_current_container_id`, `_current_container_name`) from MainScreen
- Single `_load_items()` → `_apply_filter()` data path replaces three-way branch
- `Static("Possession", id="topbar")` docked at top, always visible
- SplashScreen with ASCII art; any key calls `switch_screen(MainScreen())`
- `--transparent` flag toggles self.CSS instance attribute between two CSS blocks
- QuickAddBar: Static label + borderless Input, always-visible format hint
- Completed: 2026-02-25

### Phase 5: Data Surface — Stats Bar + Detail Panel

**Goal**: The flat list is enriched with live stats and per-item detail view.
**Depends on**: Phase 4
**Requirements**: STAT-01, PANEL-01
**Plans**: 2 plans

Plans:
- [x] 05-01: Add get_stats() aggregate query, StatsBar widget, and DetailPanel widget (STAT-01, PANEL-01)
- [x] 05-02: Wire StatsBar and DetailPanel into MainScreen with live updates and toggle behavior (STAT-01, PANEL-01)

**Details:**
- `get_stats()` aggregate query in models.py returns item_count, room_count, container_count, total_value in one SQL call
- StatsBar widget: 4-column Horizontal layout (Items | Rooms | Containers | Value), always docked below topbar
- DetailPanel widget: `show_item()` populates 7 Label widgets for all item fields
- MainScreen: Horizontal layout (DataTable + DetailPanel), Enter-to-toggle panel, Escape collapses
- `_refresh_stats()` called on every load, add, edit, delete
- Completed: 2026-02-28

### Phase 6: Keyboard UX — Filter Pickers

**Goal**: Users can narrow the flat list by Room, Container, or Category using VIM-style keyboard-driven modal pickers.
**Depends on**: Phase 5
**Requirements**: FILT-01, FILT-02, FILT-03
**Plans**: 2 plans

Plans:
- [x] 06-01: Create FilterPickerScreen reusable modal (FILT-01, FILT-02, FILT-03)
- [x] 06-02: Wire r/c/t bindings, filter state, StatsBar tags, and zero-match state into MainScreen (FILT-01, FILT-02, FILT-03)

**Details:**
- `FilterPickerScreen(ModalScreen)`: data-agnostic (receives items list as parameter, never imports models)
- Type-ahead Input filters list live; j/k navigate; Enter/Escape confirm/cancel
- Active filter floats to top with "✓" marker; highlighted active item shows "Enter to clear filter" hint
- MainScreen: 6 filter state fields, r/c/t bindings, `_build_filter_tags()`, `_any_filter_active()`, toggle-to-clear behavior
- `_load_items()` passes filter IDs to `list_items()` for SQL-level filtering (not client-side)
- Zero-match empty-state row in DataTable when filters active but no results
- Completed: 2026-02-28

---

## Milestone Summary

**Key Decisions:**

- Flat list replaces drill-down as the primary interaction model — spatial hierarchy removed from TUI, preserved only in data model
- `switch_screen(MainScreen())` in SplashScreen instead of `pop_screen()` — prevents DataTable rendering behind transparent splash
- `self.CSS` instance override (not class-level) for transparent theme toggle — simpler than CSS class toggling
- FilterPickerScreen is data-agnostic (receives items list, never imports models) — avoids circular imports, maximizes reusability
- SQL-level filtering (passing filter IDs to `list_items()`) rather than client-side — cleaner and performant
- `await lv.clear()` in FilterPickerScreen `_rebuild_list` to prevent DuplicateIds on type-ahead fast input

**Issues Resolved:**

- DataTable rendering behind transparent splash (fixed with `switch_screen`)
- QuickAddBar layout clipping (fixed with borderless Input + height:1)
- MainScreen hiding behind splash until dismissed (fixed with on_mount push pattern)
- DuplicateIds error on fast type-ahead in FilterPickerScreen (fixed with `await lv.clear()`)

**Issues Deferred:**

- Multi-field simultaneous filters (FILT-04) — deferred to v2
- Fuzzy matching in filter pickers (FILT-05) — deferred to v2

**Technical Debt Incurred:**

- `breadcrumb.py` preserved as dead code (not deleted) — safe to remove in a future cleanup phase
- `_any_input_active()` guard in MainScreen key handling — added to prevent filter picker opening while quick-add is open; logic could be consolidated with filter state

---

*For current project status, see .planning/PROJECT.md*
