Blockify Mask
Pixelate a mask into chunky blocks in one node
- masks
- mask
Blockify Mask takes a mask and turns it into a grid of solid squares - like a mosaic filter for your selection. Every block that overlaps the mask becomes fully white, everything else stays black, and you're left with a hard-edged, pixelated version of what you painted. It's the kind of node that sounds pointless until you actually need it.
The main reason people reach for it: a chunky block mask is what several pipelines want as input. WanAnimate mask preprocessing, for example, works better when the mask is coarse and stable instead of a hair-thin painted line that flickers between frames. The same idea applies to block-based inpainting, where you're regenerating whole tiles rather than a wobbly freehand region. And if you're building SAM-style region prompts or just want a mask that reads clearly at a glance, blockifying removes all the noise.
How it works
It's not a naive "snap to grid" across the whole image. The node finds the bounding box of everything the mask touches, divides that box into block_size cells, runs a max-pool over each cell - so a cell lights up if any part of the original mask was inside it - then upscales the coarse result back to full resolution with nearest-neighbor. No antialiasing, no soft edges, just blocks. The empty parts of the image never get touched, and it processes the whole batch with a little cqdm progress bar.
Inputs and outputs
Only three inputs, and you'll touch two of them:
masks(MASK) - feed it any mask, including a batched one; it's named plural on purpose.block_size(INT, 8–512, default 32) - target block size. Smaller is finer. It's a target, not exact: the code divides the mask's bounding box intobbox_size // block_sizedivisions, so the real block size is whatever divides evenly.device-cpuorgpu. Defaults tocpu; mask ops are cheap, so leave it unless you're chewing through hundreds of frames.
One output: mask (MASK), ready to feed into a sampler, a mask-to-image node, or whatever consumed your original.
Installing it
It ships in the ComfyUI-lhyNodes pack, so it's one install for all of these nodes:
- ComfyUI Manager → Custom Nodes Manager → search
lhyNodes→ Install, then restart. - Or manually:
cd ComfyUI/custom_nodes
git clone https://github.com/lihaoyun6/ComfyUI-lhyNodes.git
python -m pip install -r ComfyUI-lhyNodes/requirements.txt
Then restart ComfyUI. The pack's requirements (ultralytics, opencv-python, numpy, yarl) are pulled in at module load even though a mask utility like this one doesn't touch them - if you see an import error after installing, that's the usual culprit and reinstalling ultralytics fixes it.
Where people get burned
If your mask is smaller than block_size, the whole thing collapses into a single block - not a bug, but it surprises people who set 64 and wonder why their tiny face mask became one white square. And because blocks are max-pooled, a soft, feathered mask becomes fully hard-edged: it'll look like it covers more than it did. If you need a feathered result after blockifying, blur the output with a Blur Mask node. For the common case - a clean, coarse mask that doesn't fight you frame over frame - this is exactly the tool.
Inputs (3)
| Name | Type | Default | Description |
|---|---|---|---|
| masks | MASK | — | |
| block_size | INT | 328–512 | — |
| deviceopt | COMBO | cpu | 2 options: cpu, gpu |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| mask | MASK | — |