Video Stabilizer Classic
Stabilize shaky AI video with zero models and zero VRAM
- frames
- padding_color
- Stabilized Frames
- Padding Mask
- Motion Meta
You know the problem: the video came out of your generator with a wandering, handheld-ish camera, and you wanted a locked-off shot. Or your source clip was shot on a phone and it's all micro-jitter. This node removes that shake, it runs entirely on your CPU, and it doesn't download a single model. That last bit is rarer in the ComfyUI video world than it should be.
Video Stabilizer Classic is the lightweight member of the ComfyUI-Video-Stabilizer pack, from nomadoor - the same person behind the popular "Loop Anything with Wan2.1 VACE" workflows. His framing is worth knowing: the parameters are named after what DaVinci Resolve calls them, so if you've edited video before, most of this reads as familiar.
How it works
Classic uses sparse feature tracking, the old-school video-editor approach. OpenCV's goodFeaturesToTrack finds up to a few hundred corner points in each frame, Lucas-Kanade optical flow tracks them to the next frame, and the node fits a geometric transform to that point motion. It then smooths the camera path over time and warps every frame to cancel out the high-frequency jitter while leaving slow, deliberate moves alone.
That's why it's cheap: a couple hundred points per frame is nothing next to the per-pixel work of dense flow. The tradeoff is that it needs texture to track - a blank wall or a pan across a gradient will give it nothing to hold onto, and that's exactly the scenario where you'd reach for the pack's other node, Video Stabilizer Flow. The README is honest about it: Flow is the safer default unless speed actually matters. Classic is what you use on long clips, high frame counts, or a machine that's already sweating.
The inputs that matter
frames- a video or a batch of images. Feed it whatever your loader gives you.strength- how much of the motion to remove.0keeps the original motion,1removes it based on the smoothing. Default0.7is a reasonable middle.smooth- how strongly to smooth the motion path over time. Higher values leave only slow sweeping motion.framing_mode- what to do with the borders stabilization exposes:crop(zoom in to hide them, narrowing the FOV),crop_and_pad(limit the zoom, fill the gaps), orexpand(grow the canvas instead of cropping).camera_lock- when on, pushes hard toward a tripod-locked result and takes over fromstrength/smooth.
The rest you can mostly leave alone. frame_rate scales the smoothing window - this matters more than it looks, see below. keep_fov only does anything in crop mode (1.0 = no zoom, 0.0 = maximum zoom). transform_mode chooses the geometric model - translation, similarity (default), or perspective - and padding_color is the hex fill for padded areas.
Outputs
Three sockets, all of them useful:
- Stabilized Frames (IMAGE) - wire this to a
VHS_VideoCombineor a save node and you're done. - Padding Mask (MASK) - the exposed edges as a mask. This is the pack's killer feature: feed it to a VACE outpainting node and a video model can fill the borders, so you stabilize without sacrificing FOV. The repo ships Wan2.1 and Wan2.2 VACE example workflows showing exactly that.
- Motion Meta (JSON) - the exact camera motion that was removed. Keep it; it's how you put the original camera work back later via Video Stabilizer Motion Apply.
Install
Install via ComfyUI Manager - search "ComfyUI-Video-Stabilizer" - or:
cd ComfyUI/custom_nodes
git clone https://github.com/nomadoor/ComfyUI-Video-Stabilizer
Then restart ComfyUI. No model files, no checkpoints, nothing to hunt down on Civitai. The only real dependency is opencv-python-headless, which installs automatically. One gotcha: this pack targets ComfyUI's newer V3 node API, so if the node doesn't show up, update ComfyUI itself first.
Common issues
- High-fps footage barely stabilizes. This bit people early on - a 120 fps clip looked untouched because the smoothing window was frame-count-based. The
frame_rateparameter was added to fix exactly that, so set it to your actual fps rather than the 16 default. expand+camera_lockcan explode your canvas. Removing nearly all motion means the output needs to absorb the whole shake as padding, so the output resolution can grow a lot. Fine for a few frames, surprising on a long clip.cropdiscards pixels permanently. If you crop away the exposed edges, they're gone - restoration later can't bring them back. If you think you'll outpaint or restore, usecrop_and_padand keep the mask.
Inputs (9)
| Name | Type | Default | Description |
|---|---|---|---|
| frames | IMAGE | — | |
| frame_rate | FLOAT | 16.0 | Frame rate in frames per second used to scale smoothing window. |
| framing_mode | COMBO | crop_and_pad | Choose how to handle borders produced by stabilization. |
| transform_mode | COMBO | similarity | Select the geometric model used to estimate camera motion. |
| camera_lock | BOOLEAN | false | Treat the shot as tripod-like by aggressively damping motion. |
| strength | FLOAT | 0.700–1 | Removal gain (0 keeps original motion, 1 removes it based on smoothing). |
| smooth | FLOAT | 0.500–1 | Temporal smoothing amount applied to the estimated motion path. |
| keep_fov | FLOAT | 0.600–1 | [Crop only] How much of the original FOV to preserve (1.0 = no zoom, 0.0 = maximum zoom). Ignored when framing_mode is crop_and_pad or expand. |
| padding_color | COLOR | #7F7F7F | HEX padding color applied in crop_and_pad / expand (e.g. #404040). |
Outputs (3)
| Name | Type | Description |
|---|---|---|
| Stabilized Frames | IMAGE | — |
| Padding Mask | MASK | — |
| Motion Meta | JSON | — |