目录
基础:
兰伯特公式:
广义上的半兰伯特光照模型公式:
绝大多数情况下的半兰伯特光照模型公式:
纯实现:
一、兰伯特模型
二、半兰伯特模型
Shader "MyShader/Lambert"
{
SubShader
{
Pass
{
Tags{"LightMode"="ForwardBase"}
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include "UnityCG.cginc"
struct vertexInput
{
float4 vertex:POSITION;
float3 normal:NORMAL;
};
struct vertexOutput
{
float4 pos:SV_POSITION;
float3 worldNormal:TEXCOORD0;
};
vertexOutput vert(vertexInput v)
{
vertexOutput o=(vertexOutput)0;
o.pos=UnityObjectToClipPos(v.vertex);
o.worldNormal=UnityObjectToWorldNormal(v.normal);
return o;
}
float4 frag(vertexOutput i):SV_TARGET
{
float3 worldNormal=i.worldNormal;
float3 worldLightDir=_WorldSpaceLightPos0.xyz;
float lambert=saturate(dot(worldNormal,worldLightDir));
return float4(lambert,lambert,lambert,1.0);
}
ENDCG
}
}
}
Shader "MyShader/HalfLambert_2"
{
SubShader
{
Pass
{
Tags{"LightMode"="ForwardBase"}
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include "UnityCG.cginc"
struct vertexInput
{
float4 vertex:POSITION;
float3 normal:Normal;
};
struct vertexOutput
{
float4 pos:SV_POSITION;
float3 worldNormal:TEXCOORD0;
float3 worldLightDir:TEXCOORD1;
};
vertexOutput vert(vertexInput v)
{
vertexOutput o=(vertexOutput)0;
o.pos=UnityObjectToClipPos(v.vertex);
o.worldNormal=UnityObjectToWorldNormal(v.normal);
o.worldLightDir=_WorldSpaceLightPos0.xyz;
return o;
}
float4 frag(vertexOutput i):SV_TARGET
{
float halfLambert =saturate(dot(i.worldNormal,i.worldLightDir)*0.5+0.5);
return float4(halfLambert,halfLambert,halfLambert,1.0);
}
ENDCG
}
}
}