FSL Gemini Generate Image
FSL Gemini Generate Image — the advanced one with real inpainting
- init_image
- images
- mask
- mask_image
- image
- prompt
- model
- width
- height
- temperature
- seed
- seed_mode
- metadata
This is the maintained, advanced Gemini image node in the FSL pack - the one the README points you to if you need more than a text prompt. It's a full-featured wrapper around the Gemini image-generation REST API: inpainting with a real mask, init images, multiple reference images, quality/aspect controls, seed control, and a metadata output you can feed straight into the pack's saver. The lightweight FSLGeminiImageGenerator is the "just make an image" sibling; this is the editor.
How it works
The node builds a generateContent request with parts: your prompt (plus an injected resolution/aspect-ratio line), then optionally the base image, a mask, and extra reference images. The interesting part is how it does inpainting - instead of computing anything locally, it sends the base image and a mask PNG to the model and relies on Gemini's native understanding of masks ("modify ONLY pixels where the mask is white; keep black pixels exactly the same"). That's cloud-native inpainting, and it's worth sitting with: unlike a local inpaint pass that re-composites, the model genuinely leaves masked-out pixels untouched. The KB's inpainting.md notes mask-based editing has been getting squeezed by whole-image edit models - but this approach keeps the "only change what's masked" guarantee those models can't give you.
You have three image sources to juggle:
init_image- the primary base (usually youruse_init_imagetoggle + wire).images- an extra IMAGE input, used as reference images, or as the base whenbase_for_inpaintsays so.mask/mask_image- the edit region.masktakes a proper MASK tensor;mask_imageaccepts an image used as a mask. Both get feathered and strength-scaled in the node before upload.
The base_for_inpaint dropdown (auto / init_image / images) picks which one is "the thing being edited." In auto it uses init_image if present, else images. If you enable the mask but no base resolves, the node raises a clear error: "Inpaint requires a base image."
The inputs that matter
prompt+model- the standard pair.gemini-3-pro-image-previewdefault,gemini-2.5-flash-imageas the cheaper/speed option.quality-Standardasks for 1K-style resolution,Highfor 4K-style, both via prompt injection. Real resolution is capped by the API (~1K native for the flash models), sowidth/heightreally are metadata-only - the tooltip on those fields says exactly that.seed--1randomizes (and the node tells you via theseed_modeoutput); any other value gives reproducible-ish output.enable_safety- defaultfalsemeans the node explicitly setsBLOCK_NONEon all four harm categories. Flip totrueto use Google's default filters.invert_mask,feather_radius,mask_strength- the mask-fiddling controls. White = editable, black = preserved; invert swaps that; feather blurs the boundary; strength scales how strongly the mask "bites."
Outputs
The first output image is what you want. Behind it ride prompt, model, width, height, temperature, seed, seed_mode, and a metadata DICT - the metadata output exists precisely so you can wire it into FSLImageSaverWithMetadata and get a self-documenting PNG.
Install & troubleshooting
Manager → "ComfyUI FSL Nodes", or clone and pip install -r requirements.txt (the README's portable-Windows command is .\python_embeded\python.exe -m pip install --upgrade google-genai requests). No local weights. Key via widget or GEMINI_API_KEY env var.
Two classic failures: a RuntimeError from the node about not finding an inline image usually means a safety block or a dead/deprecated model - the code's own error message includes the finish reason. And long generations can hit HTTP timeouts; the node already uses a 180s request timeout with backoff on 429s, so if you're on slow generations, first try a newer model before blaming the node.
Inputs (22)
| Name | Type | Default | Description |
|---|---|---|---|
| prompt | STRING | — | |
| model | COMBO | gemini-3-pro-image-preview | 2 options: gemini-3-pro-image-preview, gemini-2.5-flash-image |
| width | INT | 102464–2048 | These values are used for metadata only. Actual image size is determined by 'aspect_ratio' and API limits (~1K max). |
| height | INT | 102464–2048 | These values are used for metadata only. Actual image size is determined by 'aspect_ratio' and API limits (~1K max). |
| aspect_ratio | COMBO | 1:1 | Request this aspect ratio via prompt injection. |
| quality | COMBO | Standard | Standard requests 1K-style resolution. High requests 4K-style resolution via prompt injection. |
| temperature | FLOAT | 1.00–2 | — |
| seed | INT | -1-1–2147483647 | — |
| enable_safety | BOOLEAN | false | If true, enables default API safety filters. If false, attempts to disable safety filters (BLOCK_NONE). |
| use_init_image | BOOLEAN | true | — |
| use_images | BOOLEAN | false | — |
| use_mask | BOOLEAN | false | — |
| base_for_inpaint | COMBO | auto | 3 options: auto, init_image, images |
| output_prompt | BOOLEAN | false | — |
| init_imageopt | IMAGE | — | |
| imagesopt | IMAGE | — | |
| maskopt | MASK | — | |
| mask_imageopt | IMAGE | — | |
| invert_maskopt | BOOLEAN | false | — |
| feather_radiusopt | INT | 00–64 | — |
| mask_strengthopt | FLOAT | 1.000–1 | — |
| api_keyopt | STRING | — |
Outputs (9)
| Name | Type | Description |
|---|---|---|
| image | IMAGE | — |
| prompt | STRING | — |
| model | STRING | — |
| width | INT | — |
| height | INT | — |
| temperature | FLOAT | — |
| seed | INT | — |
| seed_mode | STRING | — |
| metadata | DICT | — |