🖼️ AITEC LLM Vision
Feed up to four images to a local vision LLM and get a description back
- model
- image1
- image2
- image3
- image4
- text
- used_model
- status
The payoff node of the pack's local-LLM half. AITEC LLM Vision takes up to four IMAGE inputs, sends them to the model loaded by AITEC LLM Vision Loader, and returns a text description - captioning, analysis, even "write a prompt for this image" style tasks, all on a local model with no API key and no per-image bill.
Mechanically it's clean: each connected image is converted to a base64 PNG and embedded inline in the user message as an image_url content block, alongside your prompt text. One model, up to four images, one reply. The default prompt is "Describe the image(s) in detail," and the system_prompt default is the stock "You are a helpful assistant."
The required inputs mirror AITEC LLM Chat - model, system_prompt, prompt, temperature (0.7), top_p (0.95), max_tokens (4096), and the three reasoning-toilet toggles: remove_think (strip <think> blocks, on), remove_chatml (keep only the first assistant block, on), and suppress_thinking (add a "don't think" instruction to the system prompt, off). If you've used the Chat node, you know these already.
Then the differences, and they're deliberate:
image1throughimage4are optional inputs - the node works fine with just image1, so the "up to 4" is a ceiling, not a requirement.unload_after_rundefaults to ON here, where the Chat node defaults to off. That's the author making the VRAM call for you: vision models are heavy, so it frees the model after each run by default. Flip it off if you're running many vision calls in a row and want to skip the reload dance.seed- changing it forces re-execution (ComfyUI's cache would otherwise skip the node when nothing changed). The tooltip's honest about the caveat: same seed doesn't guarantee identical output, because llama.cpp sampling isn't that deterministic.
Outputs are three strings, same as Chat: text (the answer), used_model (which file answered), and status - where the finish_reason=length and "context may be exhausted" warnings mean raise n_ctx on the loader, not rewrite your prompt.
The wiring:
[AITEC LLM Vision Loader] → model → [AITEC LLM Vision] → text
↑ (mmproj matched to your model)
The one prerequisite is the one that bites everyone: the vision loader must be able to construct a chat handler, which requires a vision-capable llama-cpp-python - i.e. the JamePeng fork, not the stock wheel. If the loader errors on chat handlers, no amount of tweaking here helps; fix the environment first.
Install is the pack-wide path (clone, pip install -r requirements.txt, restart) plus that manual llama-cpp-python install. And the README's VRAM warning applies double here: base model + mmproj + generation models can exceed a consumer card. That's why unload_after_run defaults on, and why the pack suggests running vision in its own pass. For a no-key, on-prem image captioner inside ComfyUI, this is a genuinely useful node - just respect the memory budget.
Inputs (15)
| Name | Type | Default | Description |
|---|---|---|---|
| model | LLM_MODEL | — | |
| system_prompt | STRING | You are a helpful assistant. | — |
| prompt | STRING | Describe the image(s) in detail. | — |
| temperature | FLOAT | 0.700–2 | — |
| top_p | FLOAT | 0.950–1 | — |
| max_tokens | INT | 409664–32768 | Thinking model with 4096 or more is recommended |
| remove_think | BOOLEAN | true | Remove the <think>...</think> block (Qwen3, Gemma4, etc.) |
| remove_chatml | BOOLEAN | true | Remove repetitions of <|im_start|>assistant~<|im_end|> and return only the first response (Gemma4, etc.) |
| suppress_thinking | BOOLEAN | false | When enabled, adds an inference suppression instruction to the system prompt (for Thinking models such as Qwen3 and Gemma4) |
| unload_after_run | BOOLEAN | true | Unload the model after execution to free up VRAM. You will need to reload it when you run it again. |
| seed | INT | 00–18446744073709550000 | Changing the value each time the code runs bypasses the cache and forces a re-execution. |
| image1opt | IMAGE | — | |
| image2opt | IMAGE | — | |
| image3opt | IMAGE | — | |
| image4opt | IMAGE | — |
Outputs (3)
| Name | Type | Description |
|---|---|---|
| text | STRING | — |
| used_model | STRING | — |
| status | STRING | — |