Nodes/Ultra Tools/Ultra Tools Image Watermark
ComfyUI Node

Ultra Tools Image Watermark

Ultra Tools Image Watermark

By Yamoon-jjangยทCreated 14 days agoยทUpdated 9 days agoยท 5
Ultra Tools Image Watermark
  • image
  • watermark_image
  • mask
  • IMAGE
  • MASK
โ—„watermarkโ–บ
โ—„โ”€โ”€ ๐Ÿ–ผ๏ธ Watermark Image โ”€โ”€โ–บ
โ—„Size_Modepercentageโ–บ
โ—„Scale_Percent15.0โ–บ
โ—„Pixel_Width200โ–บ
โ—„Invert_Colorsfalseโ–บ
โ—„Color_Tintfalseโ–บ
โ—„Tint_Color_Presetcustom hexโ–บ
โ—„Tint_Color#FFFFFFโ–บ
โ—„Mask_Modeload image mask (invert)โ–บ
โ—„โ”€โ”€ โœ๏ธ Stroke โ”€โ”€โ–บ
โ—„Stroke_Width0โ–บ
โ—„Stroke_Color_Presetcustom hexโ–บ
โ—„Stroke_Color#000000โ–บ
โ—„โ”€โ”€ ๐ŸŒ‘ Shadow โ”€โ”€โ–บ
โ—„Shadow_Enabledfalseโ–บ
โ—„Shadow_Color_Presetcustom hexโ–บ
โ—„Shadow_Color#000000โ–บ
โ—„Shadow_Opacity0.50โ–บ
โ—„Shadow_Offset_X4โ–บ
โ—„Shadow_Offset_Y4โ–บ
โ—„Shadow_Blur6.0โ–บ
โ—„โ”€โ”€ ๐Ÿ”ฒ Tile โ”€โ”€โ–บ
โ—„Tile_Modeoffโ–บ
โ—„Tile_Axis_Modeangle alignedโ–บ
โ—„Tile_Spacing100โ–บ
โ—„โ”€โ”€ ๐ŸŽ›๏ธ Adjust โ”€โ”€โ–บ
โ—„Opacity1.00โ–บ
โ—„Blend_Modenormalโ–บ
โ—„Positionbottom rightโ–บ
โ—„Margin20โ–บ
โ—„Margin_X0โ–บ
โ—„Margin_Y0โ–บ
โ—„Edge_Softness0โ–บ
โ—„Rotation0โ–บ

Why not just paste a logo on

Because every naive implementation of "paste a logo on" has the same three bugs.

It sizes the watermark by the source canvas instead of the visible logo, so your carefully exported PNG with a 400ร—400 transparent canvas around a small mark comes out microscopic. It ignores alpha, so you get a black or white box where the transparency should be. And it gives you opacity and a position, then stops - no tiling, no blend modes, no way to make a pattern that survives being cropped.

Ultra Tools Image Watermark is a serious pass at all three. It's the node I'd hand to someone putting a mark on a few hundred images, and it's the one node in this pack with an obvious answer to "why this over a Python script."

How it works

The watermark is prepared in RGBA, and - this is the good bit - it gets cropped to its alpha bounding box before being scaled. The sizing percentage therefore applies to the logo you can see, not to the canvas the designer exported. There's a Mask_Mode for how the alpha is interpreted, because ComfyUI's own Load Image convention hands you an inverted alpha mask (1 - alpha); the default load image mask (invert) follows that, and normal mask (white visible) is for a mask you produced yourself where white means "show this."

Compositing is done in chunks in torch with a documented pixel ceiling per operation, so a 4K frame with a tiled, rotated watermark doesn't quietly allocate a dozen gigabytes. When a combination genuinely can't be done safely - an enormous tile spacing combined with rotation is the classic - the node stops and tells you, rather than silently downscaling your output. I'd take that trade every time, though it does mean a scary-sounding error the first time you hit it.

Tiling has two shapes and two alignments. full is a straight grid; diagonal offsets alternate rows so the pattern reads as a weave. angle aligned rotates the tile grid with the watermark; screen aligned keeps the grid orthogonal to the frame while the mark itself rotates. For copyright-defence patterns you want diagonal plus screen-aligned plus ~30ยฐ, which is the standard stock-photo look for a reason: it's very hard to crop around.

What you set

The widget list is long because it's genuinely parametric - grouped as watermark image, stroke, shadow, tile and adjust.

The ones that matter first: watermark (a dropdown of files already in ComfyUI's input folder - there's an upload button in the node, and there's also an optional watermark_image IMAGE input if you'd rather wire the mark in from the graph), Size_Mode (percentage of the image width, default, or pixels with Pixel_Width when the mark must be a fixed size regardless of frame), Position (seven placements), Margin plus Margin_X/Margin_Y for nudges.

