Prompt Builder (kppb)
Stop hand-writing FLUX Klein prompts — this node does the boring 90%
- positive_prompt
- negative_prompt
- prompt_json
The prompt box is the whole game with FLUX.2 Klein. Klein reads your text through an actual LLM encoder (Qwen-based), not CLIP, which means it wants natural-language instructions with real camera vocabulary - and it punishes the old habits like (weighted:1.3) tags and BREAK, which it reads as literal punctuation. If you've been typing "50mm lens, golden hour, cinematic" by hand and getting fifty-percent adherence, this is the node that takes over that job. Prompt Builder (kppb) is the flagship of the artokun/ComfyUI-Photoreal-Prompt-Builder pack: over twenty inputs, from a subject line to eleven dropdowns, and it composes a single flowing paragraph tuned for Klein 9B (or the 4B). No prompt engineering required, which is the entire pitch.
How it works
It's pure string assembly - no model loads, no API calls. You give it a subject and work through dropdowns for pose, scene_type, lighting_setup, photo_style, shot_type, camera_angle, lens, depth_of_field, color_grading, hairstyle, and hair_color. It then builds the prompt sentence by sentence: an opener that marries the photo style to the subject, then pose, hair, outfit, scene, lighting, the technical camera block, mood, and color grade.
Two design choices matter. First, any dropdown set to random resolves to a different concrete option each run, which makes it a one-node randomizer for XY-plot-style exploration. Second, the lighting presets ship as rich prose expansions - "ring light" becomes "even ring light illumination with circular catchlights in the eyes and minimal shadows" - and the pack's own advice is that lighting is the single highest-impact setting for Klein, which lines up with everything the photorealism crowd has been saying for years about light direction being the first thing that outs a fake photo. Only the fields you actually override get included, so a mostly-default config stays short and doesn't bloat the prompt with filler.
Inputs and outputs that matter
For a beginner the ones worth touching:
subject- your character description, e.g. "blonde woman in her mid 20s". Keep it short; identity comes from a reference image, not from here.lighting_setup- the highest-leverage dropdown. Ring light, softbox, golden hour, neon, etc.preserve_identity(default on) - appends an identity-lock phrase ("maintain exact likeness, identical facial structure…") for character-reference workflows.
Optional outfit and edit_instructions are where the pack's other nodes plug in - Outfit Composer and Image Edit Composer feed them directly. extra_details appends whatever you want, and negative_prompt merges with the auto-injected quality negatives.
The three outputs are what matter:
positive_prompt→ wire into a CLIP Text Encode node (or the VLM Refiner).negative_prompt→ the negative conditioning. One honest caveat: on the 4-step distilled Klein checkpoints running at CFG 1, a negative prompt does basically nothing - the node still emits one, but on distilled builds it's belt-and-braces.prompt_json→ a JSON dump of every setting, which the VLM Refiner consumes so it knows your exact scene configuration.
Installing it
Same story for every node in this pack. ComfyUI Manager, search "Photoreal Prompt Builder", install, restart. Or:
cd ComfyUI/custom_nodes
git clone https://github.com/artokun/ComfyUI-Photoreal-Prompt-Builder.git comfyui-klein-photoreal-promptbuilder
Then restart ComfyUI. No pip dependencies needed. It's built for FLUX.2 Klein 9B - you'll want flux-2-klein-base-9b-fp8.safetensors plus a qwen_3_8b_fp8mixed.safetensors text encoder and flux2-vae.safetensors in your loaders.
Where people get burned
The example workflows depend on ComfyLab-Pack for the XY Plot Queue nodes, and here's a genuine trap: ComfyUI Manager's Install Missing Custom Nodes cannot auto-resolve XYPlotQueue / XYPlotRender, because ComfyLab-Pack publishes those nodes under display names. You have to install "ComfyLab Pack" from the Manager search manually - the README calls this out as an upstream quirk, not a missing dependency. The author (artokun, who also maintains the comfyui-mcp agent tooling) ships example graphs that need it, so budget an extra install if you grab xy_plot_minimal.json.
Inputs (21)
| Name | Type | Default | Description |
|---|---|---|---|
| subject | STRING | — | |
| pose | COMBO | unset | 55 options: unset, random, standing, standing hand on hip, standing both hands on hips, standing arms crossed, +49 |
| action | STRING | — | |
| scene_type | COMBO | unset | 20 options: unset, random, bedroom, bathroom, living room, kitchen, +14 |
| shot_type | COMBO | unset | 17 options: unset, random, extreme close-up, close-up face, headshot, upper body portrait, +11 |
| camera_angle | COMBO | unset | 14 options: unset, random, eye level, slightly low angle, slightly high angle, 3/4 angle, +8 |
| lighting_setup | COMBO | unset | 19 options: unset, inherit from scene, random, ring light, softbox beauty, natural window light, +13 |
| photo_style | COMBO | unset | 17 options: unset, random, phone candid, mirror selfie, editorial, lifestyle, +11 |
| lens | COMBO | unset | 10 options: unset, random, 24mm wide, 35mm, 50mm, 85mm portrait, +4 |
| depth_of_field | COMBO | unset | 8 options: unset, random, razor thin f/1.4, shallow f/2.0, shallow f/2.8, moderate f/4, +2 |
| color_grading | COMBO | unset | 14 options: unset, random, natural, warm golden, cool blue, cinematic teal-orange, +8 |
| hairstyle | COMBO | unset | 37 options: unset, random, beach waves, blunt bob, box braids, braided crown, +31 |
| hair_color | COMBO | unset | 31 options: unset, random, ash blonde, auburn, black, bleach blonde, +25 |
| preserve_identity | BOOLEAN | true | Append identity lock phrase for character reference consistency |
| outfitopt | STRING | — | |
| edit_instructionsopt | STRING | — | |
| environmentopt | STRING | — | |
| lighting_customopt | STRING | — | |
| moodopt | STRING | — | |
| extra_detailsopt | STRING | — | |
| negative_promptopt | STRING | — |
Outputs (3)
| Name | Type | Description |
|---|---|---|
| positive_prompt | STRING | — |
| negative_prompt | STRING | — |
| prompt_json | STRING | — |