reelkit-cli 0.8.0 → 0.10.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (110) hide show
  1. package/README.md +3 -1
  2. package/package.json +49 -10
  3. package/skill/SKILL.md +29 -19
  4. package/skill/THIRD_PARTY.md +3 -3
  5. package/skill/commands/launch-film.md +1 -1
  6. package/skill/reference/art-styles.md +70 -0
  7. package/skill/reference/backgrounds.md +1 -1
  8. package/skill/reference/brand-motion.md +62 -0
  9. package/skill/reference/clips.md +3 -3
  10. package/skill/reference/component-authoring.md +1 -1
  11. package/skill/reference/continuity.md +5 -5
  12. package/skill/reference/delivery-review.md +40 -0
  13. package/skill/reference/hebrew-rtl.md +3 -4
  14. package/skill/reference/{remotion-composition.md → hyperframes-composition.md} +14 -8
  15. package/skill/reference/kit.md +7 -3
  16. package/skill/reference/launch-film.md +13 -9
  17. package/skill/reference/motion-design.md +18 -16
  18. package/skill/reference/sound-design.md +34 -12
  19. package/skill/reference/studio-editing.md +55 -0
  20. package/skill/reference/styles.md +9 -6
  21. package/skill/reference/three-d.md +8 -7
  22. package/skill/reference/voice-sync.md +1 -1
  23. package/src/commands/assets.ts +5 -1
  24. package/src/contract/index.ts +1 -1
  25. package/src/hyperframes/Root.tsx +1 -0
  26. package/src/hyperframes/fonts.ts +54 -0
  27. package/src/hyperframes/frame.tsx +46 -0
  28. package/src/hyperframes/host.tsx +38 -0
  29. package/src/{remotion → hyperframes}/kit/Assemble3D.tsx +1 -1
  30. package/src/hyperframes/kit/BrandTransform3D.tsx +12 -0
  31. package/src/{remotion → hyperframes}/kit/BrowserFrame.tsx +1 -1
  32. package/src/{remotion → hyperframes}/kit/Camera.tsx +1 -1
  33. package/src/{remotion → hyperframes}/kit/Captions.tsx +1 -1
  34. package/src/{remotion → hyperframes}/kit/Card3D.tsx +2 -2
  35. package/src/{remotion → hyperframes}/kit/Carry.tsx +1 -1
  36. package/src/{remotion → hyperframes}/kit/ChapterFrame.tsx +1 -1
  37. package/src/{remotion → hyperframes}/kit/ClipLayer.tsx +1 -1
  38. package/src/{remotion → hyperframes}/kit/Counter.tsx +1 -1
  39. package/src/{remotion → hyperframes}/kit/CounterRoll.tsx +1 -1
  40. package/src/{remotion → hyperframes}/kit/Entrance.tsx +1 -1
  41. package/src/{remotion → hyperframes}/kit/FootageLayer.tsx +1 -1
  42. package/src/{remotion → hyperframes}/kit/GlassPanel.tsx +1 -1
  43. package/src/{remotion → hyperframes}/kit/Grounds.tsx +1 -1
  44. package/src/{remotion → hyperframes}/kit/Headline.tsx +1 -1
  45. package/src/{remotion → hyperframes}/kit/Hero3D.tsx +1 -1
  46. package/src/{remotion → hyperframes}/kit/HudOverlay.tsx +1 -1
  47. package/src/{remotion → hyperframes}/kit/ImageLayers.tsx +1 -1
  48. package/src/{remotion → hyperframes}/kit/KenBurnsImage.tsx +1 -1
  49. package/src/{remotion → hyperframes}/kit/KeyedClip.tsx +1 -1
  50. package/src/{remotion → hyperframes}/kit/Layers.tsx +1 -1
  51. package/src/{remotion → hyperframes}/kit/LowerThird.tsx +1 -1
  52. package/src/{remotion → hyperframes}/kit/Music.tsx +1 -1
  53. package/src/{remotion → hyperframes}/kit/NamedCursor.tsx +1 -1
  54. package/src/{remotion → hyperframes}/kit/Orbit3D.tsx +1 -1
  55. package/src/{remotion → hyperframes}/kit/Particles3D.tsx +1 -1
  56. package/src/{remotion → hyperframes}/kit/Place.tsx +1 -1
  57. package/src/{remotion → hyperframes}/kit/PromptBox.tsx +1 -1
  58. package/src/{remotion → hyperframes}/kit/Scene3D.tsx +2 -2
  59. package/src/{remotion → hyperframes}/kit/SceneFrame.tsx +1 -1
  60. package/src/{remotion → hyperframes}/kit/ScreenOverlay.tsx +1 -1
  61. package/src/{remotion → hyperframes}/kit/Sfx.tsx +1 -1
  62. package/src/{remotion → hyperframes}/kit/SoundCues.tsx +1 -1
  63. package/src/{remotion → hyperframes}/kit/TerminalLog.tsx +1 -1
  64. package/src/{remotion → hyperframes}/kit/Text3D.tsx +1 -1
  65. package/src/{remotion → hyperframes}/kit/TextOnImage.tsx +1 -1
  66. package/src/{remotion → hyperframes}/kit/TitleCard.tsx +1 -1
  67. package/src/{remotion → hyperframes}/kit/Voiceover.tsx +1 -1
  68. package/src/{remotion → hyperframes}/kit/Warp3D.tsx +1 -1
  69. package/src/hyperframes/kit/brand-transform.ts +25 -0
  70. package/src/{remotion → hyperframes}/kit/docs.ts +6 -2
  71. package/src/{remotion → hyperframes}/kit/index.ts +3 -0
  72. package/src/{remotion → hyperframes}/kit/sound-cues.ts +1 -1
  73. package/src/{remotion → hyperframes}/kit/sound-kinds.ts +14 -1
  74. package/src/{remotion → hyperframes}/kit/theme.ts +42 -40
  75. package/src/{remotion → hyperframes}/kit/ui-math.ts +1 -1
  76. package/src/hyperframes/math.ts +62 -0
  77. package/src/hyperframes/three.tsx +10 -0
  78. package/src/project/chromakey.ts +1 -1
  79. package/src/project/layers.ts +1 -1
  80. package/src/project/serve.ts +2 -2
  81. package/src/render/component-preview.ts +11 -55
  82. package/src/render/render.ts +62 -64
  83. package/src/render/serve.ts +31 -0
  84. package/src/render/static-check.ts +15 -4
  85. package/src/render/validate.ts +4 -4
  86. package/src/render/word-check.ts +1 -1
  87. package/src/render/worker.ts +71 -0
  88. package/src/testing/fixtures.ts +1 -1
  89. package/src/remotion/Root.tsx +0 -31
  90. /package/src/{remotion → hyperframes}/kit/Icon.tsx +0 -0
  91. /package/src/{remotion → hyperframes}/kit/beat.ts +0 -0
  92. /package/src/{remotion → hyperframes}/kit/bg-math.ts +0 -0
  93. /package/src/{remotion → hyperframes}/kit/brand-icons.ts +0 -0
  94. /package/src/{remotion → hyperframes}/kit/caption-groups.ts +0 -0
  95. /package/src/{remotion → hyperframes}/kit/caption-style.ts +0 -0
  96. /package/src/{remotion → hyperframes}/kit/image-layers-math.ts +0 -0
  97. /package/src/{remotion → hyperframes}/kit/inter-bold-typeface.ts +0 -0
  98. /package/src/{remotion → hyperframes}/kit/media.ts +0 -0
  99. /package/src/{remotion → hyperframes}/kit/motion-math.ts +0 -0
  100. /package/src/{remotion → hyperframes}/kit/music-math.ts +0 -0
  101. /package/src/{remotion → hyperframes}/kit/quiet-three.ts +0 -0
  102. /package/src/{remotion → hyperframes}/kit/sample-text.ts +0 -0
  103. /package/src/{remotion → hyperframes}/kit/scene3d-context.ts +0 -0
  104. /package/src/{remotion → hyperframes}/kit/seeded.ts +0 -0
  105. /package/src/{remotion → hyperframes}/kit/three-fx-math.ts +0 -0
  106. /package/src/{remotion → hyperframes}/kit/three-math.ts +0 -0
  107. /package/src/{remotion → hyperframes}/kit/transition-math.ts +0 -0
  108. /package/src/{remotion → hyperframes}/kit/ui-theme.ts +0 -0
  109. /package/src/{remotion → hyperframes}/kit/word-anchor.ts +0 -0
  110. /package/src/{remotion → hyperframes}/types.ts +0 -0
