CPPN Generator
Procedural abstract art with no model download at all
- images
- images
This is the node that doesn't belong in a diffusion UI - and it's great because of it. CPPN Generator produces abstract, organic, sometimes genuinely beautiful procedural images with zero weights, zero model downloads, and zero GPU requirement beyond what a sampler would hog. A CPPN - Compositional Pattern-Producing Network - is a decades-old idea from Kenneth Stanley's NEAT research, made famous to the generative-art crowd by hardmaru's blog posts. This node is a direct descendant of those, and it's exactly the thing to reach for when you need a weird abstract texture, a tiling-ish background, or an animation seed that has nothing to do with a checkpoint.
How it works
A small neural network takes coordinates as input - x, y, and radius from center r for every pixel - plus a latent vector z, and outputs pixel color. Because the network is a continuous function over coordinates, it produces smooth, structured patterns rather than noise: blobs, ripples, gradients, cells. The magic dials are the activation functions. Set everything to Sin and you get the classic CPPN look - layered interference patterns. Tanh gives soft organic gradients, ReLU gives hard-edged geometric shards, Modulo gives... well, try it.
The node runs on CPU by default (it builds its model on cuda:0 if available, else CPU), and for a single frame it's quick. The latent z is seeded, so a given seed always reproduces the same pattern. One honest caveat: framecount is declared as an input and both the README and the auto-generated docs talk about animation, but the shipped code never actually reads it - run it and you get a single image, full stop. To animate, drive z_offset or the coordinate offsets from a loop/queue node instead of hoping framecount multiplies your output.
The inputs that matter
There are roughly twenty inputs and you should touch about six of them:
seed- the pattern identity. Everything else equal, a new seed is a new pattern.width/height- output size, up to 8192.framecount- declared, but the shipped code ignores it (see below). Don't expect it to multiply your output yet.mode-GrayscaleorRGB. RGB gets the full three-channel treatment.first_activation/middle_activations/last_activation- where the character lives. Start withSinfor the classic look.last_activationdefaults toSigmoid, which is what maps raw outputs into the 0–1 range.scale- zoom. Below 1 zooms in, above 1 zooms out. This is the fastest way to change the "wavelength" of the pattern.
The rest - mean, std, bias_*, output_factor, output_offset, offsets - are weight-init and output-shaping knobs that tune fine detail once you've got a seed you like. normalize (default off) rescales the output to use the full 0–1 range; turn it on if your pattern comes out dark or clipped.
One quirk: the schema declares an optional images input, but the current code never actually consumes it. Don't wire anything in expecting it to do something.
Install
From the Quasimondo pack - ComfyUI Manager → search ComfyUI-QuasimondoNodes, or:
cd ComfyUI/custom_nodes
git clone https://github.com/Quasimondo/ComfyUI-QuasimondoNodes
cd ComfyUI-QuasimondoNodes
pip install -r requirements.txt
The node itself is pure torch/numpy - it doesn't need the pack's moderngl or even OpenCV. No checkpoint, no LoRA, no safetensors anywhere.
Where people get burned
The two traps are both about cost. First, the default is 1024×1024 with a 3-layer network - fine as a still, but if you crank framecount to 64 at full res on CPU, it stops being instant. Start small, confirm the look, then scale. Second, normalize is off by default; without it, patterns built around Sigmoid output are already in range, but switch the last activation to something like ReLU and you'll get blown-out highlights until you enable it.
The other thing to know: this is a procedural-art toy, not a diffusion model. It will never make you a photorealistic anything. As a texture/background/latent-walk machine it's a joy; expecting a model is missing the point.
Inputs (24)
| Name | Type | Default | Description |
|---|---|---|---|
| seed | INT | 00–9007199254740991 | — |
| width | INT | 10241–8192 | — |
| height | INT | 10241–8192 | — |
| framecount | INT | 11–512 | — |
| dim_z | INT | 321–512 | — |
| channels_in | INT | 321–512 | — |
| layers | INT | 30–16 | — |
| first_activation | COMBO | 7 options: Tanh, Sigmoid, Sin, ReLU, ELU, Softplus, +1 | |
| middle_activations | COMBO | 7 options: Tanh, Sigmoid, Sin, ReLU, ELU, Softplus, +1 | |
| last_activation | COMBO | Sigmoid | 7 options: Tanh, Sigmoid, Sin, ReLU, ELU, Softplus, +1 |
| scale | FLOAT | 1.00-1024–1024 | — |
| x_offset | FLOAT | 0.0-100000000–1000000000 | — |
| y_offset | FLOAT | 0.0-1000000000–1000000000 | — |
| z_offset | FLOAT | 0.0000-1000000000–1000000000 | — |
| mean | FLOAT | 0.0000-1000–1000 | — |
| std | FLOAT | 1.00000–1000 | — |
| bias_mean | FLOAT | 0.0000-1000–1000 | — |
| bias_std | FLOAT | 1.00000–1000 | — |
| zero_bias | BOOLEAN | true | — |
| output_factor | FLOAT | 1.0-100000000–1000000000 | — |
| output_offset | FLOAT | 0.0-1000000000–1000000000 | — |
| mode | COMBO | 2 options: Grayscale, RGB | |
| normalize | BOOLEAN | false | — |
| imagesopt | IMAGE | — |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| images | IMAGE | — |