7

I'm trying to experiment a workflow where I can manually paint normals to create stylized shading for a model.

Painting on the model, I want to use object-space normal, as it's easier to work with, but it's a problem that I end up with tangent space normals. Ideally I would want to just convert it back to tangent space in the shader.

At the very least I have to know whether or not it's possible to do what I'm trying to do?

meatandmahjong
  • 85
  • 1
  • 1
  • 4

2 Answers2

15

The simplest way to do such a conversion is to calculate the dot products between the Object_Space_Normal and the Tangent plane, and then 'normalize' the result to RGB.

$\vec{Tg}_N = 0.5 + \begin{bmatrix} \vec{Tg} \cdot \vec{N}_{obj} \\ (\vec{N} \times \vec{Tg}) \cdot N_{obj} \\ \vec{N} \cdot \vec{N}_{obj} \end{bmatrix} / 2 $

And with nodes: enter image description here This is the main process when working with vectors in World space.

In the case where your Normals are Object normals encoded into RGB, then you need to convert them first to world as in the following example: enter image description here

Secrop
  • 3,576
  • 19
  • 20
  • 1
    Hi, yoür formula was really hard to read. I tried to convert it with proper formatting, but did I possibly mess up? Could you correct it, please? – Leander Aug 11 '20 at 09:31
  • 1
    @Leander, it looks ok... I'll post the equivalent in nodes, for people less comfortable with math notation. – Secrop Aug 11 '20 at 09:34
  • I'm especially confused because it says 0.5 * [...] / 2 which cancels each other out and results in [...]. – Leander Aug 11 '20 at 09:38
  • 1
    @Leander, it's supposed to be a sum.. my fail, but corrected. :) – Secrop Aug 11 '20 at 09:39
  • This look like it! I was missing the offset. I guess we'll have to reverse-engineer the math ;). But seriously, thanks. – Robin Betts Aug 11 '20 at 09:54
  • @RobinBetts, I forgot a small detail.. the posted equation is for Normals in World space, not in Object space. For Object space,we need to transform the Tangent and the Normal vector from World to Object before use them in the rest of the nodes (with VectorTransform Node). – Secrop Aug 11 '20 at 10:09
  • @Secrop cheers! That's where I was, anyway, assuming a bake from WSpace. I may take the liberty of putting that correction in, if you haven't, when I've had time to reproduce it – Robin Betts Aug 11 '20 at 10:15
  • I tried this, but it did not work as expected. Setting the nodes up like in the image. After baking object normals to an image, and putting it through this, I would expect to see no difference, since I just baked the normals that were already there, and converted them back into tangent space? Here's what I'm getting link – meatandmahjong Aug 11 '20 at 13:53
  • 1
    @meatandmahjong, I see now what you're trying to do... I'll update my answer later today, but you need to use the NormalMap node with your Texture, before plugging it into this node setup. (or 2*Tex-1) – Secrop Aug 11 '20 at 14:57
  • @Secrop Thanks for fleshing this out..I would have got it wrong. You need the Normal Map node set to 'Object' and the Vector Transform? .. I'm finding the vector-spaces hard to visualize – Robin Betts Aug 11 '20 at 19:08
  • @RobinBetts, actually the VectorTransforms aren't needed, as the three vectors (N, Tg and the NormalMap) are in the same space (world). But you need the NormalMap set to 'Object', because the painted texture isn't really a vector. – Secrop Aug 11 '20 at 22:40
  • There is an error in the screenshots. The dot product inputs are in the wrong order. Swapping the inputs produces the correct dot product – MysteryPancake Aug 21 '23 at 21:03
  • @MysteryPancake Do you mean the inputs for the DotProduct nodes? Dot Product is a commutative operation! That means Dot(A, B)==Dot(B, A). What might be cause a wrong result is if the ObjectSpace Texture was produced by a software where Y and Z are switched... – Secrop Aug 23 '23 at 13:14
  • @Secrop I don't know how but it produces a different result in the other order. I found this solution on a different stack overflow question so I thought I should post it on the original question – MysteryPancake Sep 13 '23 at 08:01
  • @Secrop see this post https://blender.stackexchange.com/questions/293663/how-do-i-convert-object-to-tangent-space-normal-maps-for-triplanar-projection – MysteryPancake Sep 13 '23 at 08:05
  • @MysteryPancake, Ohh I see.. It's not the dot product, it's the cross product... (cross product is not a commutative operation). This is only in the screenshots.. the equation above is still correct (the correct value for the CoTg is (N x Tg)!) I'll correct them as soon as possible. Thanks. – Secrop Sep 13 '23 at 12:54
0

You can simply bake the normals, just make sure you save the image and set it to non-color in the shader editor.

This isn't contained within the shader editor, but if you're hand painting it shouldn't matter.