@@ -0,0 +1,40 @@
1
+ ---
2
+ name: delivery-review
3
+ description: Verify a finished Reelkit export: layout, word and sound timing, phone playback, platform margins, media integrity and honest delivery reporting.
4
+ ---
5
+
6
+ # Verify the deliverable
7
+
8
+ Review against the original request and actual source material. A render completing proves that a file was encoded; it does not prove that the edit works. Fix observed defects and inspect the changed moments. Stop when the requested result is achieved, without mandatory review rounds or a made-up quality score.
9
+
10
+ ## Before a full render
11
+
12
+ Run `reelkit check` and `reelkit preview`. Inspect `out/preview/sheet.jpg`, then the important individual frames: opening, both sides of cuts, spoken triggers, transformation landing, readable hold and ending. The normal early and late samples can miss a brief overlap, so inspect the moving export or extract additional frames around a suspicious event. Do not invent a preview timestamp flag.
13
+
14
+ - Does each moment have a clear focal point and a reason to be there?
15
+ - Are text, captions and supplied logos readable, correctly spelled and clear of faces or controls?
16
+ - Does each claim match the user's facts and source? Are illustrative surfaces distinguishable from the real product?
17
+ - Do objects settle when their words or events happen? Do old labels leave before the replacement is readable?
18
+ - Are empty states, media edges and transparency intentional? Is the ending held long enough to read?
19
+
20
+ Preview holds as well as entrances. For a loop, compare the first frame with the loop boundary and check audio continuity; matching stills alone does not prove a seamless moving loop.
21
+
22
+ ## Phone and destination layout
23
+
24
+ Default a new short-form video to 9:16 unless the destination or user specifies otherwise. Keep critical content clear of likely platform chrome. For 1080x1920, a conservative working region leaves about 250px at the top, 350px at the bottom, 80px on the sides and extra room on the lower right. These are starting margins, not a guarantee for every app, device or caption expansion. Scale with the output dimensions and inspect the named destination when available. Do not add two platform versions automatically.
25
+
26
+ If variants are requested, change the layout in the source and render each variant; moving a finished frame can crop another element. Keep filenames explicit and retain earlier deliverables when revising. Do not publish or upload the result as part of a local export request.
27
+
28
+ ## Check the finished file
29
+
30
+ Confirm the file exists. Use `ffprobe` when available to check actual codecs, dimensions, frame rate and duration against the requested result; decode with `ffmpeg` when corruption or missing media is suspected. Reelkit normally renders H.264/AAC MP4 and masters the mix near -14 LUFS. Inspect the reported result before applying another loudness pass. A duration mismatch may be a short audio tail; investigate before changing scene timing.
31
+
32
+ Play the export when playback is available, and listen to its speech, music and effects. Speech must be intelligible; intended music and cues must actually be present. Check the first hit, a middle word, the reveal landing and the ending for sync, unexpected silence, truncated tails and clipping. Check the final mix, not only the source stems. Avoid certifying subjective audio quality when you only ran measurements; state what was verified and what could not be auditioned.
33
+
34
+ `reelkit sound --detail` reports measurable hits, swells and nearby picture changes. Use it to locate a suspected mismatch, not to fill a quota. A calm hold can have no effect, and repeated music beats can inflate hit counts. Audition a small-speaker or reduced-bass mix when available; if only analysis is possible, look for music that vanishes without its bass and report the limitation. Do not treat a fixed energy percentage or a stem-correlation threshold as proof that the mix sounds good.
35
+
36
+ If a speed change or cut shifted timing, correct the source event map and rerender. Do not offset the whole audio track to repair one bad cue. If clipping exists before mastering, lower overlapping source levels; loudness normalization cannot restore an already clipped waveform.
37
+
38
+ ## Deliver
39
+
40
+ Link or display the final video and give its project path. Briefly explain the main creative choices and why they fit, including the music when used. Report checks actually performed, material limitations and generator usage only when known. Do not claim credits were measured when the provider only exposes a remaining allowance. Keep the plan, source and media together so the edit can be revised.
@@ -15,7 +15,7 @@ Most broken Hebrew videos break in the same few ways. These rules are for text d
15
15
 
16
16
  ## Direction
17
17
  - Give every Hebrew text container `direction: "rtl"`. Without it the full stop, comma and exclamation mark jump to the wrong end of the line.
18
- - Digits and Latin words inside a Hebrew sentence order themselves when the base direction is RTL. A label that is entirely Latin or digits gets `direction: "ltr"`.
18
+ - Isolate Latin terms, URLs and technical identifiers in their own LTR span or bidi-isolated element inside the RTL container. A label that is entirely Latin or digits gets `direction: "ltr"`. Check numbers and punctuation in the rendered sentence, not just the source.
19
19
  - Everything laid out in reading order runs right to left: the first word on the right, the first list item on the right or top, tabs, chat bubbles, steps, and charts over time (the first day on the right).
20
20
  - **The exception:** progress bars, sliders, loading bars and media timelines still fill left to right, as every player does.
21
21
  - A typing effect adds characters in reading order; the caret sits at the left end of the text, where it grows.
@@ -29,8 +29,7 @@ Most broken Hebrew videos break in the same few ways. These rules are for text d
29
29
  - This overrides the masked rise that `reference/motion-design.md` recommends for Latin headlines.
30
30
 
31
31
  ## Hyphens and punctuation
32
- - **Never join two Hebrew words with a hyphen on screen**, in headlines, labels or interface text. Write the two words with a space.
33
- - No em dash and no en dash on screen. Use a comma, a full stop or a new line.
32
+ - For newly written display copy, prefer clear punctuation and breaks rather than joining words with decorative dashes. Preserve the user's exact supplied wording; do not silently remove a hyphen or punctuation from a quote.
34
33
  - A prefix letter before a number or a Latin word ("ב-2026") is correct Hebrew, but on screen prefer wording that avoids it.
35
34
  - Quote the user's text exactly, letter for letter. Never "fix" spelling, add vowel points or swap a final letter.
36
35
 
@@ -45,7 +44,7 @@ Most broken Hebrew videos break in the same few ways. These rules are for text d
45
44
 
46
45
  ## Check before you show
47
46
  1. Every word in the right order, right to left, spelled exactly as given.
48
- 2. No hyphen between words, no long dash.
47
+ 2. Punctuation matches the supplied wording and renders at the correct end of the phrase.
49
48
  3. No letter cut by the frame edge or by a mask, in the early frame or the late one.
50
49
  4. Progress bars fill left to right; everything else runs right to left.
51
50
  5. The full stop and exclamation mark sit at the left end of the last word.
@@ -1,14 +1,16 @@
1
1
  ---
2
- name: remotion-composition
2
+ name: hyperframes-composition
3
3
  description: Use when writing Video.tsx - the file rules, timing model and media rules every composition must follow.
4
4
  ---
5
5
 
6
6
  # Writing the composition
7
7
 
8
+ Reelkit uses HyperFrames with a seekable React adapter. Author TSX in `src/Video.tsx`; `reelkit/frame` supplies the frame clock, sequences, media, and animation math. The generated HTML exposes HyperFrames' seek protocol for capture and rendering.
9
+
8
10
  ## Files
9
11
  - `Video.tsx` is required and must contain `export const Video: React.FC<VideoProps> = ({ manifest, urls }) => ...`.
10
12
  - Extra component files are flat siblings, PascalCase, one component per file: `NumberBadge.tsx` exports `NumberBadge`. Import them in Video.tsx as `./NumberBadge`.
11
- - Video.tsx may import only `react`, `remotion`, `reelkit/kit` and sibling components. No other packages, no network, no file access, no `process`.
13
+ - Video.tsx may import only `react`, `reelkit/frame`, `reelkit/kit` and sibling components. No other packages, no network, no file access, no `process`.
12
14
 
13
15
  ## What the composition receives
14
16
  `Video` gets two props, `{ manifest, urls }` (type `VideoProps`, exported by `reelkit/kit`). `manifest` is the content of `manifest.json` in the project, rewritten by `reelkit assets voiceover`, `check`, `preview` and `render` from `plan.json` and the recorded voiceovers. It is not hand-edited. `urls` is separate: it is built at render time and is not in `manifest.json`.
@@ -28,7 +30,7 @@ Each `scenes` entry:
28
30
  - `imageKey`: only on an illustration scene that has its image; the project path of the image.
29
31
  - `userAssetKeys`: project paths of the user's own files that the plan assigned to this scene (an empty array when none).
30
32
 
31
- `urls` maps a project path (every file under `assets/`, except `.json` files) to the address Remotion can load it from. Pass paths from the manifest, or one you pulled, such as `urls["assets/lib/<id>/clip.mp3"]`; never build an address yourself.
33
+ `urls` maps a project path (every file under `assets/`, except `.json` files) to the address HyperFrames can load it from. Pass paths from the manifest, or one you pulled, such as `urls["assets/lib/<id>/clip.mp3"]`; never build an address yourself.
32
34
 
