V1 is not an “AI makes the whole video” system. It is a reproducible editorial build that combines real recordings, generated artwork, programmatic graphics, synthetic narration, word-level timing, and ordinary video engineering.

The result: a 2:48 working cut of MHR 001 at 1920×1080 and 24 fps, with H.264 video, 48 kHz AAC audio, and a toggleable English subtitle track.

The important part is not the model. It is that the episode can be rebuilt from source assets by running one Python script.

The pipeline at a glance

1. EvidenceReal lab testing, photos, screen recordings, measurements, and the review verdict.
2. ScriptTimed James and Milo dialogue, visual beats, ratings, caveats, and handoff.
3. VoiceJames recording plus an approved ElevenLabs voice for Milo.
4. VisualsReal B-roll, Pillow information cards, and Grok Imagine presenter art.
5. TimingWhisper word timestamps drive captions and audio-reactive mouth states.
6. AssemblyPython calls FFmpeg to normalize, concatenate, mix, caption, and package.
7. QCContact sheets, frame checks, automated media inspection, and revisioned cuts.

What each tool actually did

StageToolJobStatus in Draft 1.2
Research and editorialJames + MiloTest the product, identify the real story, write the script, and keep James' and Milo's ratings independent.Used
Presenter artworkxAI Grok Imagine image modelGenerate a reference-locked James-and-Milo frame using character references and a sanitized cartoon lab.Used
Alternate generated openerxAI Grok Imagine videoCreate a ten-second futuristic MHR studio opener with generated audio.Saved, not inserted
NarrationElevenLabsRender Milo's approved narration voice from the final script.Used
TranscriptionWhisper Large V3 Turbo via MLXProduce word-level timestamps for captions and timeline alignment.Used locally
GraphicsPython + PillowRender product cards, integration flow, setup pain, telemetry, caveats, verdict, ratings, and economics.Used
Presenter motionNumPy + Pillow + FFmpegSwitch between approved open- and closed-mouth states using the speech envelope. No generative motion model is involved.Used
Real B-rolliPhone/iPad captureShow Apple Home manually controlling the M3 Ultra plug.Used
Edit and masteringFFmpegNormalize every segment, concatenate visuals, mix audio, loudness-normalize, mux subtitles, and create the MP4.Used

1. Start with evidence, not a prompt

The episode began with a real five-plug deployment, not a product page. We connected the plugs through Zigbee, the MZ1 bridge, Matter, Home Assistant, Prometheus, and Grafana. That work supplied the claims, caveats, photographs, and verdict.

This ordering matters. The script comes after the test. Generated visuals are illustrations of evidence; they are not substitutes for it.

2. Freeze the spoken structure

The script has four explicit audio blocks: the branded jingle, James' recorded introduction, a 350 ms handoff pause, and Milo's narration. The narration is divided into product, integration, deployment, setup, telemetry, control, measurement caveats, verdict, ratings, and value.

V1 stores the visual timing directly in Python:

shots = [
    ("01-cartoon-james-milo", presenter_intro, 18.953, "video"),
    ("02-cartoon-milo",      milo_closeup,    11.700, "video"),
    ("03-product",           product_card,    12.500, "still"),
    ("08-apple-home-control", real_b_roll,     6.000, "video"),
    # ...caveats, verdict, ratings, economics
]

It is crude but honest: each beat names its source, type, and exact duration. The next version should move this manifest into shots.yaml, but we did not pretend that abstraction already existed.

3. Build a locked voice and timing track

Milo's narration was generated with an approved ElevenLabs voice. Both James' recording and Milo's narration were then transcribed locally with MLX Whisper using word timestamps.

Those timestamps serve two purposes:

The resulting subtitle track stays optional in the MP4. We mux it as English mov_text rather than permanently burning captions into the picture.

4. Mix three visual classes

Real material

Lab photographs, product photographs, James' introduction, and the Apple Home control recording establish that the review happened in a real environment.

Programmatic cards

Pillow renders the 1920×1080 information frames. Text, spacing, colors, and layout stay deterministic and easy to revise.

Generated artwork

Grok Imagine created the presenter proof from James, Milo, and sanitized lab references. We selected one candidate and preserved its provenance.

Important distinction: Grok Imagine generated an alternate ten-second video opener, but that clip was saved as a candidate and was not inserted into Draft 1.2. The working cut uses the approved four-second MHR opener.

5. Animate the presenters deterministically

We did not ask a video model to regenerate James and Milo for every line. That would introduce identity drift, hand errors, background changes, and expensive retakes.

Instead, we made minimal mouth-state edits to the approved frame, feather-composited the patches, and rendered a two-state animation. For each 24 fps frame, the script measures a smoothed RMS envelope from the active speaker's audio and chooses either the open or closed state.

speech = smooth_rms(audio, fps=24) > threshold
for mouth_open in speech:
    frame = open_state if mouth_open else closed_state
    ffmpeg.stdin.write(frame)

This is intentionally simple. It is not phoneme-level lip sync. It is stable, repeatable, and keeps the approved character image intact.

6. Normalize before concatenation

Mixed media fails at the seams. Before concatenation, every still and clip is converted to the same delivery geometry and codec profile:

scale=1920:1080:force_original_aspect_ratio=decrease,
pad=1920:1080:(ow-iw)/2:(oh-ih)/2,
setsar=1,fps=24

Once the segments share an exact format, FFmpeg's concat demuxer can join them without re-encoding the complete visual timeline.

7. Master audio separately

The visual and audio timelines are built separately. FFmpeg resamples each audio source to 48 kHz, fades and attenuates the opener, concatenates the four blocks, and applies loudness normalization at −16 LUFS integrated, −1.5 dB true peak, and an 11 LU loudness range target.

The mastered WAV is then encoded to 192 kb/s AAC and muxed with the visual track and subtitles.

8. Treat revisions as builds

RevisionWhat changedWhy it mattered
Fast draftReal photos, information cards, James' voice, Milo narration, captions.Proved the complete editorial and mastering path before spending time on motion.
Draft 1.0Added independent James and Milo rating narration and rating card.Made the review format explicit and repeatable.
Draft 1.1Replaced the opening stills with controlled cartoon presenter clips.Added character presence without generative-video instability.
Draft 1.2Inserted six seconds of real Apple Home control B-roll inside the relay-control discussion.Matched the claim with direct visual evidence.

What V1 gets right

What V1 still gets wrong

V2 direction

The next useful abstraction is small:

script.md
shots.yaml          # source, in/out, duration, transition, VO beat
assets/
  real/
  generated/
  voice/
build.py             # deterministic assembly
out/
  review.mp4
  captions.srt
  contact-sheet.jpg

Generated video should remain a swappable shot source—not the editor, timeline, or source of truth. That keeps cloud I2V, local models, real footage, and ordinary graphics interchangeable.

Bottom line: the best part of the V1 pipeline is its boring center. Models create selected assets. Python records the editorial decisions. FFmpeg makes the episode.

Companion post: MHR 001: ThirdReality Smart Plug Gen3. Telemetry implementation: ThirdReality → Home Assistant → Prometheus recipe.