2BZ Frequency Detail Transfer
Borrow the Texture, Not the Face
- base_image
- detail_image
- mask
- image
- high_pass_preview
What it's for
You have an AI image with that familiar plastic look - smooth skin, mushy hair, flat fabric - and you have a restored version of it (SeedVR2, SUPIR, whatever) that has pores and fabric weave but slightly different shapes and a different overall tone. You want the second image's texture and the first image's face.
That's frequency separation, and the KB's IC-Light entry calls it "the single most valuable technique in this doc" for exactly this reason: take lighting and form from one source, detail from another. This node does the one thing, on the GPU, in one box - no hand-built blur/subtract/add chain.
Pair it with 2BZ SeedVR2 Tile Restore (the node's own description names that pairing) or with 2BZ Retouch Blend (skin-aware) if you want the skin masked version at a lower strength.
How it works
The kernel is one line: result = blur(base, σ) + (detail − blur(detail, σ)) × strength.
The first term is the original's low frequencies - shapes, shading, colour. The second is the high-pass of the detail image, i.e. what's left after you subtract a blurred copy of itself. So the result keeps the original's structure and only accepts the restored image's fine grain. That's the same arithmetic the KB describes for unsharp masking ("blur a copy, subtract it to isolate the high-frequency detail, add that detail back"), just run for compositing instead of for sharpening.
Two details worth knowing. The high-pass is not clamped before it's added in - negative values survive, which is why the texture follows edges instead of glowing around them. And the blur runs on ComfyUI's compute device, so an 18 MP sheet costs seconds rather than the minutes you'd get on CPU.
Inputs and outputs that matter
base_image- the original. Its shapes and shading are what survives.detail_image- the texture donor. Your restored/upscaled version goes here.blur_sigma(default 3) - where "texture" stops and "form" begins. Smaller moves only pore-level grain; larger starts transplanting structure, which is how you get ghosted double edges.detail_strength(default 1.25) - how much texture you get. Below about 0.9 you're subtracting detail, because at strength 0 all you have left isblur(base)- a blurred original. The 1.25 default is the author's measured value on character sheets, not a round number picked for looks.mask(optional) - white areas only. It blends the result back over the base through the mask, so a soft mask gives you a graduated transition rather than a hard line.
Outputs are image and high_pass_preview. Wire the preview to Preview Image while you dial blur_sigma - it's the high-pass boosted ×4 around a mid-grey, so a mostly-flat grey frame with faint texture visible is correct, not a broken node. If you see big blobby shapes in there, your sigma is too large for what you're trying to transfer.
Install
Ships in the toobusy pack (너무바쁜베짱이, publisher neobabae) as of v0.5.4. It's also a standalone node that existed outside the pack; the same class name registers twice if you have both, so delete or disable the old folder.
cd ComfyUI/custom_nodes
git clone https://github.com/nicekriss/toobusy.git toobusy
Manager installs work - search the pack title - but if the newest retouch nodes don't show up, the registry copy is behind: use Manager's Install via Git URL with the repo URL, or clone and git pull. Restart ComfyUI after installing. No pip dependencies and no model files of its own; the pack's core deps are empty.
Where people get tripped up
"It made my image softer." Yes - if you run this with a weak or missing detail image, or push detail_strength under ~0.9, the output is literally a blurred base plus weak texture. The node only ever adds what the donor image actually contains.
It cannot fix shapes. If the original has a melted ear, the low frequencies are the melted ear, and no amount of high frequency from a nicer image will push the shape back. That's a job for an inpainting pass or a better first generation, not a texture transfer. Related: this is deliberately not a fix for faces that read as too smooth because they're under-resolved - for that you want the crop → re-render → paste loop, where the region gets its own latent budget.
Aspect mismatches are silent. The donor is resized to the base's dimensions, so a donor from a different crop or a differently-shaped upscale gets stretched before the subtraction. Keep both images from the same source frame.
Watch the blur_sigma ceiling. At high values the low-pass, high-pass and the base's own edges start interacting and you get halos or a doubled outline - the same failure mode as over-cranking an unsharp mask, and there's no rescue downstream.
Inputs (5)
| Name | Type | Default | Description |
|---|---|---|---|
| base_image | IMAGE | 형태·음영을 유지할 원본 | |
| detail_image | IMAGE | 질감을 가져올 이미지 (예: 2BZ SeedVR2 Tile Restore 결과) | |
| blur_sigma | FLOAT | 3.00.5–64 | 질감/형태 경계. 작을수록 모공급 미세 질감만 옮김 |
| detail_strength | FLOAT | 1.250–2 | 1.0 미만이면 원본보다 뭉개짐. 캐릭터시트 검증값 1.25 |
| maskopt | MASK | 흰 영역에만 적용 (피부/얼굴 등) |
Outputs (2)
| Name | Type | Description |
|---|---|---|
| image | IMAGE | — |
| high_pass_preview | IMAGE | — |