City decision cards rendered Chart.js canvases and AI evidence bodies before the user could see or expand those sections. This keeps the card shell visible while delaying chart data/canvas work until the section nears the viewport and skipping the AI evidence body while its details panel is collapsed.
Constraint: Preserve existing decision-card layout and evidence copy.
Rejected: Add list virtualization in the same pass | card-level render costs should be reduced before changing list mechanics.
Confidence: high
Scope-risk: narrow
Reversibility: clean
Tested: npm run build
Not-tested: Runtime scroll benchmark on a large production city set.
Dashboard.module.css mixed base shell styles with the entire scan terminal surface, making every decision-card or calendar styling pass risky. This extracts the scan terminal layer into its own CSS module and attaches that module root beside the existing dashboard root so global class selectors keep their current behavior.
Constraint: Preserve existing global scan-* class names and visual cascade.
Rejected: Rename scan classes into scoped module keys | too much DOM churn for a behavior-preserving CSS split.
Rejected: Split card/calendar/mobile rules in the same pass | safer to establish the scan-terminal layer first before finer component CSS ownership.
Confidence: high
Scope-risk: moderate
Reversibility: clean
Tested: npm run build
Not-tested: Pixel-level browser comparison across dark and light themes.