feat(statistics-deck): Day view (Room, Desk, Laptop) #134

Closed
opened 2026-09-26 11:29:16 +00:00 by gabogg · 0 comments
Owner

Blocked by: #133

Part of the statistics deck UI (accepted RFC, #80). This issue is the Day view in its three profiles. The shell (#133) provides the frame, top bar, picker, keyboard and marker helpers.

Content (RFC §4)

KPIs, most important first:

  1. Visitors, vs the same weekday last week, and also vs the same day last year when that data exists;
  2. vs usual weekday (Usual Weekday Baseline);
  3. peak people inside;
  4. average visit (open-window Mean Dwell);
  5. busiest hour;
  6. top entrance (ESTIMATED attribution shown as such).

Graphs, most important first:

  1. Visitors by hour vs the Usual Weekday Baseline;
  2. People inside over the day;
  3. Entrance share, with year-on-year change;
  4. Daypart split vs usual, each daypart labelled with its clock span (UsualDaypart.label; when it is null, show no span).

Data

  • GET /api/statistics/periods/day/{date}/summary: the KPIs.
  • GET /api/statistics/timeseries/hourly?baseline=usual_weekday: visitors by hour, and people inside (cumulative_occupancy). Ignore margin_upper / margin_lower.
  • GET /api/statistics/periods/day/{date}/entrances: entrance share.
  • GET /api/statistics/dwell/dayparts?baseline=usual_weekday: the daypart split.

Day-view marker (RFC §4.1)

  • Hatch the buckets whose gap_estimated is set on "visitors by hour" and "people inside" (the per-bucket flag comes from #129).
  • An Unreliable day greys out all its graphs.
  • The badge shows as in the shell.

Profiles

Room shows 6 KPIs and 4–5 graphs, Desk 4 KPIs and 3 graphs, Laptop 3 KPIs and 1 graph. Each smaller profile keeps the top of the ranking below (KPIs and graphs are listed most important first). Each profile is its own layout, not a crop (RFC §3.3), and follows the zero-scroll rule and row splits from the shell.

Rules that apply to every figure

  • Comparisons: the previous period first; last year only when it has data. A missing reference shows "—" with its reason, never 0%. Partial periods compare by daily average only when the route returns basis: DAILY_AVERAGE.
  • Data-quality marker (RFC §4.1): totals and averages include marked days. Records come from the route, which skips Unreliable days (#129). Mark graphs with the shell's shared Estimate / Unreliable styles. No per-KPI marks, and no confidence margins.
  • Holidays are marked on per-day graphs. Closed Days are shown as closed, not as missing.
  • All copy goes through i18n (es/en).

Acceptance

  • All three profiles render from live routes with no scroll at 1920×1080 and 1920×960.
  • "—" with a reason when there is no baseline, no last-week data or no last-year data.
  • A gap-estimated day hatches exactly the flagged buckets; an excluded day greys out.
  • Frontend tests cover the view's data mapping (route JSON to KPI and graph inputs), including the missing-reference and marker cases.

Depends on #133 and #129. Refs #80.

🤖 Generated with Claude Code

Blocked by: #133 Part of the statistics deck UI (accepted RFC, #80). This issue is the **Day** view in its three profiles. The shell (#133) provides the frame, top bar, picker, keyboard and marker helpers. ## Content (RFC §4) **KPIs, most important first:** 1. Visitors, vs the same weekday last week, and also vs the same day last year when that data exists; 2. vs usual weekday (Usual Weekday Baseline); 3. peak people inside; 4. average visit (open-window Mean Dwell); 5. busiest hour; 6. top entrance (`ESTIMATED` attribution shown as such). **Graphs, most important first:** 1. Visitors by hour vs the Usual Weekday Baseline; 2. People inside over the day; 3. Entrance share, with year-on-year change; 4. Daypart split vs usual, each daypart labelled with its clock span (`UsualDaypart.label`; when it is `null`, show no span). ## Data - `GET /api/statistics/periods/day/{date}/summary`: the KPIs. - `GET /api/statistics/timeseries/hourly?baseline=usual_weekday`: visitors by hour, and people inside (`cumulative_occupancy`). Ignore `margin_upper` / `margin_lower`. - `GET /api/statistics/periods/day/{date}/entrances`: entrance share. - `GET /api/statistics/dwell/dayparts?baseline=usual_weekday`: the daypart split. ## Day-view marker (RFC §4.1) - Hatch the buckets whose `gap_estimated` is set on "visitors by hour" and "people inside" (the per-bucket flag comes from #129). - An Unreliable day greys out all its graphs. - The badge shows as in the shell. ## Profiles Room shows 6 KPIs and 4–5 graphs, Desk 4 KPIs and 3 graphs, Laptop 3 KPIs and 1 graph. Each smaller profile keeps the top of the ranking below (KPIs and graphs are listed most important first). Each profile is its own layout, not a crop (RFC §3.3), and follows the zero-scroll rule and row splits from the shell. ## Rules that apply to every figure - Comparisons: the previous period first; last year only when it has data. A missing reference shows "—" with its `reason`, never 0%. Partial periods compare by daily average only when the route returns `basis: DAILY_AVERAGE`. - Data-quality marker (RFC §4.1): totals and averages include marked days. Records come from the route, which skips Unreliable days (#129). Mark graphs with the shell's shared Estimate / Unreliable styles. No per-KPI marks, and no confidence margins. - Holidays are marked on per-day graphs. Closed Days are shown as closed, not as missing. - All copy goes through i18n (es/en). ## Acceptance - All three profiles render from live routes with no scroll at 1920×1080 and 1920×960. - "—" with a reason when there is no baseline, no last-week data or no last-year data. - A gap-estimated day hatches exactly the flagged buckets; an excluded day greys out. - Frontend tests cover the view's data mapping (route JSON to KPI and graph inputs), including the missing-reference and marker cases. Depends on #133 and #129. Refs #80. 🤖 Generated with [Claude Code](https://claude.com/claude-code)
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
gabogg/hikcentral#134
No description provided.