TS Extract Generated Video
Your Half-Mask Render Comes Back Twice Too Wide. This Node Takes Back the Right Half
- decoded_wide_video
- layout
- generated_video
You did the side-by-side thing: reference clip on the left, latent to be generated on the right, one wide canvas, a mask so the sampler only denoises the right panel. It works - motion transfer on Wan is one of the most-used workflows in open video right now, and Wan Animate alone pulls hundreds of threads a month. Then you decode, and you're holding a video twice as wide as the clip you wanted, with a faint dark stripe down the middle where the halves meet.
TS Extract Generated Video (TSHalfMaskVideoExtractGenerated) is the second half of that pair. Feed it the decoded wide batch and the layout the canvas was built from, and it hands back only the generated right panel, at the resolution you originally asked for, with the seam band trimmed off.
What it actually does to the pixels
The node is a crop, a seam repair and a resize, in that order.
It reads the layout you feed it and refuses anything that isn't a v1 layout dict from this pack (Invalid Half Mask Video layout - that's a real error you'll see if you point it at some other node's data). Then it takes the right panel's rectangle out of that layout and scales the numbers by however much your decoded video differs from the canvas that was built: decode-time resolution changes, a 2x upscale before this node, whatever. Uniform scale factors, applied to x, y, width and height independently, so a proportional resize is handled and a non-uniform stretch is not.
Then the seam work. Both trims default to auto, which samples column luminance across the clip, takes the 95th percentile per column, and counts how many columns from that edge are persistently at or below 0.12 luma - the near-black characteristic of a VAE grid boundary rather than of actual footage. It needs at least four such columns before it trims anything, adds two pixels of safety, and never takes more than 128 or a quarter of the width. After trimming, the result is resized back to exactly the panel's right_width × right_height, so the output matches the numbers the layout node promised. That last resize is why the output isn't a byte-exact crop of the decode - it's a crop that's been trimmed and then scaled, a tiny zoom.
The one output is generated_video, an IMAGE batch, which goes wherever you'd normally send frames: a video combine node, an upscale, an interpolator.
The two inputs that matter
decoded_wide_video- theIMAGEbatch straight out of the VAE decode. Not the latents, not the file.layout- theTS_HALF_MASK_LAYOUToutput ofTS Half Mask Video Layoutfrom the same run.left_seam_trim/right_seam_trim- the panel junction and the outer right edge, in pixels.left_seam_trimis the required one, both default toauto, both accept0,8,16,24,32,48,64,96,128.
auto is usually right and you should leave it. Set it to 0 if your footage is genuinely dark near the edges - a night shot or a black costume can read as a latent band, and then the node trims real pixels and zooms to hide the evidence. Set it to 8 or 16 by hand if you can still see the stripe. Squinting at one frame and picking a number beats trusting a brightness test.
Wiring it up
Source frames → TS Half Mask Video Layout → VAE Encode → Set Latent Noise Mask
Decoded wide frames + layout → TS Extract Generated Video → video combine / upscale
The layout is a plain dict held in memory, not a file. Nothing survives a ComfyUI restart, so a reloaded workflow needs the layout node re-run before this one will accept its output. Cheap node, no reason to avoid it.
If you want the side-by-side version, don't route it through here - save the decoded wide video directly.
Install
ComfyUI Manager, search Teskor's Utils. Or by hand:
cd ComfyUI/custom_nodes
git clone https://github.com/teskor-hub/comfyui-teskors-utils
pip install -r comfyui-teskors-utils/requirements.txt
Restart, then look under the Teskor's Utils/Video category. The requirements file is just numpy and opencv-python - those are there for the pack's pose nodes. PyTorch is deliberately left out, which is the correct call: ComfyUI already ships a CUDA build and letting pip decide is how people end up on CPU.
Where it goes wrong
Frame count is not this node's problem and it won't warn you. It crops pixels and returns as many frames as you gave it. If you chunked your sampling, the 4n+1 arithmetic of the Wan VAE - temporal compression is 4x, so lengths want to be 4n+1 - is still yours to get right, and the frames that come back from a bad chunk boundary will look fine here and wrong in the final video.
One more thing: this is a small, new pack, and the usual places turn up essentially no discussion of it. Not a criticism of the code - it's a tidy fix for a genuinely annoying problem - just budget your own debugging time, and keep the layout node visible so you can check its numbers.
Inputs (4)
| Name | Type | Default | Description |
|---|---|---|---|
| decoded_wide_video | IMAGE | — | |
| layout | TS_HALF_MASK_LAYOUT | — | |
| left_seam_trim | COMBO | auto | 10 options: auto, 0, 8, 16, 24, 32, +4 |
| right_seam_trimopt | COMBO | auto | 10 options: auto, 0, 8, 16, 24, 32, +4 |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| generated_video | IMAGE | — |