jz Composite
The paste node that ends the size math
- destination
- source
- mask
- image
Pasting one image onto another sounds trivial until you try it in ComfyUI, and then you discover the stock way involves Get Image Size on two images, a few math nodes computing (a-b)/2, and a fragile crop-and-paste that breaks the moment either image changes size. jz Composite replaces that whole cluster with one node: paste a source onto a destination at a named anchor - center, any corner, any edge midpoint - with an x/y offset and a border margin. You tell it where, it does the arithmetic.
This is a workhorse for outpainting and composition workflows, and the author clearly built it for their own outpainting pipeline (the pack's README groups it under jz/image with the other outpaint helpers like jz Composite Back and jz Seam Repair). Think: paste a generated tile back into the canvas it was outpainted from, composite a subject into a scene, drop a logo into a corner. The node does not scale anything - you resize upstream (jz Resize Long Edge is handy for that) - and it raises if the source doesn't fit, with a message telling you exactly where it tried to put it. A loud error beats a silently cropped paste every time.
The inputs that matter
- destination and source - images in, image out. A 4-channel source blends through its own alpha automatically.
- anchor - nine positions: center, three top, three middle, three bottom. This is the "no math" win; center is the default.
- offset_x / offset_y - nudge the paste by pixels in either direction, negative allowed.
- margin - padding from the borders for corner/edge anchors. Use it to keep a corner paste off the literal edge without hand-computing an offset.
- mask (optional) - blend the source through a mask instead of pasting it as a rectangle. Feed it a trimap from jz Double Threshold and you've got a soft-edged composite; the mask has to match the source's size.
Blending priority, in the author's words from the source: explicit mask > source's own alpha > plain rectangle paste. So a 4-channel source just works, and a mask overrides everything.
How it fits an outpainting workflow
In the classic outpaint loop (see the KB's inpainting doc: generate outside the original canvas, then paste the original back), jz Composite is the paste-back step - you generate the extension, then composite the original image onto it at a known anchor so the interior stays bit-identical while the edges carry the new content. Combined with jz Seam Repair or feathering, that's the whole "outpaint without seams" recipe in a handful of nodes.
Installing it
Same pack, one line:
cd ComfyUI/custom_nodes
git clone https://github.com/j-zhang19/comfyui-jz
Restart ComfyUI (or Manager → search "comfyui-jz"); the node lives under jz/image. No models, no GPU; deps are requests, pillow, numpy.
Common issues
The error you'll actually see is the "does not fit" raise - a source larger than the destination at the chosen anchor just fails, and it fails loudly. Resize the source upstream or pick another anchor. Second: batch size mismatch. The node requires the source batch to be 1 or match the destination batch - a single source broadcasts over a destination batch, but a multi-frame source against a different-sized destination refuses to run. Third: the mask must match the source exactly, or you get a size mismatch error. And remember there's no scaling in here by design - if you expected a fit-to-canvas, you're using the wrong node.
Small personal-pack caveat as usual: solo author, no community footprint, README is the doc. But for a node whose whole reason to exist is removing arithmetic, the behavior is self-evident once you've placed one paste.
Inputs (7)
| Name | Type | Default | Description |
|---|---|---|---|
| destination | IMAGE | — | |
| source | IMAGE | — | |
| anchor | COMBO | center | 9 options: center, top-left, top-center, top-right, middle-left, middle-right, +3 |
| offset_x | INT | 0-16384–16384 | — |
| offset_y | INT | 0-16384–16384 | — |
| margin | INT | 00–16384 | padding from the borders for corner/edge anchors |
| maskopt | MASK | — |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| image | IMAGE | — |