PixAI Tagger Plus ⚡
Six thresholds, eight outputs, and no absolute file paths
- image
- tags_string
- character_tags
- copyright_tags
- general_tags
- artist-style_tags
- meta_tags
- rating_tags
- device
What it is, and when you'd pick it over WD14
PixAI Tagger Plus wraps PixAI Tagger v1.0 - a heavier, more modern booru tagger than the WD14 family, published by pixai-labs with Apache-2.0 weights. Same job as any interrogator: hand it an image, get Danbooru-style tags back for prompt seeding, or for LoRA dataset captions on an Illustrious/NoobAI/Pony base.
The reason to reach for it isn't that WD14 is bad - it's that WD14 has known blind spots, hair and eye colour chief among them; there's a standing complaint about it reading red hair as brown, and "try the PixAI tagger" is the usual reply. Honest framing: a strong second opinion, not a strict upgrade. Run both on a few of your own images and see which vocabulary fits your base.
The architecture code is vendored from sln77's ComfyUI-Tagger (MIT, licence kept in the repo), and the weights are 1.9 GB of safetensors - chunkier than the 361 MB vit WD model, and it takes correspondingly more of your card.
The two things this node fixes
Upstream asks you to type absolute paths into model_file and config_file text boxes. No scanning, no dropdown, and every workflow breaks the moment you move a folder. This one scans ComfyUI/models/pixai_tagger/ and gives you a combo box.
The second fix is quieter and arguably better: this node runs entirely on PyTorch, no ONNX Runtime. That sidesteps the CUDA-provider mess that silently drops WD14 to CPU when the CUDA 12 runtime is missing, so it works on a CUDA 13 torch build where the ONNX path can't - and its device output is telling you the truth about your GPU.
How it works
It loads model.safetensors plus its config.json through the vendored ViT-Det style architecture, then per image: resize the long edge to the model's configured size (1008 by default), pad to a square, normalise with mean/std 0.5, run, sigmoid the logits. Each tag is then compared against the threshold belonging to its own category.
threshold_mode decides how those are set. custom uses the six numbers on the node. optimal_calibrated uses the model's own per-tag calibrated values and ignores all six. No opinion? Try that one first - it exists so you don't have to hand-tune a cutoff you can't reason about.
The dials that matter
Required: image, model, threshold_mode, and the six thresholds - general_threshold 0.17, character_threshold 0.27, copyright_threshold 0.24, style_threshold 0.15, meta_threshold 0.17, rating_threshold 0.41. Lower means more tags. One bar for everything would be a bad idea: character and series names deserve a different confidence than standing and smile.
Optionals: device (auto/cuda/cpu); sort_by_confidence, on by default; character_first, off - turn it on to make character tags lead the combined string, which is the conventional caption order; include_style, on; include_meta and include_rating, both off, so you don't accidentally dump highres or a rating tag into a prompt; replace_underscore; exclude_tags (comma-separated, case-insensitive, matches both blue_eyes and blue eyes); config_override (leave on auto - you only need it if one folder holds several configs); and unload_after_run.
Outputs
Eight strings, and the shape is the point. tags_string is the prompt-ready line: general + character + copyright, with style/meta/rating appended only if enabled, and character tags promoted to front if character_first is on. Then character_tags, copyright_tags, general_tags, artist-style_tags, meta_tags, rating_tags, and device.
Wire tags_string into a CLIP Text Encode when you're reversing a prompt for img2img. For dataset work the split outputs are the sleeper feature: save each category to its own Save Text File path, and check character_tags/copyright_tags before you train on it. rating_tags is the one people forget they have - if you're filtering a scraped set by rating, that's your signal.
Install
cd ComfyUI/custom_nodes
git clone https://github.com/Zove-try/ComfyUI-TaggerPlus
ComfyUI Manager works too - search the pack name and restart; nodes land in the TaggerPlus category. It pulls onnxruntime-gpu for its sibling WD14 node, plus safetensors and timm; PixAI itself needs only torch and timm.
Pick pixai-tagger-v1.0 in the dropdown and the first run downloads it (1.9 GB: model.safetensors + config.json) into ComfyUI/models/pixai_tagger/. Official HuggingFace first, hf-mirror as fallback; force the mirror with:
export TAGGERPLUS_HF_ENDPOINT=https://hf-mirror.com
Manual placement, if you'd rather fetch it yourself:
ComfyUI/models/pixai_tagger/pixai-tagger-v1.0/
├── model.safetensors
└── config.json
Common issues
The model dropdown is empty. The directory scan found nothing - check the folder is pixai_tagger (not pixai-tagger) under models/, and that the files sit in a subfolder rather than loose. You can point it elsewhere with a taggerplus_dirs.json next to the pack's __init__.py:
{ "pixai_tagger": ["E:/pixai-tagger"] }
timm missing. Only PyTorch-backend models fail - and for this node that's all of them, since PixAI ships no ONNX. pip install timm.
Rating or meta junk shows up in your prompt. include_rating and include_meta are the switches, and they default off precisely because a rating tag in a positive prompt is rarely what you wanted.
VRAM pressure next to a big diffusion model. The loaded model is cached, and the pack hooks ComfyUI's memory-freeing path to drop it after about 30 seconds idle. Tick unload_after_run to release the moment the run finishes.
Inputs (19)
| Name | Type | Default | Description |
|---|---|---|---|
| image | IMAGE | — | |
| model | COMBO | 已装模型直接选;带 ⬇ 的条目会在首次使用时**自动下载**(优先官方,失败切国内镜像) 扫描目录: /tmp/ComfyUI/models/pixai_tagger | |
| threshold_mode | COMBO | custom | custom = 用下面 6 个阈值;optimal_calibrated = 模型自带的逐标签校准阈值(会忽略下面 6 个) |
| general_threshold | FLOAT | 0.170–1 | — |
| character_threshold | FLOAT | 0.270–1 | — |
| copyright_threshold | FLOAT | 0.240–1 | — |
| style_threshold | FLOAT | 0.150–1 | — |
| meta_threshold | FLOAT | 0.170–1 | — |
| rating_threshold | FLOAT | 0.410–1 | — |
| deviceopt | COMBO | auto | 3 options: auto, cuda, cpu |
| config_overrideopt | COMBO | auto | 一般不用改;只有当同名目录里有多份 config.json 时才需要指定 |
| sort_by_confidenceopt | BOOLEAN | true | — |
| character_firstopt | BOOLEAN | false | — |
| include_styleopt | BOOLEAN | true | — |
| include_metaopt | BOOLEAN | false | — |
| include_ratingopt | BOOLEAN | false | — |
| replace_underscoreopt | BOOLEAN | false | — |
| exclude_tagsopt | STRING | — | |
| unload_after_runopt | BOOLEAN | false | — |
Outputs (8)
| Name | Type | Description |
|---|---|---|
| tags_string | STRING | — |
| character_tags | STRING | — |
| copyright_tags | STRING | — |
| general_tags | STRING | — |
| artist-style_tags | STRING | — |
| meta_tags | STRING | — |
| rating_tags | STRING | — |
| device | STRING | — |