Then the finishing layer: Opacity, Blend_Mode (normal, multiply, screen, overlay, soft light - multiply is the one for a dark logo on light images, screen for the inverse), Stroke_Width and colour, Shadow_Enabled with offsets and blur, Edge_Softness, and Rotation.

Two optional inputs, both genuinely useful: watermark_image (an IMAGE, so you can generate or composite the mark in-graph) and mask (a MASK, so a detected region can gate the watermark).

Outputs are IMAGE and MASK. That MASK is the composed watermark region as a mask, which is the whole reason this node exists in a pipeline: wire it into a downstream inpaint or a Text Watermark node that needs to avoid the logo area.

Install

cd ComfyUI/custom_nodes
git clone https://github.com/Yamoon-jjang/comfyui-Ultra-Tools

Manager โ†’ Ultra Tools works too. Full restart, then Ctrl+F5 - and this node is one where the hard refresh really matters, because the upload button and half the parameter UI live in web/ultra_watermark_upload.js. An empty watermark dropdown after an update is a stale-bundle symptom, not a permissions problem.

No pip packages. Pillow and numpy, both already there. If you ran an older comfyui-Ultra-* pack alongside this one, delete it first.

Common issues

Logo barely visible at 15%. Scale_Percent is a share of image width, and 15% of 1024 sounds bigger than it looks once the mark is a thin wordmark. 20โ€“30% is more typical; for a hard-quantity mark, switch to pixels.

Nothing appears at all. If you're loading the mark through the mask input, check Mask_Mode - inverted is the default and it will happily hide your logo.

Tiled output looks like a sheet of noise. Drop tile spacing toward the default 100 and raise opacity gradually. Very small spacing plus a busy mark at full opacity is unreadable, and the node will also start refusing the work at extreme combinations.

Recommended order for a finished image: original โ†’ Image Watermark (tiled mark) โ†’ Text Watermark (credit line) โ†’ Save. And if you're posting the results, remember the PNG's metadata carries your whole graph anyway - the watermark is the part people actually see.

CategoryUltra Tools

Inputs (38)

NameTypeDefaultDescription
imageIMAGEโ€”
watermarkCOMBO2 options: , example.png
โ”€โ”€ ๐Ÿ–ผ๏ธ Watermark Image โ”€โ”€STRINGโ€”
Size_ModeCOMBOpercentage2 options: percentage, pixels
Scale_PercentFLOAT15.00.5โ€“100โ€”
Pixel_WidthINT2001โ€“8192โ€”
Invert_ColorsBOOLEANfalseโ€”
Color_TintBOOLEANfalseโ€”
Tint_Color_PresetCOMBOcustom hex17 options: custom hex, white, black, red, green, blue, +11
Tint_ColorSTRING#FFFFFFโ€”
Mask_ModeCOMBOload image mask (invert)2 options: load image mask (invert), normal mask (white visible)
โ”€โ”€ โœ๏ธ Stroke โ”€โ”€STRINGโ€”
Stroke_WidthINT00โ€“20โ€”
Stroke_Color_PresetCOMBOcustom hex17 options: custom hex, white, black, red, green, blue, +11
Stroke_ColorSTRING#000000โ€”
โ”€โ”€ ๐ŸŒ‘ Shadow โ”€โ”€STRINGโ€”
Shadow_EnabledBOOLEANfalseโ€”
Shadow_Color_PresetCOMBOcustom hex17 options: custom hex, white, black, red, green, blue, +11
Shadow_ColorSTRING#000000โ€”
Shadow_OpacityFLOAT0.500โ€“1โ€”
Shadow_Offset_XINT4-100โ€“100โ€”
Shadow_Offset_YINT4-100โ€“100โ€”
Shadow_BlurFLOAT6.00โ€“50โ€”
โ”€โ”€ ๐Ÿ”ฒ Tile โ”€โ”€STRINGโ€”
Tile_ModeCOMBOoff3 options: off, full, diagonal
Tile_Axis_ModeCOMBOangle aligned2 options: angle aligned, screen aligned
Tile_SpacingINT100-2000โ€“2000โ€”
โ”€โ”€ ๐ŸŽ›๏ธ Adjust โ”€โ”€STRINGโ€”
OpacityFLOAT1.000โ€“1โ€”
Blend_ModeCOMBOnormal5 options: normal, multiply, screen, overlay, soft light
PositionCOMBObottom right7 options: center, top left, top center, top right, bottom left, bottom center, +1
MarginINT200โ€“2048โ€”
Margin_XINT0-2048โ€“2048โ€”
Margin_YINT0-2048โ€“2048โ€”
Edge_SoftnessINT00โ€“5โ€”
RotationFLOAT0-180โ€“180โ€”
watermark_imageoptIMAGEโ€”
maskoptMASKโ€”

Outputs (2)

NameTypeDescription
IMAGEIMAGEโ€”
MASKMASKโ€”