CG Surface shader continued - normal maps, world reflection
Below is code for a reflection map that takes the normal map into account - eg , it obeys all the bumpy bits. Notice - the reflection map is taken in as a CUBE type, in all caps & uses a samplerCUBE type in the subshader variable definition. The Normal map is taken in as a 2D, just like a standard texture map - but in the Properties, we initialise it to "bump". We use the normal map by calling the UnpackNormal function - this converts the rgb values of the normal map (we get those by using tex2D) into the xyz vectors that the normals need.
We're sticking the reflection map into the output Emission for now. World Reflection is actually based on the normal of the object - the polynormals are projected outwards and they hit a cubemap - the colour of the cubemap at this point is then returned as the world reflection - HOWEVER - because we are modifying the normals using our bump/normal map this is gonna get weird. Unity will actually freak out - UNLESS - we add the INTERNAL_DATA flag to the worldRefl in the Input struct. It's kinda letting us modify normals & not have the world reflection calculation freak out. If we use the WorldNormal & are modifying the o.normal, we need to use INTERNAL_DATA there too.
Back to the WorldRefl- we're using it in the emission for now. We call texCUBE and use WorldReflection(IN, o.Normal) to take into account the normals. This is a little different to the simpler use case of texCUBE(_myRefl, IN.worldRefl);
shader "Dave/bumpedEnviro"
{
Properties{
_myAlbedo("albedo",2D) = "grey"{}
_myRefl("reflection",CUBE) = "white"{}
_myNormal("normal map",2D) = "bump"{}
_mySlider("normal intensity",Range(0,2)) = 1
_emissionSlider("emission",Range(0,1))=1
}
SubShader{
CGPROGRAM
#pragma surface surf Lambert
sampler2D _myAlbedo;
sampler2D _myNormal;
samplerCUBE _myRefl;
half _mySlider;
half _emissionSlider;
struct Input {
float2 uv_myAlbedo;
float2 uv_myNormal;
float3 worldRefl; INTERNAL_DATA
};
void surf(Input IN, inout SurfaceOutput o) {
o.Albedo = tex2D(_myAlbedo, IN.uv_myAlbedo);
o.Normal = UnpackNormal(tex2D(_myNormal, IN.uv_myNormal));
o.Normal *= float3(_mySlider, _mySlider, 1);
o.Emission = texCUBE(_myRefl, WorldReflectionVector(IN, o.Normal)).rgb;
o.Emission *= _emissionSlider;
}
ENDCG
}
Fallback "Diffuse"
}
Comments
Post a Comment