WAN LipSync Plan Step
Execute one chunk of your lipsync timeline
- plan
- image_batch
- previous_frames
- start_image
- previous_frames
- keep_frames
If WAN LipSync Timeline Planner is the architect, this node is the foreman on the site: it takes one task from the plan and hands the sampler exactly what it needs to generate that one chunk - which reference image to start from, how many frames of the previous output to carry forward, and whether a transition has to be blended at the start. It lives inside a loop, one call per extension chunk, until the whole timeline is generated.
What it does
The planner produces a list of tasks; Plan Step reads them one at a time based on loop_index. For each task it:
- validates that the accumulated timeline is exactly where it should be - the
previous_framesyou feed in must match the task's expected start frame, which is the drift check that keeps a multi-chunk generation from silently desynchronizing; - picks the right reference image from
image_batchfor this segment; - outputs the
start_imagethe sampler should condition on, theprevious_framesto keep, andkeep_frames- the count of how many frames this chunk must generate.
The inputs are plan, loop_index, image_batch, previous_frames, and blend_mode (linear or pyramid). The outputs are start_image, previous_frames, and keep_frames.
The blending bit, demystified
When a task starts with an image transition - you're switching from reference shot #1 to shot #2 - the node blends the tail of the accumulated frames with the new reference image so the switch isn't a hard cut. blend_mode pyramid uses a Laplacian pyramid blend, which is smoother across differing textures and colors than plain linear. The source is careful about one thing: that blending only happens on a temporary conditioning copy. The accumulated feedback batch that gets carried forward is never modified in place, so the running history stays authoritative and the blend can't poison the next chunk. That's the kind of detail that separates a carefully-built node from a hack.
Why the validation matters
Long multi-chunk generations have a failure mode where each loop iteration is fine but the whole thing drifts - frame counts accumulate rounding error, the sampler returns one frame short, and by chunk 40 you're out of sync. Plan Step checks the accumulated frame count against the plan on every iteration and errors the moment they disagree, so you find out at chunk 2 instead of at the final save. Annoying while debugging, invaluable in production.
Wiring it up
In a typical Eclipse WAN InfiniteTalk loop: Timeline Planner → Plan Step (plan in, loop_index from a loop counter) → sampler → save/preview, with the generated frames fed back into Plan Step's previous_frames and a keep_frames/feedback node trimming the carried batch to the overlap. The report output from the planner tells you how many iterations to expect, so you can size the loop.
Install it
Ships in ComfyUI_Eclipse. ComfyUI Manager → search "Eclipse" → Install → restart, or:
cd ComfyUI/custom_nodes
git clone https://github.com/r-vage/ComfyUI_Eclipse
Under Eclipse → Video. Standard pack deps (opencv-python, pilgram, PyYAML, aiohttp; portable installs may need pip install -r custom_nodes/ComfyUI_Eclipse/requirements.txt).
Gotchas
Plan Step is strict on purpose - mismatched image_batch count, wrong loop_index, or accumulated frames that don't match the plan all raise errors rather than limping on. If you hit "accumulated timeline drift," it usually means keep_frames handling in your loop is off (you're carrying more or fewer frames than the overlap). And remember previous_frames must be a single batch; feeding it a list is a classic beginner stumble. This is a node where reading the error message instead of fighting it saves you an hour.
Inputs (5)
| Name | Type | Default | Description |
|---|---|---|---|
| plan | WAN_LIPSYNC_PLAN | — | |
| loop_index | INT | 00–65535 | — |
| image_batch | IMAGE | — | |
| previous_frames | IMAGE | — | |
| blend_mode | COMBO | linear | 2 options: linear, pyramid |
Outputs (3)
| Name | Type | Description |
|---|---|---|
| start_image | IMAGE | — |
| previous_frames | IMAGE | — |
| keep_frames | INT | — |