Add Image Watermark
Add Image Watermark
- image
- watermark_image
- watermark_mask
- IMAGE
Watermarking is the boring chore at the end of every generation. Whether you're branding work for a client or just want a small "sample" tag so your previews don't get passed off as finished, the old way means saving the image, opening an editor, compositing, and re-exporting. This node keeps the whole thing inside the graph: two images in, one watermarked image out. Nothing leaves ComfyUI.
It's part of a small personal pack called comfyui-MGnodes (the "MG" is the author's handle, not a framework). Don't expect a big community around it - but it's a straightforward Pillow composite under the hood, so there's not much to go wrong beyond the one gotcha below.
How it works
Under the hood this is plain Pillow: both images get converted to RGBA, the watermark picks up an alpha channel from a mask you feed it, gets scaled and opacified, then gets pasted onto the base in one of six positions - Center, Top Left, Top Right, Bottom Left, Bottom Right, or Tiled Pattern. If the base image already has transparency, it's preserved; the composite doesn't flatten it to black.
The inputs that matter, from the node's own schema:
- position - where the stamp lands, or
Tiled Patternto wallpaper the image with it - opacity_percentage (0–100, default 50) - how see-through the watermark is
- scale_percentage (10–1000, default 100) - 100 is original size, below shrinks, above enlarges
- make_black - inverts the watermark colors (for light-on-light situations)
- remove_white - makes near-white pixels transparent, so a logo on a clean white background becomes a floating stamp
The single output is an IMAGE, ready to wire straight into Save Image or the next node in the chain.
The mask gotcha - read this before wiring it up
Here's where people get burned, and it's the kind of thing that makes a node look broken when it isn't. The README calls watermark_mask optional, but the node actually requires it - leave the input unconnected and it won't run. Worse, the mask is treated backwards from normal ComfyUI convention. ComfyUI masks are white = keep; this node inverts the mask before using it as the watermark's alpha.
So if you wire in the all-white mask that Load Image hands you by default, your watermark comes out fully transparent. If you want a solid, opaque stamp, think of the mask as "black where the watermark should show" - feed it a fully black mask and the watermark is fully opaque, then use opacity to dial it back. remove_white doesn't rescue you from a white mask either; it only subtracts from what the inverted mask already allows.
One more quirk: the watermark's own PNG alpha is ignored. The code converts your watermark to RGB and uses only the mask for transparency, so if your logo is an RGBA file with baked-in transparency, the node won't respect it - that's what the mask is for.
Installing it
Same steps as any custom node, via ComfyUI Manager (search "MGnodes") or manually:
cd ComfyUI/custom_nodes/
git clone https://github.com/meanin2/comfyui-MGnodes.git
Then restart ComfyUI. The good news: this pack has no requirements.txt and declares no Python dependencies. This node only uses numpy, Pillow, and torch, which ComfyUI already ships - so no dependency hell, which is more than most packs can say.
Common issues
- Invisible watermark - you fed the default white mask. Feed a black one, or a mask that's black where you want the stamp.
remove_whitedoing nothing - the white threshold is hardcoded at 220, so a grey-ish background won't be removed. The README's tip stands: it works best on a genuinely clean white background.- Make Black + Remove White order - inversion happens before white removal, per the README, so the two compose in that order.
For a tiny node it does exactly one job, does it inside the workflow, and needs zero extra packages. Just remember the mask is backwards and you'll be fine.
Inputs (8)
| Name | Type | Default | Description |
|---|---|---|---|
| image | IMAGE | — | |
| watermark_image | IMAGE | — | |
| watermark_mask | MASK | — | |
| position | COMBO | Center | 6 options: Center, Top Left, Top Right, Bottom Left, Bottom Right, Tiled Pattern |
| opacity_percentage | INT | 500–100 | — |
| scale_percentage | INT | 10010–1000 | — |
| make_black | BOOLEAN | false | — |
| remove_white | BOOLEAN | false | — |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| IMAGE | IMAGE | — |