πΊοΈ Normal Map Generator
A small, real, depth-to-normals workhorse in a pack full of stubs
- depth_map
- normal_map
- normal_visualization
- detail_strength
Every depth-based workflow eventually needs a normal map, and this node does that one job correctly. NormalMapGenerator takes a depth image and converts it to surface normals via Sobel gradients - a standard, textbook technique that's genuinely implemented. In a pack where several "AI" nodes are placeholder stubs (the kanibus/kanibus repo is Claude-generated, last commit Aug 2025), this one is refreshingly real. It's also small: one input, a couple of knobs, three outputs.
How it works
The mechanism is the classic depth-to-normal conversion: compute the image gradient of the depth map (Sobel operator on X and Y), negate and use them as the normal's tangent components, set Z to 1.0, then normalize each vector. The result is an RGB normal map where each channel encodes a surface direction - standard material/relighting input that ControlNet normal or IC-Light-style workflows consume.
strength(0.1β5, default 1) scales the gradient, i.e. how sharply the normals react to depth changes. Higher = more exaggerated relief.blur_radius(0β10, default 1) pre-blurs the depth map so noise doesn't turn into garbage normals. Blur first, sharpen later - this is the knob that saves you from speckly maps.invert_yflips the Y component for coordinate-system mismatches (some pipelines want normals flipped vertically).- The
wan_version/enable_t2i_adapteroptions just tweak the Sobel kernel size and attach metadata; harmless defaults.
Outputs: normal_map (the RGB normal image), normal_visualization (a saturated version for eyeballing), and detail_strength (a FLOAT derived from gradient standard deviation - a rough "how much relief is in this depth" meter). Feed it a depth map from a real estimator (MiDaS, Depth Anything, or even a generated one) and it works.
Inputs you'll set
The depth input is depth_map (IMAGE), and it's the only thing you must get right - a flat or noisy depth input produces flat or noisy normals. Start with strength at 1 and blur_radius 1β3, then raise strength if the result looks washed out.
Installing
cd ComfyUI/custom_nodes
git clone https://github.com/kanibus/kanibus
cd kanibus # lowercase - README's "cd Kanibus" breaks on Linux/Mac
pip install -r requirements.txt # or requirements_minimal.txt if it conflicts
python install.py
Restart ComfyUI, find it in the Kanibus category. No model downloads - it's pure OpenCV math. (The README's "you MUST download 5.6GB of ControlNet models" is not enforced by any node in this pack.)
Gotchas
- Garbage in, garbage out. This node is only as good as its depth input. Pair it with a real depth estimator, not the pack's own
AIDepthControl(whose "depth maps" are fake vertical gradients - normals from that will look like a smooth hill, every frame). - Single channel. It reads the first channel of the depth tensor; multi-channel RGB "depth" images get silently reduced.
- Invert when relighting. If your normals look wrong for a lighting pass, flip
invert_ybefore assuming a bug.
This is one of the three or four nodes in the pack I'd actually reach for. It won't change your life, but when you need a normal map from a depth map inside a Kanibus workflow, it does exactly what it says - which is more than you can say for half the pack.
Inputs (7)
| Name | Type | Default | Description |
|---|---|---|---|
| depth_map | IMAGE | β | |
| strength | FLOAT | 1.000.1β5 | β |
| blur_radiusopt | INT | 10β10 | β |
| invert_yopt | BOOLEAN | false | β |
| wan_versionopt | COMBO | auto | 3 options: wan_2.1, wan_2.2, auto |
| enable_t2i_adapteropt | BOOLEAN | true | β |
| cache_resultsopt | BOOLEAN | true | β |
Outputs (3)
| Name | Type | Description |
|---|---|---|
| normal_map | IMAGE | β |
| normal_visualization | IMAGE | β |
| detail_strength | FLOAT | β |