一、光照计算
//宏定义判断光源类型
#if defined(DIRECTIONAL)
float3 lDir = normalize(_WorldSpaceLightPos0.xyz);
float attuention = 1.0;
#elif defined(POINT)
float3 lDir = normalize(_WorldSpaceLightPos0.xyz - i.pos_WS);
float distance = length(_WorldSpaceLightPos0.xyz - i.pos_WS);
//获取点光源范围值
float range = 1.0 / unity_WorldToLight[0][0];
//获取光源衰减值
float attuention = saturate((range - distance) / range);
#endif
Pass1
{
//受光标签
Tags{"LightMode" = "ForwardBase"}
//告诉渲染管线这个pass以forwardbase渲染
#pragma multi_compile_fwdbase
//Unity光照函数库
#include "AutoLight.cginc"
}
Pass2
{
//受光标签
Tags{"LightMode" = "ForwardAdd"}
//增加混合模式
Blend One One
//告诉渲染管线这个pass以forwardadd渲染
#pragma multi_compile_fwdadd
//Unity光照函数库
#include "AutoLight.cginc"
}
二、法线贴图
法线:即模型顶点法线;
切线:根据模型uv的u方向获得(由引擎生成);
副法线:法线叉乘切线获得;
法线贴图在干什么?→ 将顶点法线转化为像素法线
//顶点操作 → 获取顶点法线、切线、副法线
v2f vert (appdata v)
{
o.normal_Dir = normalize(mul(float4(v.normal,0.0), unity_ObjectToWorld).xyz);
o.tangent_Dir = normalize(mul(unity_ObjectToWorld, v.tangent).xyz);
//v.tangent.w:tangent的第四个分量,为了处理不同平台下的兼容性问题
o.binormal_Dir = cross(o.normal_Dir, o.tangent_Dir) * v.tangent.w;
}
//片元操作 → 顶点法线转像素法线
fixed4 frag (v2f i) : SV_Target
{
float4 normal_Map = tex2D(_NormalMap, i.uv);
//对法线数据进行解码,将压缩的法线数据从[0,1]恢复成[-1,1]
float3 normal_data = UnpackNormal(normal_Map);
//得到逐像素法线,若想加强法线强度,则在xy方向上乘上强度值
//写法1
nDir = normalize(tDir * normal_data.x + bDir * normal_data.y + nDir * normal_data.z);
//写法2 → TBN变换
float3x3 TBN = float3x3(tDir, bDir, nDir);
nDir = normalize(mul(normal_data.xyz, TBN));
}
|