AP Image Mask Inpaint Crop
Crop to the mask, inpaint, stitch back — the batch-safe crop that remembers where everything goes
- images
- masks
- cropped_images
- cropped_masks
- stitch_data
Inpainting a small region on a big frame is wasteful and often worse: the model spends its attention budget on a whole 1024×1024 image to fix a face-sized patch, and the result can be a weirdly-recomposed scene. The standard professional move is crop-and-stitch - cut out just the masked region, inpaint the crop, paste it back. That's exactly what this node and its partner AP_ImageMaskStitch automate, and the part people underrate is that the crop has to remember where it came from so the stitch can put it back exactly.
That memory is the pack's AP_STITCH metadata type. AP Image Mask Inpaint Crop takes your image batch and mask batch, crops each to the mask's bounding box (plus padding), and emits the cropped image, the cropped mask, and a stitch_data object carrying everything needed to place the result back - offset, size, and per-frame batch alignment. The README calls it a "reliable crop→inpaint→stitch roundtrip," and the batch support is the part that makes it production-usable: it handles a whole sequence of frames, not a single image.
The inputs that matter
imagesandmasks- the frame batch and its per-frame masks. The mask defines the region to crop around.padding(default 32) - how much context to add around the mask's bounding box. This is your inpaint-quality dial: too little and the model has no context to blend edges; too much and you're back to inpainting half the frame. Start at 32 and raise it if you see seam artifacts.mask_threshold(default 0.001) - pixels above this mask value count as "masked" when computing the bounding box. Near-zero by default so soft mask edges still get included.crop_universal_box- when true, all frames in the batch share one bounding box (the union) so the crop size is consistent across frames. For video inpainting this is usually what you want: a moving subject with a drifting mask would otherwise give you a jittering crop box every frame.out_width/out_height(default 0 = keep crop size) - force the crop to a target resolution, withupscale_onlycontrolling whether it ever downscales. Theinterpolationchoice applies here.
Outputs
cropped_images and cropped_masks go to your inpaint model (or a VAE encode → sampler → VAE decode chain, or a dedicated inpaint checkpoint). stitch_data (AP_STITCH) is the return-ticket: it goes straight to AP_ImageMaskStitch alongside the original frames and the inpainted crops, and that node does the rest. Do not lose this wire - without it, the stitch node can't know where anything goes.
Installing it
Pack-wide install: ComfyUI Manager (search "AP_OpticalFlow"), or
cd ComfyUI/custom_nodes
git clone https://github.com/adampolczynski/ComfyUI_AP_OpticalFlow
python -m pip install -r custom_nodes/ComfyUI_AP_OpticalFlow/requirements.txt
Restart. Dependency is torchvision>=0.15.
Why this pattern is worth it
Two reasons, one practical and one about video. Practically, inpainting a crop is dramatically faster and gives the model a tighter task - fix this patch, don't touch anything else - which is the mask-based inpainting that's still the right tool when you want the rest of the image left alone (see the KB's inpainting essay on why instruction-editing models drift where masked inpainting doesn't). For video, the universal-box option plus batch support is what lets you run the same crop/inpaint/stitch chain across an entire sequence frame-by-frame without the crop box jittering, which is a precondition for temporally-stable results. The temporal side is where the pack's other half - loops, flow warp, temporal blend - can slot in around it.
The natural pairing
AP Image Mask Inpaint Crop → inpaint (however you like: dedicated inpaint checkpoint, or encode→sample→decode) → AP Image Mask Stitch. That's the whole pipeline, and the README's recommended feather advice for the stitch is to start low and only raise it when a seam is visible. If your inpaint output comes back misaligned or blurred, the usual suspects are insufficient padding and a feather that's too aggressive - dial those before touching your inpaint model.
Inputs (9)
| Name | Type | Default | Description |
|---|---|---|---|
| images | IMAGE | — | |
| masks | MASK | — | |
| padding | INT | 320–2048 | — |
| crop_universal_box | BOOLEAN | false | — |
| mask_threshold | FLOAT | 0.0010–1 | — |
| out_width | INT | 00–8192 | — |
| out_height | INT | 00–8192 | — |
| upscale_only | BOOLEAN | false | — |
| interpolation | COMBO | bilinear | 3 options: bilinear, bicubic, nearest |
Outputs (3)
| Name | Type | Description |
|---|---|---|
| cropped_images | IMAGE | — |
| cropped_masks | MASK | — |
| stitch_data | AP_STITCH | — |