ShaderLab
ShaderLab模块将持续更新,ShaderLab中将会陆续更新较为常见的Unity Shader,比如常见于游戏中的部分特效,常见于三维可视化的特效Shader
- 目前打算每周更新多个,两个?三个?四个?都有可能
- 目前打算每十个为一组,直接根据顺序进行分组
利用这个ShaderLab模块来记录自己的Shader学习过程并且也有给学习Shader的同学一些练习的内容。本文不讲解shader的基础语法,建议有一定shader基础的同学学习
目录
- 支持透明的边缘发光着色器(SupportAlphaRim.shader)
1.支持透明的边缘发光
效果图
材质球
实际效果
简要原理
- 支持透明,需要将ZWrite设置为OFF,然后开启Blend,进行混合操作
- 计算漫反射利用法线和视角方向点积值乘以颜色并混合环境光。
- 这里为什么没有利用传统的法线和灯光方向,因为利用灯光的话就是产生背面阴影,当然你也可以使用半柏林光照让背面也产生一定的光强,根据需要自行修改。
- 计算边缘光,利用法线和视角方向的点积角度取反,乘以边缘色得到边缘光
- 混合漫反射和边缘光,利用float值控制输出颜色的alpha值,以实现透明控制
Shader代码
Shader "Custom/SupportAlphaRim"
{
Properties
{
_Color("Main Color",Color) = (0.6,0.6,0.6,1)
_AlphaRange("Alpha Range",Range(0,1)) = 0
_RimColor("Rim Color",Color) = (1,1,1,1)
}
SubShader
{
Tags{"RenderType"="Transparent" "Queue"="Transparent" }
LOD 200
Pass
{
Tags{"LightMode"="ForwardBase"}
Cull back
Blend SrcAlpha OneMinusSrcAlpha
ZWrite OFF
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include "unitycg.cginc"
#include "unitylightingcommon.cginc"
struct a2v
{
float4 vertex : POSITION;
float3 normal : NORMAL;
};
struct v2f
{
float4 pos : SV_POSITION;
float3 normalDir : Texcoord0;
float3 worldPos : TEXCOORD1;
};
fixed4 _Color;
float _AlphaRange;
fixed4 _RimColor;
v2f vert( a2v i )
{
v2f o;
// 转化顶点位置
o.pos = mul(UNITY_MATRIX_MVP,i.vertex);
// 获取世界空间法线向量
o.normalDir = mul(float4(i.normal,0),_World2Object).xyz;
// 获取世界坐标系顶点位置
o.worldPos = mul(_Object2World,i.vertex);
return o;
}
fixed4 frag( v2f v ):COLOR
{
// 法线标准化
float3 normal = normalize(v.normalDir);
// 视角方向标准化
float3 viewDir = normalize(_WorldSpaceCameraPos.xyz - v.worldPos.xyz);
// 点积
float NdotV = saturate(dot(normal,viewDir));
// 漫反射
fixed3 diffuse = NdotV *_Color + UNITY_LIGHTMODEL_AMBIENT.rgb;
float alpha = 1 - NdotV;
// 边缘色
fixed3 rim = _RimColor *alpha;
// 混合输出
return fixed4(diffuse + rim ,alpha * (1-_AlphaRange)+_AlphaRange);
}
ENDCG
}
}
// 如果需要阴影在此回滚 不需要注释掉即可
Fallback "Diffuse"
}
结尾
- 此模块持续更新,如果你想学习更多Shader的实现,欢迎关注我的博客