# S03: Key Moment Card Redesign — Research

**Date:** 2026-03-30

## Summary

The key moment cards in the technique page sidebar need a layout adjustment: move the title to its own prominent line, then show source filename, timestamp, and content type badge on a clean secondary metadata row. This is a straightforward CSS + minor JSX restructure within a single component file and one CSS file. No API changes, no new data fields, no new dependencies.

The cards currently render inside a 22rem sidebar (established by S02). The `.technique-moment__header` is a flex row with `flex-wrap: wrap` containing title, source, timestamp, and badge all inline. At 22rem width this wraps unpredictably. The fix is to split the header into two explicit rows: a title row and a metadata row.

## Recommendation

Restructure the card JSX to separate the title from the metadata. The title becomes a standalone element outside the metadata row. The metadata row (source filename, timestamp, content type badge) becomes its own flex container. This gives the title full width and visual prominence, while metadata items stay compact on a single secondary line.

No need for new CSS custom properties — the existing `--color-text-secondary`, `--color-text-muted`, and badge variables cover everything. The summary paragraph below the header remains unchanged.

## Implementation Landscape

### Key Files

- `frontend/src/pages/TechniquePage.tsx` (lines 413–430) — Key moment card JSX. Currently renders a single `.technique-moment__header` div with title, source, timestamp, and badge as siblings. Needs restructuring: title pulled out of header, header renamed/repurposed to metadata row.
- `frontend/src/App.css` (lines 1337–1380) — Key moment card styles. `.technique-moment__header` is `display: flex; align-items: center; gap: 0.5rem; flex-wrap: wrap`. Needs: title gets its own block-level style, header becomes a metadata-only flex row with smaller gap.
- `frontend/src/api/public-client.ts` (line 29) — `KeyMomentSummary` interface. No changes needed — all required fields (`title`, `video_filename`, `start_time`, `end_time`, `content_type`) already exist.

### Current Card Structure (JSX)
```
<li className="technique-moment">
  <div className="technique-moment__header">     ← single flex row
    <span className="technique-moment__title">   ← title inline with metadata
    <span className="technique-moment__source">  ← source filename
    <span className="technique-moment__time">    ← timestamp range
    <span className="badge badge--content-type"> ← type badge
  </div>
  <p className="technique-moment__summary">      ← summary text
</li>
```

### Target Card Structure (JSX)
```
<li className="technique-moment">
  <h3 className="technique-moment__title">       ← title on its own line, prominent
  <div className="technique-moment__meta">        ← metadata row
    <span className="technique-moment__source">   ← source filename
    <span className="technique-moment__time">     ← timestamp range
    <span className="badge badge--content-type">  ← type badge
  </div>
  <p className="technique-moment__summary">       ← summary text (unchanged)
</li>
```

### Build Order

1. Restructure JSX in TechniquePage.tsx — pull title out of header div, rename header to `__meta`, change title from `<span>` to block-level element
2. Update CSS in App.css — adjust `.technique-moment__title` to block display with bottom margin, add `.technique-moment__meta` as the flex row (inheriting current `__header` styles with adjustments), remove or redirect `__header` styles
3. Verify at desktop (22rem sidebar) and mobile (single column) widths

Single task — the JSX and CSS changes are tightly coupled and should be done together.

### Verification Approach

- `npx tsc --noEmit` — TypeScript compiles cleanly
- `npm run build` — production build succeeds
- Visual check at desktop width: title is on its own line, metadata items (source, timestamp, badge) are on a secondary row
- Visual check at mobile width (≤768px): card still renders cleanly in single-column layout
- No hardcoded colors in new/modified CSS rules (all use existing custom properties)

## Constraints

- Sidebar width is fixed at 22rem (D019). Card must look good within this constraint.
- Existing badge classes (`.badge`, `.badge--content-type`) must not be modified — they're shared across the app.
- No new CSS custom properties needed — existing color tokens cover the design.
- The `<ol>` list wrapper and `<li>` card container structure should be preserved for semantic correctness.
