PixelForge · Resolution Selector
PixelForge's divisible-size picker
- width_px
- height_px
- ratio_w
- ratio_h
- orientation
- total_megapixels
Every ComfyUI user has sat there with EmptyLatentImage open, squinting at the width and height fields and doing mental math. Is 1344×768 divisible by 64? Is that under a megapixel? Would it look better as 16:9 or 3:2? PixelForge is the answer to that specific, weirdly common chore: it's a resolution selector that hands you a pre-computed, divisible, under-your-MP-cap size, and it never lets you pick an invalid one.
Here's the whole pitch: one dropdown of valid resolutions, filtered live by the settings you actually care about. You decide the aspect ratio, the orientation, the divisibility constraint, and the megapixel ceiling - the node does the arithmetic. It ships as part of the tiny room3dev/ComfyUI-PixelForge pack (MIT licensed, no dependencies, no models to download), and it pairs with the pack's Resize Image node, which is the sibling that actually resizes a real image to one of these sizes.
How it works
The clever part isn't in Python - it's in the frontend. At load time, the node's Python code precomputes 692 candidate resolutions by crossing 5 aspect ratios, 3 divisibility values (16/32/64), and 7 megapixel caps, then it registers a web/js/pixel_forge.js extension in ComfyUI. That JavaScript watches your aspect_ratio, orientation, divisible_by, and max_megapixels widgets and rebuilds the resolution dropdown in the browser the moment you change any of them. The backend just parses the W×H string you end up with, does a safety orientation swap, and returns the numbers.
So the workflow-side node is dumb in the good way. It produces six outputs:
- width_px and height_px - these are the ones that matter; wire them into EmptyLatentImage's width/height (or into any node that takes a size) and you never mismatch latent dims again.
- ratio_w / ratio_h - handy if you're doing aspect-ratio math downstream, e.g. building the empty conditioning that SDXL wants to see.
- orientation and total_megapixels - bookkeeping, but nice to have as graph data.
The settings that matter
- divisible_by (16/32/64) - this is the one beginners skip and then wonder why their Flux VAE explodes. Flux and SDXL want sizes that are multiples of 64 for clean latents; SD 1.5 is happier at multiples of 8. If you're generating, default 16 is fine; pick 64 for models that are picky about it.
- max_megapixels (1–16 MP) - a hard cap on total pixels, with 1 MP defined as 1024×1024. Try it: 16:9 under 1 MP tops out at 1280×720. That's the constraint doing exactly its job.
- resolution - the filtered dropdown of ~60–100 valid combos for your current settings (out of the 692 precomputed). Just pick one.
Installing it
The README's "copy the folder into custom_nodes/" line is the whole manual install, because there's nothing else to it - no requirements.txt, no model files, nothing. Easiest route: ComfyUI Manager → "Install Custom Nodes" → search ComfyUI-PixelForge → install → restart. Or from a terminal:
cd ComfyUI/custom_nodes
git clone https://github.com/room3dev/ComfyUI-PixelForge
Then restart ComfyUI and look under the PixelForge category.
Where it bites
Because the filtering is frontend JS, the dropdown behaves oddly if that extension doesn't register - a stale browser cache or a workflow loaded in some embedded mode can leave you staring at the full 692-item list instead of the filtered one. The node still works; you're just back to eyeballing. And a genuine trap: keep max_megapixels near 1–2 MP for latent-space generation. Generating directly at 4K with the 12 MP setting is how you get the duplicate anatomy and tiling every troubleshooting thread warns about - that's a native-resolution problem, not a settings one. Pick a sane latent size here, then upscale the pixels afterward. There's no community chatter about this pack to lean on, so treat it as a young, unproven node - fine for a utility this simple, but test it before it becomes the backbone of a big workflow.
Inputs (5)
| Name | Type | Default | Description |
|---|---|---|---|
| aspect_ratio | COMBO | 1:1 | 5 options: 1:1, 3:2, 4:3, 16:9, 16:10 |
| orientation | COMBO | square | 3 options: landscape, portrait, square |
| divisible_by | COMBO | 16 | 3 options: 16, 32, 64 |
| max_megapixels | COMBO | 1 MP | 7 options: 1 MP, 2 MP, 4 MP, 6 MP, 8 MP, 12 MP, +1 |
| resolution | COMBO | 1024×1024 | 692 options: 16×16, 32×32, 32×48, 48×32, 48×48, 48×64, +686 |
Outputs (6)
| Name | Type | Description |
|---|---|---|
| width_px | INT | — |
| height_px | INT | — |
| ratio_w | INT | — |
| ratio_h | INT | — |
| orientation | STRING | — |
| total_megapixels | FLOAT | — |