Image Concatenate (UTK)
Side-by-side (or top-to-bottom) image stitching without the size mismatch headache
- image1
- image2
- IMAGE
The core ComfyUI Image Concatenate node is famously finicky - it wants the two images to already match on the stitching axis, and if they don't, you're resizing by hand. Image Concatenate (UTK) from ComfyUI-UniversalToolkit removes that chore: it resizes the images to a common dimension for you, so two mismatched generations just go together. For before/after shots, batch comparison strips, or assembling reference sheets, this is the version I'd put in the graph.
How it works
You feed image1 and image2. If match_image_size is on (it is, by default), the node resizes both so they line up on the join - for a horizontal right stitch, it matches heights; for down, it matches widths - using bilinear. Then it concatenates them onto a canvas, adding a gap in pixels if you set one, and capping the result at max_size (default 4096) by downscaling if the combined canvas would blow past it.
The smart touch is direction = "auto". Rather than forcing you to guess whether your images are taller or wider, it looks at the two dimensions and picks the axis that makes the canvas most square-ish. Two 1024×1024 squares go side by side; two tall portrait crops stack vertically. You can override with explicit right/down/left/up if auto doesn't match your intent. background_color (black/white/gray/transparent) fills the gap and any leftover canvas.
Inputs and outputs that matter
image1/image2- the two frames. Both required.direction-auto(default) or right/down/left/up.match_image_size- resize to a common join size. Leave on.gap(0–512) andmax_size(64–8192) - spacing and output cap.
Single output: IMAGE, the stitched frame. It's a normal (non-output) node, so route it into a preview or save node yourself.
Install and gotchas
Install via ComfyUI Manager (search "ComfyUI-UniversalToolkit") or:
cd ComfyUI/custom_nodes
git clone https://github.com/whmc76/ComfyUI-UniversalToolkit
pip install -r requirements.txt
Restart ComfyUI. No models, no keys - Pillow/numpy/torch.
The honest caveat: "match sizes" here means stretch to match, not aspect-crop. If you stitch a 4:3 against a 16:9 horizontally, the 4:3 gets stretched to the 16:9's height, which can visibly fatten faces. For outputs of the same model at the same resolution - the normal case - you'll never notice. For mismatched material, normalize aspect ratios first. And one more: the output dims are capped by max_size, so if your two images are already 4096 each, the combined 8192 canvas gets scaled down to fit. That's a feature for sanity, but it means the stitched result won't be true 1:1 pixels for very large inputs.
Inputs (7)
| Name | Type | Default | Description |
|---|---|---|---|
| image1 | IMAGE | — | |
| image2 | IMAGE | — | |
| direction | COMBO | auto | 5 options: right, down, left, up, auto |
| match_image_size | BOOLEAN | true | — |
| max_size | INT | 409664–8192 | — |
| gap | INT | 00–512 | — |
| background_color | COMBO | black | 4 options: black, white, gray, transparent |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| IMAGE | IMAGE | — |