Skip to content

0003 timer surface tiers

github-actions[bot] edited this page Oct 21, 2026 · 2 revisions

3. Timer surface tiers

Date: 2026-10-20 Status: Accepted Decides: which timer surface renders on which host Design source: Kimi_Agent_WOD Timer UI Prototypes/app/index.html (three-tier ladder)

Context

The playground had one timer surface (Detail: TimerStackView via TimerDisplay) on every host at every size, plus a Chromecast receiver surface and (since #1078) a mobile Minimal surface. The prototype defines a three-tier capability ladder — general = minimal

  • context (chips, session clock, title), detail = general + time axis (audit, queue, header chrome) — and one shared core (TimerCore) underneath all tiers.

Decision

  1. Tier = container size, taken from the existing PanelSizeMode ladder — no new breakpoints:

    PanelSizeMode Container width Tier Surface
    compact < 500px Minimal MinimalTimerSurface
    wide ≥ 500px General GeneralTimerSurface (full hero at any height¹)
    full ≥ 900px Detail TimerDisplay (StackIntegratedTimer + TimerStackView)

    ¹ Amended 2026-10-20: the mode="strip" short-host compression was removed. One General view renders everywhere the tier renders — including the cast receiver, which already overrode the ladder (decision 2). The strip's single-row layout read as a "wide line" on TV-shaped hosts and duplicated the surface for a rare host shape.

    TimerSurface (apps/playground/src/components/organisms/workout/TimerSurface.tsx) is the single picker; hosts mount it instead of choosing themselves.

  2. The cast receiver overrides the ladder: receiver-rpc.tsx mounts GeneralTimerSurface directly — the TV is General at any pixel size.

  3. Strict ladder for history/audit chrome: VisualStatePanel (stack history, Up Next card) renders only alongside Detail (full). Wide hosts show General alone.

  4. Live metric prompts (session-total bubbles via MetricTrackerCard) render on Minimal and General at every host height (the strip exception retired with the amendment to decision 1). In-run input prompts stay Detail-only until an input design exists.

  5. Detail keeps its own richer derivation (StackIntegratedTimer); the shared useTimerSurfaceModel deliberately re-derives the subset Minimal/General need. Consolidate only if the two derivations drift.

Consequences

  • Wide browser hosts (editor timer pane, track view, /run/:id on tablets) lose the stack view; that is intended — audit is a largest-screen capability.
  • Dead Detail-only paths in hosts that no longer show Detail are deleted at cutover, not shimmed.
  • Adding a fourth tier or changing thresholds touches PanelSizeContext + TimerSurface only.

Clone this wiki locally