33
35
  ```json
34
36
  {
@@ -51,12 +53,12 @@ Each `scenes` entry:
51
53
  - Reference media only as `urls[path]`, where `path` is the file's project path, using the paths in the manifest: `s.voiceoverKey`, `s.imageKey`, `s.clipKey`, `s.clipKeyedKey`, `s.userAssetKeys`, `manifest.footageKey`. Never hard-code a URL.
52
54
  - A scene with narration has `s.voiceoverKey`: give it exactly one `<Voiceover src={urls[s.voiceoverKey]} />` inside its SceneFrame, and `<Captions words={s.words} />` unless the notes say otherwise. In a plan with `voice: "none"` no scene has a `voiceoverKey` and `s.words` is empty, so render no `<Voiceover>` and no `<Captions>` (`manifest.captions` is `"none"`); keep the guard `s.voiceoverKey ? ... : null` so the same code works either way.
53
55
  - Footage mode (`manifest.footageKey` is set): one `<FootageLayer>` at the bottom, outside the scenes.
54
- - User images: `<Img src={urls[key]} />` from remotion.
56
+ - User images: `<Img src={urls[key]} />` from reelkit/frame.
55
57
  - Write a media path as one plain string, so that `reelkit check` can verify the file exists. A path built with a template string or by joining parts (`` `assets/lib/${id}/hit.mp3` ``) cannot be checked and is reported as missing. Write `"assets/lib/sfx-ab12/hit.mp3"` in full, or read the key from the manifest.
56
58
 
57
59
  ## Layer stack (every video, bottom to top)
58
- 1. Background: `<BgMesh>` from the kit, or `<FootageLayer>` in footage mode. Never a flat solid colour.
59
- 2. Images: `<KenBurnsImage>` inside its scene. Every still image moves; alternate `direction` between consecutive image scenes.
60
+ 1. Background: a chosen field, picture, `<BgMesh>` or `<FootageLayer>` in footage mode. A flat colour is valid when it serves the design.
61
+ 2. Images: `<KenBurnsImage>` when a camera move helps, or a stable image for reading and comparison. Keep important details in frame.
60
62
  3. Clips: `<ClipLayer>` inside its scene (a clip scene's picture); a green-screen `<KeyedClip>` above the scene's background and below its type and captions. See `reference/clips.md`.
61
63
  4. Graphics and type, inside each scene's SceneFrame.
62
64
  5. Anything that must survive a scene change: a `<Carry>` layer beside the scenes and above them (outside the SceneFrame fades), and `<Camera>` around the scenes when one camera moves through all of them. See `reference/continuity.md`.
@@ -70,9 +72,9 @@ Each `scenes` entry:
70
72
  - Run `reelkit assets pull <id>` before referencing an overlay. It lands in `assets/lib/<id>/`; reference it as `urls["assets/lib/<id>/<file>"]`, and read its duration from `assets/library.json`.
71
73
 
72
74
  ## Animation rules
73
- - **No linear motion.** Every `interpolate()` takes an `easing` from the kit's `ease` and both `extrapolateLeft: "clamp"` and `extrapolateRight: "clamp"`. Entrances use `spring()` with a kit `springs` preset.
75
+ - Choose easing or a spring to fit the move; linear interpolation is valid for steady motion. Clamp finite interpolation ranges with `extrapolateLeft: "clamp"` and `extrapolateRight: "clamp"` so elements do not drift beyond their intended pose.
74
76
  - **Entrances move two or three properties together** (opacity, position, scale). Wrap content in `<Entrance>` rather than fading alone.
75
- - **Stagger, never simultaneous.** Words 3 frames apart, list items and cards 4 to 5, big blocks 6.
77
+ - Stagger related items when that improves hierarchy; simultaneous motion is valid for one coordinated action. Spoken words follow their real timestamps rather than a fixed stagger.
76
78
  - **Exits exist and are faster than entrances** (about 10 frames against 20). Use `<Entrance exitAt={...}>` or the SceneFrame fade.
77
79
  - **A missing clamp shows elements before their entrance or after their exit.** Check for it.
78
80
  - Derive timing from `fps` in `useVideoConfig()`, not bare frame counts, when you express a duration in seconds.
@@ -91,3 +93,7 @@ Each `scenes` entry:
91
93
  1. `reelkit assets search "<description>" --kind component`, and `reelkit assets pull <id>` for any you plan to use (it lands in `src/`).
92
94
  2. Write each new component in `src/`, then `src/Video.tsx`.
93
95
  3. `reelkit check`. Fix every error it reports and check again until it passes.
96
+
97
+ ## Revising a shot in HyperFrames
98
+
99
+ Every pose must be computable from the current frame, including a direct seek to the landing or held state. Use `reelkit/frame` timing helpers; avoid CSS animations, wall-clock timers, and state accumulated by previous frames. Derive sound from the same event frames as the visual. Inside a `SceneFrame` timing is local; outside it add `startFrame` once. For a branded arrival use `BrandTransform3D` and `brandTransformFrames` (`reference/brand-motion.md`). Preview early, middle and held states after retiming, and listen to the rendered file after changing sound.
@@ -127,6 +127,10 @@ Scene3D { camera?: { keys: { frame: number; x?: number; y?: number; z?: number;
127
127
  A three.js scene at the size of the frame, for real depth. Transparent unless background is set, so it lays over a 2D ground; a soft three-point light is placed for you (lights={false} to place your own); mood ("studio", "night", "sunset" or "neon") chooses the light colours, their intensities and the fog tint together instead, so lights are never hand-tuned. Put it inside a SceneFrame, with captions and small labels in 2D above it. camera.keys move the camera with the same timing as Camera (a spring that starts 12 frames before the key's frame and lands on it); the default camera is at z 6, looking at the origin, fov 50, and a key that leaves a value out keeps the one before. What it sees: at fov 50 the height is 0.93 times the distance to the object and the width that times width over height, so 3.1 units across at z 6 on 9:16 (4.7 at z 9), 5.6 on 1:1 and 9.9 on 16:9 (not "5.5"). Text3D and Orbit3D read the camera keys and size themselves to fit at the key where the camera is closest: leave their sizes out. visibleWidth(distance, aspect, fov?) and visibleHeight(distance, fov?) give the same numbers. No GL context is made unless a Scene3D is on screen. A 3D scene renders slower: use it only for the shots that need it. See reference/three-d.md.
128
128
  <Scene3D camera={{ keys: [{ frame: 0, z: 7.5 }, { frame: 40, z: 6 }] }}><Text3D text="Reelkit" color={palette.hero} enter="rise" /></Scene3D>
129
129
 
130
+ BrandTransform3D { mode?: "turn" | "arc" | "launch"; from?: number (0); frames?: number (32); strength?: number (0 to 1, default 1); children }
131
+ A deterministic arrival for a branded object inside Scene3D: turn exposes its face, arc carries it on a curved path, launch approaches from depth. Wrap Text3D, Card3D or Hero3D; the final pose is neutral and holds exactly. Keep the supplied identity intact and allow a readable hold after landing. A transformation has no built-in audio. brandTransformFrames({ from, frames }) returns { start, settle } in the same local clock; cuesFor([start, settle], "transform", { offset: scene.startFrame, voice, sweepFrames }) places the transform-sweep role before the landing and transform-lock on it. Map both roles to pulled sound files. sweepFrames is the chosen sound's attack in frames (default 10). brandTransformAt(frame, fps, options) returns { visible, position, rotation, scale }; BRAND_TRANSFORMS lists the modes. See reference/brand-motion.md for when and why to choose each.
132
+ <BrandTransform3D mode="turn" from={6} frames={32}><Text3D text="Reelkit" fit={0.72} /></BrandTransform3D>
133
+
130
134
  Text3D { text: string; fit?: number (0.8); size?: number; depth?: number; color?: string; position?: [x, y, z]; rotation?: [x, y, z] (degrees); enter?: "rise" | "turn" | "fly" | "none"; delay?: number }
131
135
  Extruded text, centred on its position, inside a Scene3D. Latin letters, digits and common punctuation only (one bundled typeface, Inter Bold): Hebrew and other scripts stay 2D. Leave size out: the word is measured on its own letters and sized to fill fit (default 0.8) of the frame's width at the closest the Scene3D camera comes, so it is whole at every moment on any aspect; a line break in the text makes a second line, and the height is held to fit of the frame's height. A size you give wins (scene units, the height of a capital-ish line). A push-in starts the word smaller in proportion: z 7.5 to 6 is a gentle one. depth is how far it is extruded (default a quarter of the size). enter is how it arrives, starting delay frames into the scene; "none" is there from the start. Keep type that must be read facing the camera and held at least 1.5 seconds.
132
136
  <Text3D text="Meet Reelkit" color="#ffffff" position={[0, 1, 0]} enter="turn" delay={6} />
@@ -227,8 +231,8 @@ cuesOnChanges(scenes, { impact?: { sound, volume? }, whoosh?: { sound, volume?,
227
231
  Sounds for the scene changes, placed where the eye sees them. A SceneFrame transition is complete on the boundary but the picture changes most half the transition's frames before it (4 for the default 8, 3 for transitionFrames={6}; none for "cut"), and a hit on the boundary lands after the change. scenes are the manifest's scenes, each with the exit and transitionFrames its SceneFrame has: cuesOnChanges gives an impact on that peak and a whoosh (frames long, from the search line's duration times 30) that ENDS on it, for every change but the one after the last scene; skip lists scene indices to leave silent. changeFrame(scene) is the peak for one scene. A camera zoom, zoomTo or punch is a picture change too: cueOnCamera(frame) is the frame where the Camera move to the key at "frame" is fastest (about 9 frames before it); with punch: true, the fastest frame of a punch (just after its frame). The Camera counts frames from the scene's start when it is inside a SceneFrame, so add the scene's startFrame for an absolute cue.
228
232
  const exits = [{ exit: "zoom-through" as const }, { exit: "whip-left" as const, transitionFrames: 6 }, {}]; const cues = cuesOnChanges(manifest.scenes.map((s, i) => ({ ...s, ...exits[i] })), { impact: { sound: "thud", volume: 0.55 }, whoosh: { sound: "whoosh", frames: 24, volume: 0.3 } });
229
233
 
230
- cuesFor(events, kind, { offset?, fps?, voice?, volume?, seed?, riserFrames? }): { at, sound, volume }[] clearBefore(cues, frame, { seconds?, fps?, riserFrames? }): cues
231
- Turns the event frames a component reports into SoundCues with a sensible sound role, level and density for the kind: "type" (promptFrames(...).type: a tick on every 2nd or 3rd character, at most 12 a second, a little different in level each, and a thock one frame after the last), "click" (clickFrames), "snap" (panelSettleFrame: a card or panel landing), "pop" (chapterFrames(...).badges), "count" ([start, settleFrame]: a train of ticks that speeds up and ends on a chime ON settleFrame), "stream" (terminalFrames(...).lines: one soft tick per line, at most 6 a second), "assemble" ([start, lockFrame]: a rising run that gets louder and a lock hit on lockFrame) and "resolve" ([frame] the logo or end card lands: a riser that ends on the chime, which is on the frame). offset is the scene's startFrame when the events are in the scene's own clock. voice: true gives the quieter levels for a film with a narrator (never over 0.3). Each cue's sound is a role: type-tick, type-return, click, snap, pop, count-tick, count-settle, stream, assemble-run, assemble-lock, resolve-riser, resolve-chime. Map each role to a pulled file in sounds, searching with: type-tick "mouse click"; type-return "glass tap"; click "mouse click"; snap "soft impact"; pop "bubble pop"; count-tick "counter ticks"; count-settle "success chime"; stream "glass tap"; assemble-run "counter ticks"; assemble-lock "soft impact"; resolve-riser "whoosh buildup"; resolve-chime "sparkle shimmer" (reelkit assets search "<words>" --kind sfx; the interface pack's names begin with sfx-ui-). clearBefore(cues, chimeFrame) removes every other cue in the second before the riser so the end card has a clear second of nothing; give the music a dip there (Music dips).
234
+ cuesFor(events, kind, { offset?, fps?, voice?, volume?, seed?, sweepFrames?, riserFrames? }): { at, sound, volume }[] clearBefore(cues, frame, { seconds?, fps?, riserFrames? }): cues
235
+ Turns the event frames a component reports into SoundCues with a sensible sound role, level and density for the kind: "type" (promptFrames(...).type: a tick on every 2nd or 3rd character, at most 12 a second, a little different in level each, and a thock one frame after the last), "click" (clickFrames), "snap" (panelSettleFrame: a card or panel landing), "pop" (chapterFrames(...).badges), "count" ([start, settleFrame]: a train of ticks that speeds up and ends on a chime ON settleFrame), "stream" (terminalFrames(...).lines: one soft tick per line, at most 6 a second), "assemble" ([start, lockFrame]: a rising run that gets louder and a lock hit on lockFrame), "transform" ([start, settle]: transform-sweep begins sweepFrames before settle, never before start, and transform-lock lands on settle) and "resolve" ([frame] the logo or end card lands: a riser that ends on the chime, which is on the frame). offset is the scene's startFrame when the events are in the scene's own clock. voice: true gives the quieter levels for a film with a narrator (never over 0.3). Each cue's sound is a role: type-tick, type-return, click, snap, pop, count-tick, count-settle, stream, assemble-run, assemble-lock, transform-sweep, transform-lock, resolve-riser, resolve-chime. Map each role to a pulled file in sounds, searching with: type-tick "mouse click"; type-return "glass tap"; click "mouse click"; snap "soft impact"; pop "bubble pop"; count-tick "counter ticks"; count-settle "success chime"; stream "glass tap"; assemble-run "counter ticks"; assemble-lock "soft impact"; transform-sweep "soft ui whoosh"; transform-lock "soft impact"; resolve-riser "whoosh buildup"; resolve-chime "sparkle shimmer" (reelkit assets search "<words>" --kind sfx; the interface pack's names begin with sfx-ui-). clearBefore(cues, chimeFrame) removes every other cue in the second before the riser so the end card has a clear second of nothing; give the music a dip there (Music dips).
232
236
  const p = promptFrames({ text, reply }, fps); const cues = [...cuesFor(p.type, "type", { offset: s.startFrame }), ...cuesFor([p.send], "click", { offset: s.startFrame }), ...cuesFor([settleFrame({ delay: 20 })], "snap", { offset: s.startFrame })];
233
237
 
234
238
  Music { src: string; volume?: number; duckTo?: number; dips?: { from: number; to: number; volume: number }[] }
@@ -252,7 +256,7 @@ Voiceover { src: string; volume?: number }
252
256
 
253
257
  ```tsx
