Skip to content

Add Triplanar texture coordinate type#409

Open
jakeblakeley wants to merge 2 commits into
ucupumar:masterfrom
jakeblakeley:triplanar-mapping
Open

Add Triplanar texture coordinate type#409
jakeblakeley wants to merge 2 commits into
ucupumar:masterfrom
jakeblakeley:triplanar-mapping

Conversation

@jakeblakeley

@jakeblakeley jakeblakeley commented Jul 7, 2026

Copy link
Copy Markdown
Contributor

Summary

Adds a Triplanar texture coordinate type for both layers and masks. It projects the layer/mask source along the three object axes and blends the three samples by the surface normal, so it works with any source — images and procedural textures alike — in both Eevee and Cycles, back to Blender 2.80.

Controls (layers and masks)

  • Projection Blend — transition softness between the projection axes.
  • Expand — grows the coverage of the shown sides to counteract the fade that appears when some sides are hidden. This may be too much as there's other ways to do this, but its handy to get more of one axes for things like moss.
  • Show +X / −X / +Y / −Y / +Z / −Z — per-side visibility, selected by the sign of the surface normal so each side of an axis can be toggled independently.

How it works

When a layer or mask uses the Triplanar coordinate, its source group is wrapped in a per-entity node tree that instances the actual source three times with swizzled object-space coordinates. This is a little expensive on weaker hardware so we may want to warn folks. Color always blends all three projections (so there is no stretching on faces that tilt away from a single axis), while the Show/Expand controls only fade coverage through the alpha weights. get_source_tree / get_mask_tree transparently unwrap the wrapper, so the rest of the addon (modifiers, linear nodes, baking, source editing) is unaffected.

It composes with the existing machinery: smooth bump reuses the same wrapper for its neighbor sources, and layer/mask duplication copies the inner source tree so instances are not shared. You can technically get this effect with the fake lighting approach, but its quite a long setup. This also exists in similar software like Substance Painter.

All the weight math is built from scalar Math, Separate/Combine XYZ and Mix nodes, so it evaluates identically in both engines with no version-specific fallbacks. The triplanar utility node groups are generated in lib.py following the existing programmatic node-group convention (like get_smooth_mix_node), so no changes to the binary lib*.blend files were needed.

Commits

  1. Bugfix — grouped source tree handling in check_layer_source and replace_layer_type. Both are pre-existing issues affecting any layer that uses a source group (e.g. with smooth bump), independent of this feature; split out for separate review.
  2. Feature — the Triplanar coordinate type.

Testing

Verified on Blender 5.2: node-graph validity, coordinate switching round-trips without leaking wrapper trees, procedural and image layers/masks, smooth-bump interaction, layer type changes, duplication, and save/reload. Rendered per-face parity checks in both Eevee and Cycles confirm the projection, per-side hiding, and expand behavior. Compatibility with 2.80 is by construction (only nodes and Vector Math ops available since 2.80 are used). Test on Nvidia and Mac GPUs.

You might need to set "shade smooth" on low poly meshes to see the effect properly. Here's screenshots of the effect working with textures, as a mask, and with procedural effects:
triplanar with noise
triplanar on layer
triplanar as mask

…ayer_type

check_layer_source added the source node to the layer tree instead of the
source group tree, so toggling a channel on a layer that uses a source group
(e.g. with smooth bump enabled) could recreate the source with a blank image.
Redirect it through get_source_tree.

replace_layer_type removed the source's input link from the layer tree rather
than the source group tree that actually owns it, raising "Unable to locate
link in node tree" when changing the type of a layer that uses a source group.
Use source_tree for the removal.
Projects the source along the three object axes and blends them by the surface
normal, so it works with any source (images and procedural textures alike) in
both Eevee and Cycles, back to Blender 2.80.

The source group is wrapped in a per-entity node tree that instances the source
three times with swizzled object-space coordinates. Color always blends all
three projections to avoid stretching, while the per-side controls only fade
coverage through the alpha weights. Works with smooth bump (the neighbor sources
share the wrapper) and layer/mask duplication.

Controls, exposed on both layers and masks:
- Projection Blend: transition softness between projection axes
- Expand: grows shown-side coverage to counteract fading when sides are hidden
- Show +X/-X/+Y/-Y/+Z/-Z: per-side visibility, selected by the normal direction

All the weight math is built from scalar Math, Separate/Combine XYZ and Mix
nodes so it evaluates identically in both engines with no version-specific
fallbacks. Triplanar utility node groups are generated in lib.py following the
existing programmatic node group convention.
@ucupumar

ucupumar commented Jul 7, 2026

Copy link
Copy Markdown
Owner

Wow! Thanks a lot for this!

This looks like a big change, since Ucupaint is currently undergoing a big refactor that removes the smooth bump and separates the height/bump and normal channels, I think this will be better merged after the refactor to avoid unnecessary complexity. The refactor will be released as version 3.0 (https://github.com/ucupumar/ucupaint/milestone/3). It should be released this month at the earliest or next month at the very least.

You can test version 3.0 in the branch v300bt. It's still WIP, and many UI elements and properties will likely change. I'll open a discussion about the changes soon in the discord server, feel free to join in!

@jakeblakeley

Copy link
Copy Markdown
Contributor Author

Awesome! I'll hold off on refactoring this onto that until then. Let me know if you need design support or feedback, I'm a product designer as my day job (https://jake.ly/) and would love to help out with UCUpaint as I use it daily

@ucupumar

ucupumar commented Jul 8, 2026

Copy link
Copy Markdown
Owner

Nice! Your designs are amazing! Version 3.0 really has so many changes that the UI needs many reconsiderations. I already posted some progress in the channel #ucupaint-ui-design-and-feedback on Discord. There are not many discussions there yet, but if you have any opinions, feel free to tell me 🙏

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants