Nano Banana - Painted Edit
Paint a region, type a sentence, get exactly that changed
- target_image
- mask
- identity_1
- identity_2
- identity_3
- identity_4
- identity_5
- identity_6
- network
- image
- status
- mask
- debug_sheet
NanoBananaPaintedEdit is the odd one out in this pack, and it might be the most useful. The swap nodes are all about faces; this one is a general paint-and-edit node. You paint a mask over any region - an arm, a t-shirt, a wall - type what you want there, and Nano Banana edits exactly that region while the rest of the frame stays untouched.
It's the pack's answer to the thing the KB's inpainting essay keeps circling: instruction-edit models are great at "change this," but they drift the whole image while doing it. This node pins the edit to your mask, crops tight, and composites back, so unmasked pixels come back bit-identical. That's the whole remaining case for masked editing in 2026, and this node does it properly.
The two modes
edit_mode=blend(default) - tuned for edits that should look native: face regions, skin, anything you want to blend seamlessly. LAB color match and sharpness match on, Laplacian composite.edit_mode=additive- for tattoos, logos, stickers, objects you want to stand out. It force-disables LAB color match, sharpness match, and Laplacian - all of which would desaturate and flatten your crisp new tattoo.
This is the single most important decision on the node, and the tooltip spells it out. Add a rose tattoo in blend mode and it comes back looking waterlogged; put a face edit in additive mode and it glows.
Inputs that matter
api_key,model,target_image,mask- the MASK comes from LoadImagePaint (its whole reason to exist). Paint, wire, go.edit_prompt- a sentence. Default is "Add a small rose tattoo to the painted region." Plain language works; this is where the instruction-editing shine is.thinking_level(NONE default) - Nano Banana Pro's reasoning. NONE is the fast default; HIGH is for edits that need the model to think before drawing.crop_tightness_pct(default 100) - padding around the mask before sending. 0 = mask bbox only, tightest, and - per the tooltip - best for evading safety filters on revealing content. 100% = bbox-sized padding, more scene context.obscure_outside_mask(off) - the pack's safety-dodge: blur / mosaic / neutral-solid the non-painted area of the crop before sending, so the classifier sees skin tone and lighting but no anatomical shapes. If your edit is near revealing content and trips IMAGE_SAFETY, this plus a tight crop is the fix.obscure_blur_px(40),composite_dilate_px(0),composite_feather_px(24),image_size, the integrate stack (color_match,grain_match,sharpness_match,composite_method,lab_strength,grain_strength).identity_1..identity_6- optional. Wire refs and you can do identity-aware edits, not just object insertion.
Outputs
Standard four: image, status, mask, debug_sheet - and the debug sheet is genuinely useful here, because you can see exactly what crop you sent and whether the obscuring did its job.
Install
Same pack, one install covers it:
cd ComfyUI/custom_nodes
git clone https://github.com/IxMxAMAR/ComfyUI-NanoBanana-FaceSwap
cd ComfyUI-NanoBanana-FaceSwap
pip install -r requirements.txt
Restart ComfyUI (or ComfyUI Manager → "NanoBanana FaceSwap"). Needs a Gemini API key; no heavy local downloads.
Troubleshooting
- Tattoo looks washed out - you're in
blendmode. Flipedit_mode=additive. - Face region edit looks fake - you're in
additive. Flip toblend. - REFUSED near revealing content - set
obscure_outside_masktoblurormosaicand dropcrop_tightness_pcttoward 0. That combo is the pack's tested anti-IMAGE_SAFETY configuration. - Edit leaks outside the mask - raise
composite_feather_pxisn't the fix; that controls seam softness. Checkcrop_tightness_pct- a huge crop gives Gemini room to wander. Tighter crop, tighter behavior.
Inputs (31)
| Name | Type | Default | Description |
|---|---|---|---|
| api_key | STRING | — | |
| model | COMBO | gemini-3.1-flash-image-preview | 3 options: gemini-3.1-flash-image-preview, gemini-3-pro-image-preview, gemini-2.5-flash-image |
| target_image | IMAGE | — | |
| mask | MASK | — | |
| edit_prompt | STRING | Add a small rose tattoo to the painted region. | — |
| seed | INT | 00–2147483647 | — |
| thinking_level | COMBO | NONE | 4 options: NONE, LOW, MEDIUM, HIGH |
| edit_mode | COMBO | blend | blend = tuned for face-swap / refining a region to look native (LAB+sharpness on, Laplacian composite). additive = tuned for tattoos / logos / objects you WANT to stand out crisply (LAB off, sharpness off, feather composite, grain still on). |
| crop_tightness_pct | INT | 1000–200 | Padding around the painted mask bbox before cropping. 0 = mask bbox only (tightest, best for evading safety filters on revealing content). 100% = bbox-sized padding per side (more scene context for the model). |
| obscure_outside_mask | COMBO | off | Fill the crop's non-painted area before sending. 'blur' = heavy Gaussian (model gets skin tone + lighting but no NSFW shapes). 'mosaic' = pixelate. 'neutral' = solid skin tone. Use when editing near revealing content that trips IMAGE_SAFETY. |
| obscure_blur_px | INT | 404–200 | Blur radius (or mosaic block size) for obscure_outside_mask. Bigger = more hidden. |
| composite_dilate_px | INT | 00–40 | Expand the painted mask outward before feather. 0 = composite exactly inside the painted region. |
| composite_feather_px | INT | 240–128 | — |
| image_size | COMBO | 2K | 3 options: 1K, 2K, 4K |
| color_match | BOOLEAN | true | — |
| grain_match | BOOLEAN | true | — |
| sharpness_match | BOOLEAN | true | — |
| composite_method | COMBO | laplacian | 2 options: laplacian, feather |
| lab_strength | FLOAT | 0.600–1 | — |
| grain_strength | FLOAT | 1.000–2 | — |
| identity_1opt | IMAGE | — | |
| identity_2opt | IMAGE | — | |
| identity_3opt | IMAGE | — | |
| identity_4opt | IMAGE | — | |
| identity_5opt | IMAGE | — | |
| identity_6opt | IMAGE | — | |
| dry_runopt | BOOLEAN | false | — |
| timeout_msopt | INT | 1800005000–600000 | — |
| ref_cap_pxopt | INT | 10240–4096 | — |
| auto_relax_on_refusedopt | BOOLEAN | false | — |
| networkopt | NB_NETWORK | Optional. Wire a NanoBanana - Network Route node here to route this swap's API call through that proxy (e.g. US egress). |
Outputs (4)
| Name | Type | Description |
|---|---|---|
| image | IMAGE | — |
| status | STRING | — |
| mask | MASK | — |
| debug_sheet | IMAGE | — |