PettyPaintImageMaskCropper
Cut a character out of a full scene using its mask file
- image
- mask
- cropped_image_path
Extracting a clean cutout from a full scene is one of those chores every layered workflow eventually needs: the background plate is done, the character is rendered in place, and now you want just the character as its own transparent PNG. That's exactly what this node does - crop a color image down to the bounding box of its mask and bake that mask in as alpha. It's the petty-paint pack's way of turning a full-page render into a reusable layer file.
The whole pack is the ComfyUI-side integration for Petty Paint, Andrew Porter's web canvas that reimagines doodles via Stable Diffusion. Petty Paint's pipeline generates character poses and page backgrounds as separate files, and this cropper is how a full composite gets reduced to the character-alone PNG the app composites with later.
How it works
The important thing to know up front: this node does its work from file paths, not tensors. You give it mask_image_path (the mask PNG), color_image_path (the full-color image), and save_image_path (where the cutout goes). It opens the mask in grayscale, finds its bounding box with getbbox(), crops both images to that box, then stamps the mask into the color image's alpha channel and saves the result. Output is cropped_image_path - the string you saved to, ready to wire into a load node or hand back to the app.
The two IMAGE inputs (image, mask) are in the schema, but the implementation ignores them - it reads the files from disk. So don't fight it by building a tensor pipeline; feed it paths.
The inputs that matter
skip- if true, the node skips the whole crop and returnssave_image_pathunchanged. Wire this to a file-exists check for idempotent pipelines.mask_image_path/color_image_path- the two files to crop from.save_image_path- the output PNG path.- Output:
cropped_image_path, a STRING.
Note the graceful behavior: if skip is on, or either source file doesn't exist, it passes the save path through rather than erroring. That's friendly for looping workflows but means silent no-ops - check your paths if nothing appears.
Installing it
Same pack, same install - ComfyUI Manager, search "petty-paint-comfyui-node", or:
cd ComfyUI/custom_nodes
git clone https://github.com/mephisto83/petty-paint-comfyui-node
Restart ComfyUI. The declared dependency is Flask==2.1.2; this node doesn't even touch it, and there are no model files to fetch.
Common issues
The one real failure mode is a fully black mask: getbbox() returns nothing and the node raises "The mask image is completely black, no cropping region found." If you hit that, your mask file is wrong or empty - check it on disk rather than debugging the graph. And keep in mind the crop is tight to the mask's bounding box, so a noisy mask with stray specks produces a bigger-than-needed cutout. Feather or clean your mask before it goes to file if you want crisp edges.
Inputs (6)
| Name | Type | Default | Description |
|---|---|---|---|
| skip | BOOLEAN | false | — |
| save_image_path | STRING | — | |
| mask_image_path | STRING | — | |
| color_image_path | STRING | — | |
| imageopt | IMAGE | — | |
| maskopt | IMAGE | — |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| cropped_image_path | STRING | — |