Upscale Latent From Image
Upscale Latent From Image
- image
- latent
Here's the version of this node most people meet it through: you generate, then you want a hires-fix-style second pass, so you decode to pixels, upscale the image, and re-encode it before sampling again. That encode/decode round trip is lossy - every VAE cycle grinds a little detail out of the image, and chained passes accumulate the damage. Upscale Latent From Image refuses to do the round trip. You feed it the image that came straight out of a VAEDecode, and it finds the latent that produced that image and upscales that instead, in latent space, using Comfy's own LatentUpscaleBy under the hood.
How it works
The trick is provenance tracking. At execution time the node reads your workflow graph, walks back from the image input, and looks for an unmodified VAEDecode that could have produced it. When it finds one - through only transparent pass-through nodes - it grabs the original latent and expands into a native LatentUpscaleBy call with your upscale_method and scale_factor. The node isn't reimplementing upscaling; it's a smarter wire that hands Comfy the source latent instead of a re-encoded approximation.
That's why the input tooltip is so strict. The image must come directly from a VAEDecode, with only pass-through nodes in between. Pixel edits, image upscalers, crops, detailers, loaders, and even previews break the chain, and when it can't prove where the image came from it raises a clear error rather than silently re-encoding. That's the safe behavior and it's the right call - guessing at a latent from a finished tensor would be nonsense.
The inputs
image- wire this straight from aVAEDecode. Nothing else.upscale_method- the interpolation passed to Comfy's latent upscale:nearest-exact,bilinear,area,bicubic, orbislerp. For latents,nearest-exactis the common default and usually fine;areais the one to reach for when you're downscaling.scale_factor- the multiplier for latent width and height (default 1.5, range up to 8x).
The single output, latent, plugs into the samples input of a KSampler for your second pass.
When to use it (and when not to)
It shines in a clean two-pass graph: KSampler → VAEDecode → [this node] → KSampler (partial denoise). You get the true source latent, upscaled, with none of the encode noise added. It pairs with the pack's Simple VAE Encode, which does the mirror-image trick on the encode side - reuse the original latent when the graph proves it's safe.
Don't reach for it the moment your image has been touched by anything that isn't a VAE decode. The whole design assumes provenance; if you've cropped, detailed, or filtered the image in between, the node will correctly refuse, and you'll want a normal VAEEncode (or the pack's VAE Encode (Options)) instead. That's not a bug - it's the node refusing to pretend a lossy round trip never happened.
Installing it
It ships in the SimpleSyrup pack. ComfyUI Manager: search SimpleSyrup, install, restart. Or:
cd ComfyUI/custom_nodes
git clone https://github.com/Artificial-Sweetener/SimpleSyrup.git
cd SimpleSyrup
../venv/bin/python -m pip install -r requirements.txt
SimpleSyrup needs a current ComfyUI (it uses the v3 extension API), and there's no extra model download for this node - it leans entirely on Comfy's built-in latent upscaler.
Inputs (3)
| Name | Type | Default | Description |
|---|---|---|---|
| image | IMAGE | Connect an image that comes directly from VAE Decode, with only transparent pass-through nodes between them. Pixel edits, image upscalers, crops, detailers, loaders, and previews break latent provenance. | |
| upscale_method | COMBO | Interpolation method passed to Comfy's Upscale Latent By behavior. | |
| scale_factor | FLOAT | 1.500.01–8 | Multiplier for the latent width and height passed to Comfy's Upscale Latent By behavior. |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| latent | LATENT | Upscaled latent produced from the source latent behind the decoded image. |