254
258
  import React from "react";
255
- import { AbsoluteFill, useVideoConfig } from "remotion";
259
+ import { AbsoluteFill, useVideoConfig } from "reelkit/frame";
256
260
  import { BgMesh, Captions, FootageLayer, fonts, Grade, Grain, KenBurnsImage, palettes, SceneFrame, Vignette, Voiceover, WordReveal } from "reelkit/kit";
257
261
  import type { VideoProps } from "reelkit/kit";
258
262
 
@@ -9,11 +9,11 @@ The short films that studios post when a product launches have no narrator. The
9
9
 
10
10
  ## When to choose it
11
11
 
12
- Choose it for a product, a feature or a brand reveal where nobody needs to explain anything out loud. If the user wants a person to talk, or a story told in sentences, it is the wrong tool: write a narrated video instead. Ask the user whether the video has a narrator; if not, this file applies. Skip the voice and caption steps.
12
+ Choose it for a product, a feature or a brand reveal where nobody needs to explain anything out loud. If the user wants a person to talk, or a story told in sentences, it is the wrong tool: write a narrated video instead. Use the requested format; ask about narration only if that decision is still consequential and unclear. Skip the voice and caption steps.
13
13
 
14
14
  ## What good ones measured
15
15
 
16
- The owner measured four launch films of 15 to 55 seconds. Use these numbers as targets.
16
+ Four previously measured launch films of 15 to 55 seconds provide examples of one energetic style. Their ranges are context, not targets for every brand or edit; a calm reveal can use fewer sounds and longer holds.
17
17
 
18
18
  - No speech at all. Loudness between -14.1 and -14.8 LUFS in every one.
19
19
  - 2.0 to 3.0 sound hits a second over the whole film (music beats and effects together), 1.5 to 2.8 of them low, and a whoosh-like swell every one to two seconds (0.5 to 1.3 a second).
@@ -27,7 +27,7 @@ The owner measured four launch films of 15 to 55 seconds. Use these numbers as t
27
27
 
28
28
  Write `plan.json` with `"voice": "none"`. Every scene then has `seconds` (a number from 0.3 to 15) and `narration` may be an empty string; `voiceId` is not needed, and `captions` is `none` unless you set it. Up to 16 scenes are allowed in this mode.
29
29
 
