caption-word-reveal
Skill3 starsChanged 4 months agoMITView on GitHub
Word-by-word ("karaoke") burned-in captions for avatar reels: each word appears at the instant it's spoken, building up the SAME phrase unit in place (frozen layout, no reflow), and the phrase clears when the next one begins. Use when the user wants captions/subtitles where words form the sentence as the narration says them (word-by-word reveal, karaoke captions, "las palabras van apareciendo") on any reel produced by the avatar-reel-composer pipeline.
In this repository45 other files it gives its agents.
- asset-generatorSkill
- audio-theaterSkill
- avatar-ambient-sfxSkill
- avatar-camera-anglesSkill
- avatar-framesSkill
- avatar-inventSkill
- avatar-locationSkill
- avatar-reel-composerSkill
- avatar-talking-videoSkill
- bg-music-hqSkill
- bg-musicSkill
- brand-content-strategySkill
- broll-actor-copySkill
- broll-avatar-cameraSkill
- broll-browser-recorderSkill
- broll-coreSkill
- broll-cursorSkill
- broll-finderSkill
- broll-generatorSkill
- broll-storySkill
- broll-terminalSkill
- broll-web-captureSkill
- carousel-generatorSkill
- cuento-reelSkill
- facebook-videosSkill
- gpt-image-2Skill
- instagram-videosSkill
- luxury-hnwi-salesSkill
- onboarding-scriptSkill
- pdf-remixSkill
- reel-discoverySkill
- reel-restyleSkill
- rule-of-six-editSkill
- seedance-2Skill
- sound-effectsSkill
- tiktok-videosSkill
- video-bg-replaceSkill
- video-composeSkill
- video-remixSkill
- video-scene-analysisSkill
- video-transcribeSkill
- viral-video-scriptSkill
- voice-cloneSkill
- voice-isolateSkill
- youtube-videosSkill
The file
We split this skill into the rules it gives an agent
3 rules. About 0 are common, 2 are distinctive, and 1 is very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈2
Distinctive · estimate
This author's own choices. Worth a look.
1
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Distinctive: line 53
If a polish pass (golden-flash / SFX) was applied, re-run it afterward so the effects sit on top of the freshly captioned video (see …
- Distinctive: line 72
Frame-snapped timeline: Every reveal-state boundary is rounded to the fps grid and durations accumulate in whole frames, so the reveal …
- Very specific: line 76
One lossless alpha overlay: All per-word states are baked into a SINGLE transparent qtrle (.mov) track via an ffconcat list and composited …
≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
Caption word-by-word reveal
Karaoke-style captions for reels: instead of a whole phrase popping in at once, each aligned word appears the moment it's spoken, building the phrase up in place; already-spoken words stay lit and the phrase clears when the next phrase starts (same "replace" progression as the static captions).
This is already implemented in the avatar-reel-composer finishing pass
(finish_reel.py) — this skill is how to apply/tune it and the invariants to
keep. It is the default caption mode (caption_reveal="word").
When to use
- The user wants captions where the words form the sentence as they're spoken ("palabra por palabra formando la frase", karaoke captions, word reveal).
- Applying that look to a new reel, or re-captioning an already-finished reel without regenerating any video.
Requirements
- A reel folder produced by
compose_reel.py(hasvideo_track.mp4,narration.mp3,reel_manifest.json). - Word-level timings at
narration.align.json(faster-whisper alignment) — the reveal is driven by each word'sstart. Without it, captions are skipped.
How to apply
A) New reel — set it in the storyboard finish block
"finish": { "enabled": true, "subtitles": true, "caption_reveal": "word" }Then compose normally; caption_reveal defaults to "word", so a finish
block already gets the reveal unless you set "phrase".
B) Any existing reel — re-caption in place (no re-render of video)
python3 .cursor/skills/avatar-reel-composer/scripts/finish_reel.py <reel_dir> \
--caption-reveal word --no-music--no-music reuses the existing bed and only rebuilds the caption layer. Drop it
(or add --music-prompt "…") to also (re)build music. Re-running is idempotent.
To revert to static phrase-replace captions use --caption-reveal phrase.
If a polish pass (golden-flash / SFX) was applied, re-run it afterward so the
effects sit on top of the freshly captioned video (see avatar-reel-composer
Polish). Tune text with the same knobs as static captions: --max-words,
--no-emphasis, --casing, --fontsize, --y-frac, --regular-font,
--emph-font.
How it works (invariants — keep these when tuning)
The reveal reuses the SAME phrase units and setup/payoff styling as the static captions; only the presentation differs. Four properties keep it from looking janky — preserve them:
- Frozen layout, no reflow. The wrap, font size and every word's
x/yare computed ONCE from the FULL phrase, then frozen. Drawing the first k words reproduces the head of the finished line — words never recenter or jump as they arrive. (_reveal_fit_fslocks the size with the static fit rule;_positioned_tokensfreezes positions.) - Replace, not accumulate. A phrase clears to blank only when the next phrase begins — the viewer never reads stale, not-yet/already-spoken text stacked up.
- Frame-snapped timeline. Every reveal-state boundary is rounded to the fps grid and durations accumulate in whole frames, so the reveal can't drift against the frame-locked picture (same anti-drift discipline as the video assembly). Long reels stay in sync to the end.
- One lossless alpha overlay. All per-word states are baked into a SINGLE
transparent
qtrle(.mov) track via anffconcatlist and composited in oneoverlaypass — not ~hundreds of overlays. RLE +argbkeeps the serif edges crisp. (build_reveal_track→overlay_reveal_track.)
Styling matches the static captions: serif (Georgia), subtitle casing
(lowercase, intentional ALL-CAPS + accents kept, no trailing dot), white with a
soft shadow/outline; the breath-group payoff is bold-italic.
Verify
Extract a few frames spanning a phrase and confirm words accrue left→right without the line shifting, and that the last words land in sync near the reel's end (where drift would show first):
ffmpeg -y -ss <t> -i <reel_dir>/final.mp4 -frames:v 1 /tmp/rev_check.pngFiles (in the avatar-reel-composer skill)
scripts/finish_reel.py_event_tokens— per-word display strings + spoken start times + payoff split._reveal_fit_fs/_positioned_tokens— lock font size + freeze full-phrase word positions.render_reveal_state— render one state (first k words lit).build_reveal_track— bake all states into one frame-snapped transparent qtrle track.overlay_reveal_track— composite the track over the base video in one pass.finish(..., caption_reveal="word"|"phrase")/ CLI--caption-reveal(defaultword).
scripts/compose_reel.py— passesfinish.caption_revealthrough tofinish().
See the avatar-reel-composer skill for the full finishing pass (caption phrasing, emphasis, music, polish).
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

