# HyperFrames Composition Project

## Scope

- This file applies to `apps/promo-video`, the HyperFrames composition workspace.
- Keep the root `AGENTS.md` in mind for workspace and generated-output rules.
- Do not edit generated `renders`, `.thumbnails`, or `.waveform-cache` output.

## Skills

This project uses AI agent skills for framework-specific patterns. Install them if not already present:

```bash
npx skills add heygen-com/hyperframes
```

Skills encode patterns like `window.__timelines` registration, `data-*` attribute semantics, Tailwind v4 browser-runtime styling for `--tailwind` projects, and shader-compatible CSS rules that are not in generic web docs. Using them produces correct compositions from the start.

## Commands

```bash
pnpm --filter ./apps/promo-video dev     # preview in browser (studio editor)
pnpm --filter ./apps/promo-video check   # lint + validate + inspect
pnpm --filter ./apps/promo-video render  # render to MP4
pnpm --filter ./apps/promo-video publish # publish and get a shareable link
npx hyperframes docs <topic> # reference docs in terminal
```

Root shortcuts exist for common checks: `pnpm check:promo`, `pnpm build:promo`, and `pnpm render:promo`.

## Project Structure

- `index.html` — main composition (root timeline)
- `compositions/` — sub-compositions referenced via `data-composition-src`
- `assets/` — media files (video, audio, images)
- `meta.json` — project metadata (id, name)
- `transcript.json` — whisper word-level transcript (if generated)

## Linting — Always Run After Changes

After creating or editing any `.html` composition, run the full check before considering the task complete:

```bash
pnpm --filter ./apps/promo-video check
```

Fix all errors before presenting the result.

## Key Rules

1. Every timed element needs `data-start`, `data-duration`, and `data-track-index`
2. Visible timed elements **must** have `class="clip"` — the framework uses this for visibility control
3. GSAP timelines must be paused and registered on `window.__timelines`:
   ```js
   window.__timelines = window.__timelines || {};
   window.__timelines["composition-id"] = gsap.timeline({ paused: true });
   ```
4. Videos use `muted` with a separate `<audio>` element for the audio track
5. Sub-compositions use `data-composition-src="compositions/file.html"`
6. Only deterministic logic — no `Date.now()`, no `Math.random()`, no network fetches

## Documentation

Full docs: https://hyperframes.heygen.com/introduction

Machine-readable index for AI tools: https://hyperframes.heygen.com/llms.txt