30
- - The film is 15 to 45 seconds and has 6 to 14 shots.
30
+ - A common short launch film is 15 to 45 seconds with 6 to 14 shots; adapt to the requested duration and reading time.
31
31
  - Lengths vary at least fourfold: one or two shots under a second, one long hold, the rest in between.
32
32
  - On-screen text carries every word the viewer will read, so each scene has `onScreenText` or `notes` saying what is on screen (`reelkit plan check` flags a scene with neither).
33
33
  - The product's logo comes first or last.
@@ -56,7 +56,7 @@ What the strongest short launch films have in common, in rules a plan can follow
56
56
  - **Open on the question.** When the product is an assistant or a tool, the first scene is the user's own question typed into a `PromptBox`. Always end on an end card: the wordmark, one line, one call to action, with a clear second before it (`clearBefore`).
57
57
  - **Ask for the real material before writing**: screenshots, the real numbers, the logo, the exact product name; and use it. No third-party brand marks.
58
58
  - **Length.** 15 to 40 seconds; state it in the plan. Over 60 seconds the same effect repeats.
59
- - **Review.** After `reelkit preview`, check the contact sheet: no text smaller than about 28 px at 1080 wide, every claim has a visible demonstration, the grounds alternate as planned, the hero object is in every scene it should be. Fix and preview again, at most twice.
59
+ - **Review.** Inspect the preview for phone readability, demonstrated claims, planned grounds and the hero object where it belongs. Fix observed problems and recheck changed shots. Finish with `reference/delivery-review.md`.
60
60
 
61
61
  ## The pictures
62
62
 
@@ -71,12 +71,12 @@ With no voice the sound is half of the film. Plan it as you plan the picture.
71
71
 
72
72
  1. **Choose the track first and let the beat set the cuts.** Search for 107 to 145 BPM (`reelkit assets search "driving clean product launch, 120 BPM" --kind music`), pull it with `reelkit assets pull <id> --music`, and read `reference/beat-sync.md`. The CLI holds each scene to the next beat, so every cut lands on the beat, a little more than the films did. Let the effects fill the places between.
73
73
  2. **Sound from the first frame.** A cue at frame 0 and the music running from frame 0. `reelkit check` notes a film with nothing placed in the first half second.
74
- 3. **Every visible change has a sound, on the frame where the eye sees it.** A press clicks, a card arriving pops, a move whooshes, a scene change lands on a low hit, and a reveal is led in by a riser that ends on it (`cueBefore`). Two things the measurement showed:
74
+ 3. **Score meaningful changes on the frame where the eye sees them.** A press clicks, a card arriving pops, a move whooshes, a scene change lands on a low hit, and a reveal is led in by a riser that ends on it (`cueBefore`). Two things the measurement showed:
75
75
  - A `SceneFrame` transition is complete on the boundary, but the picture changes most in the middle of it: for a zoom-through, blur, push or whip exit that is half the transition's frames before the boundary (4 frames for the default 8, 3 for `transitionFrames={6}`). A hit on the boundary frame lands after the change and does not register against it. Use `cuesOnChanges(scenes, { impact, whoosh })`: it puts the impact on the visual peak and the whoosh so that it ENDS there. Give each scene the same `exit` and `transitionFrames` you give its `SceneFrame` (one array for both, so they cannot disagree).
76
76
  - A camera zoom, `zoomTo` or punch is a picture change too and needs its own hit. `cueOnCamera(frame)` gives the frame where a `Camera` key's move is fastest (about 9 frames before the key's frame, because the move starts 12 frames early); `cueOnCamera(frame, { punch: true })` gives it for a punch (just after its frame). Inside a `SceneFrame` the Camera counts frames from the start of the scene: add the scene's `startFrame` for an absolute cue.
77
- 4. **Density.** Aim for about one placed effect a second on top of the music: more in the burst, none in the rest. With the beats this gets near the measured 2 to 3 hits a second. `reelkit check` counts what the code places and says when it is under one per two seconds; that is a count of the code, not a listening test. Its sound-count notes stay silent when the cues are computed (built by a loop, a helper such as `cuesOnBeats`, or a variable that is not a plain list), so their absence proves nothing: use the render's sound report to see what the film really has.
77
+ 4. **Density.** An energetic burst may use frequent effects; a restrained film may need only the main actions and reveal. Allow deliberate silence. The measured 2 to 3 hits a second describes examples, not a quality threshold. `reelkit check` counts what the code places and says when it is under one per two seconds; that is a count of the code, not a listening test. Its sound-count notes stay silent when the cues are computed (built by a loop, a helper such as `cuesOnBeats`, or a variable that is not a plain list), so their absence proves nothing: use the render's sound report to see what the film really has.
78
78
  5. **One family of sounds.** Take them from the interface pack in `reference/sound-design.md`, and mix families only when one is missing what you need. For the music, see "Background music" there.
79
- 6. **Levels.** For a film with no voice these are the numbers, and they replace any others you have read, including `reference/sound-design.md` and the narrated range in `reference/beat-sync.md`:
79
+ 6. **Levels.** For a film with no voice these are starting levels for the example style, rather than universal overrides of `reference/sound-design.md` and the narrated range in `reference/beat-sync.md`:
80
80
 
81
81
  | What | `volume` |
82
82
  |---|---|
@@ -85,7 +85,7 @@ With no voice the sound is half of the film. Plan it as you plan the picture.
85
85
  | Impacts and drops on a scene change | 0.5 to 0.6 |
86
86
  | Swells: whooshes that rise, risers | 0.25 to 0.35 |
87
87
 
88
- Every pulled sound is levelled on the way in (the interface effects got a gain of 0.7 to 0.8), and `reelkit render` then masters the whole film to -14 LUFS, so only the balance between these matters. At 0.2 to 0.3 an effect sits 6 dB or more under the music, which the tester of 0.8.0 found too quiet to register against the picture; a swell above about 0.35 hides the impact that ends it (the impact no longer rises out of what came before, and the report counts a change with no hit: on a test film, whooshes at 0.2 left 5 of 6 changes with a hit and at 0.35 or more only 2 of 6). Read the report after the render and move a level only if it says so.
88
+ Every pulled sound is levelled on the way in (the interface effects got a gain of 0.7 to 0.8), and `reelkit render` then masters the whole film to -14 LUFS, so only the balance between these matters. At 0.2 to 0.3 an effect sits 6 dB or more under the music, which the tester of 0.8.0 found too quiet to register against the picture; a swell above about 0.35 hides the impact that ends it (the impact no longer rises out of what came before, and the report counts a change with no hit: on a test film, whooshes at 0.2 left 5 of 6 changes with a hit and at 0.35 or more only 2 of 6). Read the report and audition the mix when possible; change levels for an audible balance or timing problem, not merely to increase a measured count.
89
89
  - **Which sounds swell.** The library's own "UI" pack (`sfx-ui-soft-whoosh`, `sfx-ui-fast-whip`) is made of short bursts that start at full level and fall away: they are hits to a listener and to the report, not swells. A swell that carries rises for half a second or more and cuts off on the change. Search for these words: `reelkit assets search "reverse whoosh" --kind sfx` (the reverse whooshes of the Quantum Motion pack, 1.7 to 2.3 seconds, with energy between 2 and 10 kHz), `"whoosh sweep"` and `"wind sweep"` for longer air, and `"riser building up"` or `"riser tension"` for a lead into a reveal. Their length is at the end of the search line: give it to `cueBefore` or `cuesOnChanges` (`whoosh: { frames }`), minus the tail after the peak. Measured on a test film, seven reverse whooshes at 0.2 gave six swells where they stand, while the film's UI whooshes gave three at the same places.
90
90
  7. **Silence.** Before the biggest moment, drop the effects, or the music, for a beat or two. The hit that follows then lands. Give `Music` a `dips` entry for the rest, in absolute frames: `dips={[{ from: reveal.startFrame - 24, to: reveal.startFrame, volume: 0.05 }]}` brings the track down for the last moments before the reveal and back up after it.
91
91
 
@@ -93,7 +93,7 @@ Place all the cues once, outside the scenes, with `SoundCues`; use `cuesOnBeats`
93
93
 
