Eric Qwen-Image UltraGen Inpaint (ControlNet)
The Qwen node that actually leaves the rest of your image alone
- pipeline
- controlnet
- image
- mask
- upscale_vae
- image
Qwen-Image-Edit is the best open instruction editor around, and it has one structural flaw: it redraws the whole canvas on every edit. Areas you didn't touch come back close-but-not-identical, and the drift compounds across a chain of edits - which is exactly why the community keeps dragging masks back into the workflow (the KB's inpainting doc puts it bluntly). This node is EricRollei's attempt to fix that the right way, with a ControlNet that understands a real mask channel.
What it does differently
Most Qwen inpaint hacks blank the masked area and let the edit model hallucinate into the hole. The UltraGen Inpaint CN node instead uses InstantX's Qwen-Image-ControlNet-Inpainting model, which was trained for this job. Its pipeline takes 17 channels of conditioning: 16 channels of VAE-encoded masked image plus 1 channel of the mask itself. The model knows there's a mask, so it regenerates only the edit region while the compositor preserves your original pixels everywhere else - bit-identical, not "close."
That's the same InstantX team behind the Qwen ControlNet Union, and their inpainting variant earned real community heat when it landed: the "Qwen Inpainting Controlnet Beats Nano Banana" thread called it a step up from Flux Fill for surgical edits. It's the correct tool for object replacement, background swap, text modification, and outpainting when you care about not degrading the untouched 90% of the frame.
How it runs
It's a multi-stage pipeline, same family as the pack's UltraGen generation node:
- S1 - low-res ControlNet draft from the masked image (defaults follow InstantX's own recipe: 30 steps, CFG 4.0)
- S2A - higher-res ControlNet refine with the mask dilated by
mask_grow_px - S2B - a whole-image harmonize pass with no mask and no ControlNet, so the seam between inpainted and original content blends
- S3 - optional polish upscale, also CN-free
Then a feathered composite (feather controls the edge blur) pastes the result back over the original. For outpainting, outpaint_direction (left/right/top/bottom/all sides) expands the canvas and auto-generates the mask for the new region - outpaint_pixels says how far.
Inputs that actually matter
pipeline- theQWEN_IMAGE_PIPELINEfrom the pack's Qwen-Image Loader (generation pipeline, not the edit one)controlnet- load InstantX/Qwen-Image-ControlNet-Inpainting with the pack's ControlNet Loader. Get this wrong and nothing matches.image+mask- white = regenerate, black = preserve; mask must match image dimensionsprompt- describe the entire desired image, not just the hole. "A green taxi on a road with tall buildings," not "replace the car."auto_stages- smart stage selection that skips S1 for big inputs; leave ons2_harmonize_denoise- the seam-fixer; if you see boundary artifacts this is the dial to nudgedetail_prompt- a richer prompt for the late, mask-free stages; the pack's ControlNet Prompt Rewriter feeds in hereupscale_vae/upscale_vae_mode- optional 2× upscale VAE hookup, same as UltraGen
Output is a single image (IMAGE).
Install & gotchas
Install the pack via ComfyUI Manager (search "Eric Qwen-Edit") or git clone https://github.com/EricRollei/Eric_Qwen_Edit_Experiments.git into custom_nodes/, then restart. The ControlNet-Inpainting weights auto-download from HuggingFace on first run; you also need the full Qwen-Image-2512 model (~54 GB). This pack runs the real diffusers pipeline, so it's heavy - figure 24 GB VRAM for small images, more for big canvases.
Read the experimental label before you get excited. The author's own README admits this node "is not fully working" - it produces visible halos and ghosting from double-sampling at mask boundaries, and the harmonization pass reduces but doesn't eliminate them. The alternative in the same pack, Eric Qwen-Edit Inpaint, currently produces better results despite its whole-image reprocessing. Where people get burned: expecting clean seams out of the box. Treat this as a genuinely experimental node and budget for artifact wrangling.
Inputs (42)
| Name | Type | Default | Description |
|---|---|---|---|
| pipeline | QWEN_IMAGE_PIPELINE | From the Qwen-Image loader or component loader | |
| controlnet | QWEN_IMAGE_CONTROLNET | From the Qwen-Image ControlNet Loader. Load InstantX/Qwen-Image-ControlNet-Inpainting. | |
| image | IMAGE | Source image to inpaint or outpaint. Can be any resolution — will be fitted to generation dimensions for Stage 1. | |
| mask | MASK | Inpaint mask. White (1.0) = areas to regenerate, Black (0.0) = areas to preserve. Must match image dimensions. | |
| prompt | STRING | Describe the ENTIRE desired image, not just the inpainted area. Use descriptive language. Good: 'A green taxi on a road with tall buildings' Bad: 'Replace the car with a taxi' | |
| negative_promptopt | STRING | 低分辨率,低画质,肢体畸形,手指畸形,画面过饱和,蜡像感,人脸无细节,过度光滑,画面具有AI感。构图混乱。文字模糊,扭曲。 | What to avoid in the generation. |
| outpaint_directionopt | COMBO | disabled | Expand the canvas for outpainting. A mask is auto-generated for the expanded region. |
| outpaint_pixelsopt | INT | 2560–2048 | Pixels to expand in the chosen direction. Will be rounded up to nearest multiple of 16. |
| featheropt | INT | 80–50 | Mask-edge feathering radius for final composite. Higher = softer blend at mask edges. 0 = hard edge. |
| mask_grow_pxopt | INT | 240–128 | Dilate the mask by this many pixels for Stage 2. Creates a transition zone around the edit where the model can regenerate for seamless blending. The growth zone uses a gradient falloff in the final composite. 0 = use original mask only. |
| auto_stagesopt | BOOLEAN | true | Smart stage selection based on input image size. When enabled and the input image is large enough (>= 50%% of S2 target MP), Stage 1 is skipped and Stage 2 generates from noise at higher resolution directly. Saves time without sacrificing quality for large inputs. |
| aspect_ratioopt | COMBO | 1:1 Square | Aspect ratio for generation dimensions. Set to 'match_image' to auto-detect from input. |
| match_image_aspectopt | BOOLEAN | true | Override aspect_ratio to match the input image. Recommended for inpainting to avoid distortion. |
| seedopt | INT | 00–18446744073709550000 | Random seed (0 = random) |
| seed_modeopt | COMBO | offset_per_stage | How seeds are chosen for each stage: • same_all_stages — one seed for all • offset_per_stage — S2=seed+1, S3=seed+2 • random_per_stage — independent random per stage |
| max_sequence_lengthopt | INT | 1024128–1024 | Maximum prompt token length. |
| cn_auto_scaleopt | BOOLEAN | true | Auto-calibrate ControlNet strength to match the transformer's hidden-state magnitude. Compensates for finetuned transformers. |
| cn_target_strengthopt | FLOAT | 1.00.1–6 | ControlNet influence (auto-scale mode). 1.0 = standard. Higher = stronger guidance. |
| controlnet_conditioning_scaleopt | FLOAT | 1.00–50 | Manual ControlNet scale (when auto-scale is OFF). For custom transformers, 10–30 may be needed. |
| control_guidance_startopt | FLOAT | 0.000–1 | When CN guidance begins (fraction of steps). |
| control_guidance_endopt | FLOAT | 1.000–1 | When CN guidance ends (fraction of steps). |
| s2_cn_scaleopt | FLOAT | 1.00–50 | ControlNet strength on Stage 2. When auto_scale is ON, this is relative to S1. 1.0 = same as S1 (recommended for inpainting). 0.0 = disable CN for S2. |
| s2_cn_startopt | FLOAT | 0.000–1 | When CN guidance begins in Stage 2. |
| s2_cn_endopt | FLOAT | 1.000–1 | When CN guidance ends in Stage 2. |
| s1_mpopt | FLOAT | 0.50.3–2 | Stage 1 resolution in megapixels. |
| s1_stepsopt | INT | 301–200 | Stage 1 inference steps. InstantX recommends 30 for inpainting. |
| s1_cfgopt | FLOAT | 4.01–20 | Stage 1 true CFG scale. InstantX recommends 4.0 for inpainting. |
| upscale_to_stage2opt | FLOAT | 4.00–10 | Upscale factor (area) from S1 to S2. 0 = skip S2 & S3 (output S1 only). |
| s2_stepsopt | INT | 261–200 | Stage 2 inference steps. |
| s2_cfgopt | FLOAT | 4.01–20 | Stage 2 true CFG scale. |
| s2_denoiseopt | FLOAT | 0.850.1–1 | Stage 2 denoise strength. |
| s2_sigma_scheduleopt | COMBO | linear | Sigma schedule for Stage 2. |
| s2_harmonize_denoiseopt | FLOAT | 0.350–0.8 | S2 Phase B: whole-image harmonization pass. Runs after the CN inpaint pass (Phase A) at S2 resolution with NO mask and NO ControlNet, so the model can harmonize boundaries between inpainted and original content. 0.0 = disabled (skip Phase B). |
| s2_harmonize_stepsopt | INT | 101–60 | Number of inference steps for S2 harmonization. Lower = faster, higher = smoother blending. |
| upscale_to_stage3opt | FLOAT | 0.00–8 | Upscale factor (area) from S2 to S3. 0 = disabled (2-stage output). |
| s3_stepsopt | INT | 181–200 | Stage 3 inference steps. |
| s3_cfgopt | FLOAT | 2.01–20 | Stage 3 true CFG scale. |
| s3_denoiseopt | FLOAT | 0.450.1–1 | Stage 3 denoise strength. |
| s3_sigma_scheduleopt | COMBO | karras | Sigma schedule for Stage 3. |
| upscale_vaeopt | UPSCALE_VAE | Optional: Wan2.1 2× upscale VAE. Load with Eric Qwen Upscale VAE Loader. | |
| upscale_vae_modeopt | COMBO | disabled | How the upscale VAE is used: • disabled — upscale VAE ignored • inter_stage — decode S2→2×→re-encode for S3 • final_decode — 2× upscale on final output • both — inter-stage + final decode |
| detail_promptopt | STRING | Optional detailed prompt for late stages (S2B harmonization and S3 polish). These stages resample the ENTIRE image without a mask, so a richer, more descriptive prompt produces better results. Wire the ControlNet Prompt Rewriter output here for best quality. If empty, the main prompt is used for all stages. |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| image | IMAGE | — |