kimai-plugin-heatmap/.planning/phases/05-polish/05-CONTEXT.md
Christopher Mühl 843ac84805
docs: phase 5 planning artifacts
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-08 16:05:50 +02:00

3.8 KiB

Phase 5: Polish - Context

Gathered: 2026-04-08 Status: Ready for planning

## Phase Boundary

Add streak indicator, summary statistics row, and weekend visual distinction to the heatmap widget. Also integrate user's start-of-week preference from Kimai.

## Implementation Decisions

Streak Indicator

  • Count consecutive calendar days (including weekends) with tracked time, counting backward from today
  • Display as a simple text line above or below the heatmap: "Current streak: N days"
  • If today has no entries yet, check from yesterday backward (user may still be tracking today)
  • Computed client-side from the fetched heatmap data — no new API endpoint

Summary Stats Row

  • Rendered below the heatmap SVG, inside the same Tabler card
  • Three stats: Total Hours, Avg Hours/Day (days with tracked time only), Busiest Day
  • Computed client-side from the fetched heatmap data array
  • Styled as inline stat items using Tabler's existing typography classes
  • "Busiest Day" shows date + hours (e.g., "Mar 15 — 8.5h")

Weekend Styling

  • Weekend cells (Saturday/Sunday) get reduced opacity (0.85) compared to weekday cells
  • Applied via CSS class .heatmap-weekend with opacity rule
  • Empty weekend cells also get the distinction so the grid pattern is visible
  • No border changes — keep existing rounded rect style

Start-of-Week Preference

  • Read user's first_weekday from Kimai (exposed via User entity or system config)
  • Pass as data-week-start attribute on the container div (0=Sunday, 1=Monday, etc.)
  • Use in d3 grid layout to set which day is row 0
  • Adjust day-of-week labels to match
  • Default to Monday if not available (current behavior)

Testing Strategy

  • Vitest tests for streak calculation (consecutive days, gaps, weekend inclusion, today edge case)
  • Vitest tests for summary stats computation (totals, averages, busiest day)
  • Vitest tests for weekend cell class assignment
  • CSS changes don't need unit tests — visual verification

Claude's Discretion

  • Exact Tabler CSS classes for the stats row layout
  • How to extract first_weekday from Kimai's User entity (check source)
  • Whether streak resets on weekends or not (decision: it does — every calendar day counts)
  • d3 time interval function for configurable week start (d3.timeSunday vs d3.timeMonday etc.)

<code_context>

Existing Code Insights

Reusable Assets

  • renderHeatmap(container, data, config) — main render, needs extension for weekend classes and stats
  • init() — fetches data and calls render, will also compute streak/stats after data arrives
  • HeatmapData.days array — source for all client-side computations
  • generateCells() helper — can add weekend detection here
  • HeatmapWidget::getData() — can add weekStart to template data

Established Patterns

  • d3 selections for SVG element class assignment
  • Data attributes on container div for passing server config to JS
  • Tabler card structure with widget template embedding
  • CSS classes added to cells based on data state (.heatmap-empty)

Integration Points

  • heatmap.html.twig — add data-week-start attribute, stats container div
  • heatmap.css — add .heatmap-weekend, .heatmap-stats styles
  • heatmap.ts — extend renderHeatmap for weekends, add streak/stats functions
  • HeatmapWidget.php — pass user's week start preference to template

</code_context>

## Specific Ideas
  • Memory note: heatmap must respect Kimai user's start-of-week preference (not hardcoded Monday)
  • Stats should feel lightweight — not a full stats panel, just quick context below the heatmap
## Deferred Ideas

None — all three requirements (POLI-01, POLI-02, POLI-03) plus start-of-week fit within polish scope.