94
94
  ```tsx
95
95
  import React from "react";
96
- import { AbsoluteFill } from "remotion";
96
+ import { AbsoluteFill } from "reelkit/frame";
97
97
  import { Music, SceneFrame, SoundCues, cueBefore, cuesOnBeats, cuesOnChanges } from "reelkit/kit";
98
98
  import type { VideoProps } from "reelkit/kit";
99
99
 
@@ -188,3 +188,7 @@ The same numbers are in the render's `data.sound`. A measurement that cannot be
188
188
  ## Check before you show it
189
189
 
190
190
  `reelkit preview` shows two frames per scene and prints a continuity line and a beat line (how many scene changes carry something across and land on the beat). It prints no rhythm line: the rhythm of the scene lengths is `reelkit plan check`'s. Look for a shot that holds still for long (the films were still for 11 to 35 percent of the time and no more), a shot whose type is over the object, and a second accent colour. Then show the user the frames, as in the main steps.
191
+
192
+ ## Brand reveals and transformations
193
+
194
+ For a brand-led shot, consult `reference/brand-motion.md`. Choose `BrandTransform3D` turn, arc or launch by the idea it connects; use the supplied identity, finish in a readable neutral pose, and place the sweep and lock from `brandTransformFrames` with `cuesFor(..., "transform")`. Several 3D shots are appropriate for a requested brand film when they each have a different purpose. Map the `transform-sweep` and `transform-lock` roles to the chosen whoosh and impact files. Treat the sound report as evidence to investigate, not a quota to fill with extra hits. Existing approval to edit or render carries through to the requested revision.
@@ -32,19 +32,19 @@ description: Use when deciding how a scene looks and moves - layout, typography,
32
32
  - Reveal Latin text with a masked rise (translate up from behind an overflow-hidden box), word by word, about 2 frames apart. Avoid plain opacity fades for headlines. Hebrew never uses a mask: its words enter whole (see `reference/hebrew-rtl.md`).
33
33
 
34
34
  ## Motion
35
- - **Springs, never linear moves and never cartoon bounce.** Use `spring()` with a damping high enough for a tiny overshoot at most. Presets (stiffness / damping): snappy UI 320 / 30, default containers 170 / 26, heavy type and logos 120 / 24.
35
+ - **Match the motion to the material.** Springs suit responsive UI and weighty arrivals; restrained eased motion suits calm or premium shots. Bounce, squash and overshoot suit playful scenes when deliberate. Useful spring starting points (stiffness / damping): snappy UI 320 / 30, containers 170 / 26, heavy type and logos 120 / 24.
36
36
  - A big move gets a small anticipation first: a few frames of pull the other way.
37
37
  - Exits are faster than entrances. An entrance takes about 0.1 to 0.25 seconds.
38
- - Linear motion is only for movement with no start or end inside the shot (a slow camera turn, a continuous scroll). Every entrance, exit and change of state is a spring.
38
+ - Linear motion suits steady scrolls or continuous travel; entrances and stops need an intentional easing or spring unless the chosen effect is a hard cut.
39
39
  - **The camera is a group.** Put the whole scene inside one wrapper and move that: a slow push of 2 to 4 percent across a shot, on a softer spring than the content. Never scale text up by enlarging a container that holds it as an image; set the size so it stays sharp.
40
- - **Work on a grid.** Place every event on a fixed grid (half a second is a good default) or on the spoken words. Something happens on every grid step.
41
- - **One thing moves at a time.** Stagger related items by 4 to 8 frames rather than moving everything at once.
40
+ - **Choose the clock.** Use spoken triggers for narrated meaning and music beats for rhythmic decoration. Do not invent an event to fill every grid step.
41
+ - Stage attention. Stagger a list when each item matters; move related objects together when their shared action explains the idea.
42
42
  - **Pace to speech.** One visible change per spoken beat, roughly every 0.4 to 1.2 seconds. Use the word timings in `s.words` to bring an element in on the frame its word starts, never before.
43
- - Something new should happen every 2 to 4 seconds, and something must move within the first half second of the video. No dead stretches.
43
+ - Make the premise clear early. Change the picture when attention or meaning needs it; a useful pause, close-up or readable hold is not dead time.
44
44
  - **Rhythm is hit, hold, build.** A fast move, then a hold of about half a second where nothing new enters, then the next move. Constant motion reads amateur; contrast reads expensive. During a hold, settled elements keep their slow breathe.
45
- - **Nothing sits perfectly frozen for more than about a second.** After an element settles, keep a very slow drift or scale (1 to 2 percent over the scene) alive so the frame breathes.
45
+ - A held pose can remain still. Add a slow drift only when it supports the look and keeps text sharp; do not force it onto footage or a reading-heavy shot.
46
46
  - Let an element finish animating and stay readable for at least 1.5 seconds before it leaves. A label or phrase of more than one word stays at least 1.3 seconds; the closing title or message is held at least 1.5 seconds before the last frame. If the plan's length cannot fit that, lengthen the scene and tell the user.
47
- - Counters, progress bars and drawn lines finish before the scene's midpoint.
47
+ - Counters and progress bars land on the event they explain, such as the spoken result or task completion; leave a readable hold afterward.
48
48
  - Text that swaps inside a container that is also changing size needs its own exit and enter timing, or old and new text overlap.
49
49
  - **Whatever a scene adds, the scene removes.** Every overlay, label and effect leaves when its moment ends. A leftover from an earlier scene is the most common thing a review finds.
50
50
  - **Show exactly what is being said.** Each visual belongs to its own sentence. A picture that fits only roughly is worse than plain type, and the same picture or clip never appears twice.
@@ -52,8 +52,8 @@ description: Use when deciding how a scene looks and moves - layout, typography,
52
52
  ## Legibility over images and footage
53
53
  - Text over an image or footage needs help: a dim layer of 0.2 to 0.45 on the media, or a solid plate behind the text, plus a soft shadow.
54
54
  - In footage mode keep overlays to one graphic at a time, clear of the subject.
55
- - Talking to a still camera gets dull fast. Give each sentence one small punch-in on its most important word: 10 to 15 percent, on a spring, centred on the speaker's face, landing on the frame the word starts and resetting at the next sentence. Give the last sentence a slow 3 percent push instead. Do not add this over footage that already has zooms of its own (screen recordings from tools that zoom automatically): two zooms on top of each other make people dizzy.
56
- - Never let more than about 3 seconds of speech pass in footage with nothing new on screen.
55
+ - Use a punch-in on selected emphasis or to improve framing; calm personal speech may need none. Keep the face framed and avoid repeated resets. Do not add a second zoom over footage that already zooms.
56
+ - Add an insert where it clarifies the speech or demonstrates evidence, not merely because a timer elapsed.
57
57
  - A punch-in softens 1080 footage. If the user can still choose, suggest filming in 4K when zooms are planned.
58
58
 
59
59
  ## Truth on screen
@@ -62,7 +62,7 @@ description: Use when deciding how a scene looks and moves - layout, typography,
62
62
  - Do not invent product screens or features. A recreated interface that is not the user's real one is illustrative and should look generic.
63
63
 
64
64
  ## Determinism
65
- - Never use `Math.random()` or the clock. A frame must render the same every time. Use `random(seed)` from remotion for any variation.
65
+ - Never use `Math.random()` or the clock. A frame must render the same every time. Use `random(seed)` from reelkit/frame for any variation.
66
66
  - Everything is a function of `useCurrentFrame()`. No CSS transitions or animations, no timers.
67
67
 
68
68
  ## Shape of a 30 second video
@@ -86,15 +86,13 @@ Hook (first 1.5 s: the boldest visual and claim) → context (one line, one visu
86
86
  - Compute heavy geometry once, outside the frame function, and only position it per frame.
87
87
  - Grain or paper texture is one static layer above everything, outside the camera group. Inside a zooming group it is slow and the grain swells into blotches.
88
88
 
89
- ## Banned, because they read as AI-made or cheap
90
- These hold unless the look chosen in `reference/styles.md` names an exception (a showreel look uses flat colour fields; the neon look uses glow on its hero element and lines).
91
-
92
- Flat solid backgrounds, opacity-only fades, everything entering at once, rainbow or multi-stop gradients on text and UI, particles and sparkles, glows on interface chrome, emoji as graphics, bouncy easing, gratuitous 3D flips, a centred title on a plain gradient, mixed icon styles, lorem ipsum, and anything that looks like a stock template.
89
+ ## Techniques need a purpose
90
+ A flat field, fade, particles, glow, comic bounce or 3D transformation can be right for the chosen idea. Avoid combining them as generic decoration. Keep identity, hierarchy and readability intact. Placeholder copy, false product results and unrelated logos are defects regardless of style. Consult `reference/styles.md` and `reference/brand-motion.md` for techniques that fit the message.
93
91
 
94
92
  ## The studio test
95
93
  Before showing anything, every answer is yes:
96
94
  1. There is one clear idea at each moment, and the eye knows where to look.
97
- 2. Every move starts and ends on a spring, with a small anticipation before a big one.
95
+ 2. Motion starts, lands and holds intentionally, with the timing and weight the material needs.
98
96
  3. Nothing is frozen longer than the look allows, and nothing shakes without a reason.
99
97
  4. Every word reads at phone size, in the right order, uncut and not touching its neighbour.
100
98
  5. Every colour comes from the palette that was agreed; no shade crept in on the way.
@@ -102,6 +100,10 @@ Before showing anything, every answer is yes:
102
100
  7. It looks like a studio made it, not like a template or a slide deck.
103
101
 
104
102
  ## Check your own frames
105
- Go round at least twice: preview, fix, preview again. The first pass finds what is broken; the second finds what is merely weak. If the review shows that something in the approved plan cannot work (an ending too small in the frame), make the smallest change that fixes it and tell the user what changed and why; a different scene or different words goes back for approval.
103
+ Preview and fix observable defects; repeat after a real change or unresolved problem. If an approved shot does not fit, make the smallest layout or timing correction and explain it. A substantial change of message or concept needs user direction when it was not already delegated. Use `reference/delivery-review.md` to verify the export.
106
104
 
107
105
  Run `reelkit preview`, then look at both frames of every scene in `out/preview/` (early at 30%, late at 90%) as a harsh director would. Hunt for: text overlapping during a swap, text cut by the frame edge, type too small for a phone, a frame with nothing in it, and anything that looks like a template. Fix what is real, then check again.
106
+
107
+ ## Choosing a transformation
108
+
109
+ Change the shot when the idea changes or the same object must take a new role. Name the relationship first: question to answer, parts to whole, product to result, or result to brand. Keep the agreed palette and the actual identity through the change. Use `reference/brand-motion.md` to choose a 2D carry, clear cut or branded 3D arrival and its sound. A deliberate readable hold can remain still; do not add drift or a flip just to meet a motion quota.
@@ -5,16 +5,16 @@ description: Use when adding sound effects to a video - which moments get a soun
5
5
 
6
6
  # Sound design
7
7
 
8
- A few well-placed sounds make motion feel real. Too many make a video tiring. The voiceover is always the most important sound.
8
+ Sound gives selected actions weight and shapes the story. Density follows the material: calm speech may need almost no effects; an energetic graphic sequence may use many small cues. Spoken words take priority whenever speech is present.
9
9
 
10
10
  ## What gets a sound
11
11
  - **Entrances that matter:** the hook's first hit, each numbered point arriving, the payoff. A whoosh, swipe or soft impact.
12
12
  - **Scene changes:** a short transition sound across the cut.
13
13
  - **Interface moments:** a notification arriving, a button tap, a tick appearing. A click, pop or chime.
14
14
  - **Build-ups:** a riser into the payoff or the final call to action.
15
- - Not every element. Two to four sounds per scene at most, and usually one. A sound on every movement sounds like a toy.
16
- - At most one whoosh or swish per scene, and quieter than the hits on purpose.
17
- - One deep sub or boom per scene at most, and one or two big impacts in the whole video, on its peak moments.
15
+ - Choose the important actions rather than sounding every decorative element. A dense interface sequence can use quiet ticks; a personal story can rely on voice and silence.
16
+ - Keep a family of sounds and reserve the strongest hits for the main moments. Whooshes support movement; they should not cover its landing or a spoken word.
17
+ - Use a boom when the reveal needs weight, not at every cut. A deliberate quiet beat can make the next arrival stronger.
18
18
 
19
19
  ## Finding sounds
20
20
  1. `reelkit assets search "<description>" --kind sfx` with what you want to hear: "whoosh", "soft click", "notification pop", "riser", "camera shutter", "bass impact". Add "one-shot" or "short" to the query for one-shots.
@@ -23,25 +23,43 @@ A few well-placed sounds make motion feel real. Too many make a video tiring. Th
23
23
  4. Reuse one whoosh and one click across the video rather than a different sound each time. Consistency sounds designed.
24
24
 
25
25
  ## Timing
26
- - Start a whoosh or swipe **2 to 3 frames before** the visual lands. Early feels in sync; late feels broken.
26
+ - Align the audible peak with the visual landing. A short UI whoosh may need a 2 to 3 frame lead; a reverse swell may need much more. Inspect the actual file's attack and tail rather than using one lead for every sound.
27
27
  - Put impacts and clicks on the exact frame the visual hits.
28
28
  - Start a riser so that it **ends** on the reveal: `at = revealFrame - durationSec * fps`.
29
29
  - Use the word timings in `s.words` when a sound belongs to a spoken word.
30
30
 
31
31
  ## Volume
32
- - The voiceover plays at 1. Sound effects sit between 0.2 and 0.45. Impacts on the hook can go to 0.6.
32
+ - The voiceover plays at 1. While narration is heard, sound effects stay at 0.3 or below. Without narration, effects can sit between 0.2 and 0.45 and a chosen hook impact can reach 0.6.
33
33
  - Ambience and drone beds: 0.06 to 0.12.
34
- - Never let two loud sounds overlap. Stagger them.
34
+ - Overlap only deliberately; avoid summed peaks that clip or mask the speech. Lower competing layers before mastering.
35
35
  - When the same kind of sound repeats, grade it: the first at full level, the rest quieter.
36
36
 
37
37
  ## Background music
38
- - A video with little or no voice needs a track; a voice-led video usually gains from a quiet one. Search by mood and use: `reelkit assets search "clean airy product launch" --kind music`, `"lo-fi calm"`, `"driving phonk"`, `"epic cinematic build"`, `"minimal tech under a voiceover"`. Each result says its mood and tempo.
39
- - `reelkit assets pull <id>`; the pull prints the path. Place it once, outside the scenes, so it runs across the cuts: `<Sfx src={urls["<path the pull printed>"]} at={0} volume={0.12} />`.
40
- - Under a voiceover the music sits at 0.08 to 0.15. With no voice it carries the video at 0.4 to 0.6, and the effects come down to 0.2 to 0.35 so they sit inside it.
41
- - Library tracks are about 30 seconds. For a longer video place the track again on a scene change, where a transition sound covers the join.
42
- - One track for the whole video. Pick the tempo first: scene changes on a grid of the beat (60 / bpm seconds, or two or four of them) make ordinary cuts feel designed.
38
+ - Choose music from the story's tone and pace; a personal or documentary moment can work with no music. Search by genre, mood and use, usually with English library terms. Decide a fitting track and explain the reason rather than requiring the user to choose a playlist.
39
+ - `reelkit assets pull <id> --music` records the selected track and its beat grid. Place `<Music src={urls[manifest.music.key]} />` once outside the scenes. It applies the measured gain, ducks under speech, loops when needed, and fades at the end. Do not manually repeat the track with `Sfx`.
40
+ - Leave `Music` at its defaults initially; adjust `volume`, `duckTo` or a planned `dips` interval only after listening to the rendered mix. The music should support the brand reveal without covering its lock sound.
41
+ - One track is usually enough for a short film. Pick its tempo before beat-led scene timing, and read `reference/beat-sync.md`. Align the peak with the reveal, allow a rest before it, and give the ending a musical resolution. Under speech prefer instrumental passages; avoid lyrics competing with the message. The current `Music` component loops from the supplied file's start, so trim a derived copy if a different loop section or entry point is needed.
43
42
  - Never use the music of a reference or of any video the user points at. Describe its mood and tempo and search the library with that.
44
43
 
44
+ ## Music direction by material
45
+
46
+ | Material | Starting search direction | What to listen for |
47
+ |---|---|---|
48
+ | Tech demo or energetic explainer | `minimal tech instrumental`, `tech house instrumental`, `glitch hop` | Clear rhythm, room for words, no long empty intro |
49
+ | Tutorial or calm routine | `chillhop instrumental`, `deep house soft`, `light acoustic` | Steady support without a melody fighting the explanation |
50
+ | Premium product or brand | `cinematic minimal`, `dark downtempo`, `luxury deep house` | Restraint and a reveal that earns its weight |
51
+ | Montage or fashion | `fashion house`, `UK garage instrumental`, `nu disco` | Phrases that match changes of action and framing |
52
+ | Personal story | `felt piano`, `documentary acoustic`, or silence | Emotional fit without over-scoring a small moment |
53
+ | Humor or playful graphics | `quirky funk`, `chiptune`, `comedy pizzicato` | Timing that supports the joke without dictating it |
54
+
55
+ These are starting terms, not required genres or BPM ranges. A supplied track takes precedence when the user wants it. Do not infer commercial rights from a song being downloadable or present in an editor; verify a relevant license if the destination requires it.
56
+
57
+ ## Phone playback and verification
58
+
59
+ Do not judge music by its sub-bass alone. A track with audible percussion, melodic content or bass harmonics can survive small speakers better than a sub-only bed. Check speech intelligibility and whether the intended music still contributes with reduced bass or actual phone playback. Adjust relative levels and arrangement, not just the final loudness.
60
+
61
+ Verify the finished export for present stems, cue alignment, clipping and truncated tails (`reference/delivery-review.md`). Measurements can locate a problem but cannot prove emotional fit. Do not impose a universal frequency-energy percentage, hit count or volume ratio. If playback is unavailable, report the checks you performed without claiming to have listened.
62
+
45
63
  ## The interface pack
46
64
  The library holds a matched set made for interface motion; search these words with `--kind sfx`: "soft ui whoosh" and "fast whip" for moves, "bubble pop" and "glass tap" for things appearing and being pressed, "keyboard typing" under a typed field, "toggle switch", "message sent", "notification ping", "success chime" on a tick, "sparkle shimmer" on an AI result, "counter ticks" under a number counting up, "soft impact" and "sub bass drop" for the landing and the payoff, "short riser" into a reveal, "camera shutter" on a freeze. Sounds from one set sit together; mix sets only when one is missing what you need.
47
65
 
@@ -55,3 +73,7 @@ The library holds a matched set made for interface motion; search these words wi
55
73
  <Sfx src={urls["assets/lib/<id>/clip.mp3"]} at={12} volume={0.35} />
56
74
  ```
