Skip to content

Commit 22e32c2

Browse files
committed
added the ImageCompositeWatermark node.
1 parent c5b925f commit 22e32c2

File tree

3 files changed

+73
-1
lines changed

3 files changed

+73
-1
lines changed

README.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,9 @@ According to the input image ratio, decide which standard SDXL training size is
8686
## UpscaleImageWithModelIfNeed
8787
Enhanced the official UpscaleImageWithModel node by adding a judge. If the input image area exceeds a predefined threshold, upscaling is bypassed. The threshold is a percentage of the SDXL standard size (1024x1024) area.
8888

89+
## ImageCompositeWatermark
90+
This node is designed to composite a watermark into the destination image. It can select the position of the watermark, resize the watermark according to the input ratio, and add a margin to the watermark.
91+
8992
## DetectorForNSFW
9093
This node adapts the original model and inference code from [nudenet](https://github.com/notAI-tech/NudeNet.git) for use with Comfy. A small 10MB default model, [320n.onnx](https://github.com/notAI-tech/NudeNet?tab=readme-ov-file#available-models), is provided. If you wish to use other models from that repository, download the [ONNX model](https://github.com/notAI-tech/NudeNet?tab=readme-ov-file#available-models) and place it in the models/nsfw directory, then set the appropriate detect_size.
9194

py/node_image.py

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
from comfy_extras.nodes_mask import ImageCompositeMasked
2+
import torch
3+
4+
class ImageCompositeWatermark(ImageCompositeMasked):
5+
@classmethod
6+
def INPUT_TYPES(s):
7+
return {
8+
"required": {
9+
"destination": ("IMAGE",),
10+
"watermark": ("IMAGE",),
11+
"position": (["bottom_right", "bottom_center", "bottom_left"], {"default": "bottom_right"}),
12+
"resize_ratio": ("FLOAT", {"default": 1, "min": 0, "max": 10, "step": 0.1}),
13+
"margin": ("INT", {"default": 0, "min": 0, "max": 1000, "step": 1}),
14+
},
15+
"optional": {
16+
"mask": ("MASK",),
17+
"enabled": ("BOOLEAN", {"default": True, "label_on": "enabled", "label_off": "disabled"}),
18+
"invert_mask": ("BOOLEAN", {"default": False, "label_on": "enabled", "label_off": "disabled"}),
19+
}
20+
}
21+
RETURN_TYPES = ("IMAGE",)
22+
FUNCTION = "composite_watermark"
23+
CATEGORY = "utils/image"
24+
25+
def composite_watermark(self, destination, watermark, position, resize_ratio, margin, mask=None, enabled=True, invert_mask=False):
26+
if not enabled:
27+
return (destination,)
28+
29+
if resize_ratio != 1:
30+
watermark = torch.nn.functional.interpolate(
31+
watermark.movedim(-1, 1), scale_factor=resize_ratio, mode="bicubic", antialias=True).movedim(1, -1).clamp(0.0, 1.0)
32+
if mask is not None:
33+
mask = torch.nn.functional.interpolate(mask.unsqueeze(
34+
0), scale_factor=resize_ratio, mode="bicubic", antialias=True).squeeze(0).clamp(0.0, 1.0)
35+
36+
37+
# 计算水印的位置
38+
dest_h, dest_w = destination.shape[1:3]
39+
water_h, water_w = watermark.shape[1:3]
40+
41+
# 计算y坐标 - 总是在底部
42+
y = dest_h - water_h - margin
43+
44+
x = 0
45+
# 根据position计算x坐标
46+
if position == "bottom_left":
47+
x = margin
48+
elif position == "bottom_center":
49+
x = (dest_w - water_w) // 2
50+
elif position == "bottom_right":
51+
x = dest_w - water_w - margin
52+
53+
if invert_mask and mask is not None:
54+
mask = 1.0 - mask
55+
56+
57+
return self.composite(destination, watermark, x, y, False, mask)
58+
59+
60+
NODE_CLASS_MAPPINGS = {
61+
62+
#image
63+
"ImageCompositeWatermark": ImageCompositeWatermark,
64+
}
65+
66+
NODE_DISPLAY_NAME_MAPPINGS = {
67+
# Image
68+
"ImageCompositeWatermark": "Image Composite Watermark",
69+
}

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
[project]
22
name = "comfyui-utils-nodes"
33
description = "Nodes:LoadImageWithSwitch, ImageBatchOneOrMore, ModifyTextGender, GenderControlOutput, ImageCompositeMaskedWithSwitch, ImageCompositeMaskedOneByOne, ColorCorrectOfUtils, SplitMask, MaskFastGrow, CheckpointLoaderSimpleWithSwitch, ImageResizeTo8x, MatchImageRatioToPreset, UpscaleImageWithModelIfNeed, MaskFromFaceModel, MaskCoverFourCorners, DetectorForNSFW, DeepfaceAnalyzeFaceAttributes etc."
4-
version = "1.2.2"
4+
version = "1.2.3"
55
license = { file = "LICENSE" }
66
dependencies = []
77

0 commit comments

Comments
 (0)