Nodes/pfaeff-comfyui/ImagePadForBetterOutpaint
ComfyUI Node

ImagePadForBetterOutpaint

Core's outpainting pad, but it pre-fills the void

By Pfaeff·Created 3 years ago·Updated 2 years ago· 22
ImagePadForBetterOutpaint
  • image
  • IMAGE
  • MASK
  • IMAGE
left256
top256
right256
bottom256
inpaint_radius5

"Better than what?" is the fair first question, because ComfyUI already ships a Pad Image for Outpainting node in core. The difference is what happens inside the empty padding. Core's node leaves the new area pure black and hands you a mask; this one runs OpenCV's inpainting (Navier-Stokes mode) over the padding first, smearing the edge colors of your image outward into the new space. The diffusion model then starts from content that plausibly belongs there instead of a black void - and that starting point is the difference between an outpaint that extends naturally and one that has to invent its entire edge from nothing.

It's one leg of this pack's outpainting mini-stack: pad here, load a diffusers inpainting pipeline, inpaint the masked area, then crop or composite back to size.

How it works

Four steps, all grounded in the source:

  1. cv2.copyMakeBorder pads the image with constant black on each side.
  2. A mask is built where the padding is white (255) and the original image is black - the same polarity core's outpainting node uses, so it drops into standard inpaint workflows without surprises.
  3. cv2.inpaint (Navier-Stokes) smears the image's edge colors into the padding, using inpaint_radius as the reach.
  4. You get three outputs: the padded, pre-smeared image; the mask; and the padded image with the padding blacked out again (the original masked back down to its own rectangle).

That third output is handy when you want to feed the untouched original into an inpaint conditioning node while the smeared version informs the model.

The inputs that matter

  • left / top / right / bottom (INT, default 256 each) - padding in pixels per side. They step in multiples of 8, which keeps the padded dimensions friendly for latent sizes. 256 is a lot of extension; try 128 or 64 for a modest grow.
  • inpaint_radius (INT, default 5, min 3) - how far the edge smear reaches into the padding. Bigger = smoother fill that bleeds further into the original edge; smaller = crisper but with more void left over. 5 is a reasonable start.

Outputs: IMAGE (padded + smeared), MASK (white = padding), IMAGE (padded image, padding blacked out).

Using it, and one honest caveat

Wire output 1 and output 2 into this pack's Inpainting node with a prompt describing what's beyond the edge ("the street continues", "more sky", whatever belongs there). A hard, feathered mask would be nicer, but there's no feathering here - the mask edge is sharp, so expect a visible seam unless your inpaint pass blends it, and consider compositing the result back over the original with ImageCompositeMasked afterward.

One bit of context so you don't waste an afternoon: outpainting is the part of this space that 2026's instruction-editing models took cleanly. On Flux or Qwen, the current trick is to pad with a solid color and just tell the model to replace it. This node's mask-and-smear route is the honest way to do it on the SDXL/diffusers stack this pack targets - you get to keep the original pixels and mask exactly what regenerates, which is the one thing masked methods still uniquely guarantee.

How to install it

Shared with the pack - a work in progress whose README says "not tested, yet" (author Pfaeff, a long-time SD community handle from the diffusers era). Via ComfyUI Manager if it's in the registry, or manually:

cd ComfyUI/custom_nodes
git clone https://github.com/Pfaeff/pfaeff-comfyui

then restart. Dependencies (opencv-python-headless, diffusers) install automatically on first load.

Common issues & troubleshooting

The padding is still black. The cv2 inpaint only reaches inpaint_radius pixels into the padding. With a big pad and a small radius, most of it stays void - bump the radius, or accept that the inpaint pass handles it (that's what it's for).

A visible seam where the padding meets the image. No feathering here. Let the inpaint pass blend it, or composite the result back over the original with ImageCompositeMasked.

Dimensions not multiples of 8. The step-locked inputs make this hard to hit by accident, but if you're pairing with a latent-size-sensitive model, check your padded width/height before encoding.

CategoryPfaeff/outpainting

Inputs (6)

NameTypeDefaultDescription
imageIMAGE
leftINT2560–16384
topINT2560–16384
rightINT2560–16384
bottomINT2560–16384
inpaint_radiusINT53–128

Outputs (3)

NameTypeDescription
IMAGEIMAGE
MASKMASK
IMAGEIMAGE