57
75
  Inside a SceneFrame, `at` counts from the start of that scene.
76
+
77
+ ## Branded transformations
78
+
79
+ Read `reference/brand-motion.md` when the move reveals a brand, carries an object, or turns the product toward the viewer. Use `brandTransformFrames` and `cuesFor([start, settle], "transform", { offset: scene.startFrame, voice: true, sweepFrames: 10 })` for one sweep and one lock. Adjust the sweep lead to the actual sound file. Keep sounds outside `Scene3D`, and add the scene offset once. Listen to the final video; a high hit count is not a quality target by itself.
@@ -0,0 +1,55 @@
1
+ ---
2
+ name: studio-editing
3
+ description: Choose an editing approach from the actual material: footage, screen recordings, graphics, mixed media, pacing, inserts and sound. Read for an open brief or an existing-video edit.
4
+ ---
5
+
6
+ # Choose the edit from the material
7
+
8
+ Understand the message, audience, intended action, emotional tone and strongest source moments before adding effects. Watch supplied footage when playback is available; otherwise inspect sampled frames, metadata and an accurate transcript and state that limitation. Read the entire transcript in context, including pauses and emphasis. Do not infer spoken words from a few stills.
9
+
10
+ Choose the direction and explain it briefly. Ask about a missing fact, audience or goal only if it changes the edit. A request to improve a particular shot should produce that revision, not a new briefing or an unsolicited replacement concept.
11
+
12
+ ## Choose the mode
13
+
14
+ | Material and purpose | Starting approach | What would weaken it |
15
+ |---|---|---|
16
+ | Personal or calm talking head | Preserve expression and useful pauses; clean captions; occasional motivated punch-in; quiet music or none | Constant zooms, whooshes and cuts that remove emotional timing |
17
+ | Energetic explanation or opinion | Strong opening claim supported by evidence; emphasis cuts; a few illustrative inserts | Effects that obscure the argument or alter its meaning |
18
+ | Tutorial or screen recording | Real screen, callout on the relevant control, step tracker, readable hold after the action | Camera moves or captions covering the control being taught |
19
+ | Product or premium brand | Supplied identity, consistent type and materials, restrained object motion, purposeful sound | Generic fabricated UI, conflicting styles or perpetual logo spin |
20
+ | Narration carried by graphics | A visual metaphor per idea; word-timed emphasis; continuity through a recurring object, type or accent | Repeating one flat layout or animating every word equally |
21
+ | Fashion, montage or reveal without speech | Cut by action and musical phrasing; minimal text; peak on the reveal | Adding explanatory captions or a narrator without a reason |
22
+
23
+ These are starting points, not templates. Mixed media can change visual worlds at a change of meaning while retaining a thread. A consistent brand system can vary framing, depth and scale without changing its identity.
24
+
25
+ ## Build the edit map
26
+
27
+ For a substantial new film, keep a compact table in the project notes: source time or scene, purpose, visible action, spoken trigger or beat, text and sound. Each insert needs a reason: explain a step, demonstrate a claim, reveal the result, or make an abstract idea visible. The first few seconds should make the premise clear; a hook can be a strong image or a question, not necessarily a loud effect. End with an action only when the video's goal calls for one.
28
+
29
+ Use real footage, screens and logos first. Use code for exact type, numbers, diagrams, UI interactions and brand motion. Generate imagery only when an illustrative or filmed subject is missing. Search the shared library before generation, check the allowance with `reelkit whoami`, and use an alternative when the allowance is exhausted or a result cannot be used. Do not repeatedly regenerate an asset to chase minor taste differences.
30
+
31
+ For a new concept, show the essential direction if the user needs to choose it. Earlier approval and an explicit instruction to edit or render remain valid. A routine fix does not restart approval.
32
+
33
+ ## Footage in this CLI
34
+
35
+ Reelkit overlays graphics on registered footage; it is not a CapCut draft editor or an automatic transcript-based jump-cut tool. It does not provide a CapCut JSON writer, original-speech transcription import, or an edit-decision-list command. Do not invent those commands or replace someone's recorded speech with generated narration.
36
+
37
+ Register a derived working copy with `reelkit assets upload ./working.mp4 --footage --describe "what the footage shows"`. Preserve the original. The plan then uses `mode: "footage"` and every scene uses `treatment: "footage-overlay"`. The manifest uses the footage's dimensions, capped at 1920 on the long side, and its full duration. Use one `FootageLayer` below the graphics; its `muted` default is true. Set `muted={false}` when the original audio is wanted, and do not duplicate that audio as another track. For existing speech use `voice: "none"` to avoid generating a second voice; that setting means no generated narration, not that the source audio must be silent.
38
+
39
+ If the requested edit needs cuts, normalization or reframing, make a separate derived clip with available local video tools, verify its new source timing, and register that copy. If a needed operation is unavailable, identify the missing capability. Do not install or automate another editor merely because the inspiration skill uses one. Keep media paths stable and the sources reproducible.
40
+
41
+ Original-speech captions need accurate timestamps from the supplied transcript or an available transcription tool authorized to process that recording. The standard manifest's `s.words` comes from generated voiceovers; uploading footage does not populate it. Keep original-speech timings in a separate local source and explicitly implement and validate their use in the composition. Do not hand-edit the generated manifest or use generated narration timings for the speaker. If timings cannot be obtained, complete the feasible edit and report the caption limitation. Music ducking also needs these real speech spans: pass `Music` a `scenes` array of `{ startFrame, words }` using scene-local word seconds, or keep the music conservatively low through the recording. With empty manifest words the default music cannot detect source speech.
42
+
43
+ ## Inserts and pacing
44
+
45
+ Prioritize the moments where the viewer needs help. A number pop should show the real number as it is said; a callout should point at the actual control; a step tracker should advance with the step. Avoid unrelated B-roll that merely looks attractive. Align narrated visuals with the actual word onset, not the nearest clip boundary (`reference/voice-sync.md`). Keep captions and inserts clear of faces and controls.
46
+
47
+ Cut dead air, false starts and repeats only when it preserves meaning and cadence. Do not remove all pauses. Use a punch-in for emphasis or reframing, not on every sentence. Do not stack it on a screen recording that already zooms. Reduce travel or lengthen a move if it smears or ghosts; a held frame is valid when the viewer needs to read, compare or feel the moment.
48
+
49
+ When source speed changes, update the entire clock. At speed factor r, source time t maps to output time t/r. For a trimmed segment beginning at source time a and output time b, map t to b + (t-a)/r. Recompute word events, inserts and SFX from the edited timeline; regenerate narration timings if generated narration changed. Choose music phrasing separately rather than stretching the finished mix to repair sync.
50
+
51
+ ## Design and sound references
52
+
53
+ Read only what the edit needs: `reference/styles.md` for visual techniques, `reference/motion-design.md` for staging, `reference/brand-motion.md` for transformations, `reference/three-d.md` for depth, `reference/hebrew-rtl.md` for Hebrew, `reference/captions.md` for generated-speech captions, and `reference/sound-design.md` for scoring. These are choices that serve the video, not requirements to use every technique.
54
+
55
+ Useful transformations include a field becoming its result, a sketch resolving into a product, a number joining its chart, or a product turning to expose its relevant face. Use particles, text rings, a comic or a 3D environment only when that metaphor fits the message and chosen style. Keep the identity recognizable after the transformation and give it a readable hold.