Home Technical Talk

(Solved, sort of) [Blender] Unpack normal map

polycounter lvl 6
Offline / Send Message
bitinn polycounter lvl 6
Hi all,

I couldn't figure out how to properly unpack a normal map with Blender. My normal map's RG are stored in a texture's G/A channel. I am trying to reconstruct B, combine, then supply it to the normal map node.

Question: how does the normal map node work though? (What color input does it expect? 0~1 range? -1~1 range? Why does it has a separate uv map field when we have sampled the texture already?)



I have done this many times in Unity/Maya, so I don't believe my normal unpack math is wrong: it's likely something Blender specific I am not aware of.

I have tried both 0~1 and -1~1 range, neither look right (as in, I don't expect a default normal map to change an object's shading, but it does...)

Without normal map:



With normal map (range 0~1 or -1~1)




Thx in advance!


Replies

  • FourtyNights
    Offline / Send Message
    FourtyNights polycounter
    What's with this complex node setup for your normal map before the "Normal Map" node, and odd channel organizing? Why not just plugging a regular normal map (RGB) as an image texture and set it to use "Non-Color Data"? :D It's simple as that.

    Or am I missing something, since I don't get what's the reason behind this...
  • bitinn
    Offline / Send Message
    bitinn polycounter lvl 6
    What's with this complex node setup for your normal map before the "Normal Map" node, and odd channel organizing? Why not just plugging a regular normal map (RGB) as an image texture and set it to use "Non-Color Data"? :D It's simple as that.

    Or am I missing something, since I don't get what's the reason behind this...
    As stated in OP, my normal map is not a simple normal map, it's a form of channel packing.
  • bitinn
    Offline / Send Message
    bitinn polycounter lvl 6
    Not sure I should open another thread for this question, so I am adding it here:

    I also face another issue (which didn't appear a few days ago, so I must have messed up something else), where Principled BSDF doesn't show color texture but issue only happens in render view, you can see it looking fine in material view (not great, due to lack of real-time PBR shader in 2.79, and some normal shading bug I don't fully understand).

    What could have caused this? 




  • FourtyNights
    Offline / Send Message
    FourtyNights polycounter
    Yeah, but packing textures to different channels apply to greyscale images, not images that are using the full RGB colors in order to work, such as an albedo and a normal map. For the record, I also use packing for textures, but for greyscale ones such as roughness, metalness, specular, ambient occlusion, thickness and transparency.
  • bitinn
    Offline / Send Message
    bitinn polycounter lvl 6
    Yeah, but packing textures to different channels apply to greyscale images, not images that are using the full RGB colors in order to work, such as an albedo and a normal map. For the record, I also use packing for textures, but for greyscale ones such as roughness, metalness, specular, ambient occlusion, thickness and transparency.
    Normal map packing works, that's all I am going to say.

    (My question is specific to Blender)
  • bitinn
    Offline / Send Message
    bitinn polycounter lvl 6
    bitinn said:
    Not sure I should open another thread for this question, so I am adding it here:

    I also face another issue (which didn't appear a few days ago, so I must have messed up something else), where Principled BSDF doesn't show color texture but issue only happens in render view, you can see it looking fine in material view (not great, due to lack of real-time PBR shader in 2.79, and some normal shading bug I don't fully understand).

    What could have caused this? 





    So I have "understood" my 2 issues here:

    Issue 1: Normal Map unpacking

    My math was right, but my image file color space setting is wrong: at some point during my experiment, I have changed the texture file's color space to linear and turned "use alpha" off. Since my normal RG is stored in image's GA channel, half of my normal data were dropped, hence the normal map discrepancy.

    During my test, I also discover another subtle issue in Material View:

    - If I use PNG image file (straight alpha), then Blender somehow force pre-multiplication on the result, and the workaround is to set alpha to "premultipled"

    - If I use TGA image file (also straight alpha), then Blender doesn't force the same multiplication, and hence I should leave the alpha setting to "straight".

    This only affects the material view; render view is fine either way.

    Issue 2: Color texture with straight/unassociated alpha

    This is where Blender fall short: as of Blender 2.79 (2018-07-12 build), it still doesn't support a color texture with unrelated alpha channel (eg. a straight alpha with some grayscale data that's not transparency).

    This means, for a pixel with RGBA (100, 120, 140, 0), I can either:

    - Drop the alpha, get the correct RGB color.
    - Keep the alpha, but get a black RGB color.

    But I can't get both; whether the file is PNG or TGA doesn't matter. And this only affects the Render view, as shown above, Material view is fine neither way.

    The workaround? Duplicate the texture file, and import it as a separate texture... (EDIT: or duplicate the image data block which is referencing that image file.)

    As the color-space and use-alpha setting are per-texture, this is the only way to get both RGB and A.

    TL;DR

    - If you use channel packing texture like me, be aware of Blender's PNG treatment, which require you to set Alpha to Premultiplied, as Blender is being too clever in trying to multiple RGB by Alpha (this is desirable in many cases, just not cases when you want Alpha to actually be separately from RGB). This only affects Material View.

    - If you use channel packing, and somehow store color texture in RGB with some grayscale texture in A, then note that you can't extract both in Blender 2.79; you can workaround it by importing 2 files and extract RGB and A separately. This only affects Render view.

    Feel free to correct me if I am wrong, here are my reference:

    Image Texture node
    image file color space
    - My research summarized in here.
Sign In or Register to comment.