Unity-Chan Toon Shader卡通渲染学习

(本文记录一下从0-1复刻UTS2,持续更新中)

一、UTS2介绍

Unity-Chan Toon Shader 2.0 (UTS2) 是一款用于图像和视频的卡通着色器,旨在满足从事卡通着色 3DCG 动画的创作者的需求。

UTS2开源项目地址:GitHub - unity3d-jp/UnityChanToonShaderVer2_Project: UnityChanToonShaderVer2 Project / v.2.0.9 Release

二、从0-1复刻UTS2

(1)3 Basic Colors

UTS2的漫反射部分主要有三个层组成,分别是基本颜色、第一阴影色和第二阴影色,分别对应着美术理论中的白、灰、黑。

基本颜色主要是对受光面着色,也就是物体的亮部:

 

第一阴影色对受光面到背光面之间过渡的阶段着色:

 

第二阴影色对背光面着色:

然后是几个参数可以调节这三个颜色的范围以及羽化程度:

BaseColor Step用于调节第一阴影色的范围:

Base/Shade Feather用于调节第一阴影色的羽化程度:

 

ShadeColor Step用于调节第二阴影色的范围:

1st/2nd_Shades Feather用于调节第二阴影色的羽化程度:

 

简单实现代码:

float4 baseMap_var = tex2D(_BaseMap, i.uv);
float3 baseMap_RGB = baseMap_var * _BaseMapCol; //基本色
float4 _1st_ShadowMap_var = lerp(tex2D(_1st_ShadowMap, i.uv), baseMap_var, _Use_BaseAs1st);
float3 _1st_ShadowMap_RGB = _1st_ShadowMap_var * _1st_ShadowMapCol; //第一阴影色
float4 _2nd_ShadowMap_var = lerp(tex2D(_2nd_ShadowMap, i.uv), _1st_ShadowMap_var, _Use_1stAs2nd);
float3 _2nd_ShadowMap_RGB = _2nd_ShadowMap_var * _2nd_ShadowMapCol; //第二阴影色
float halfLambert = 0.5 * dot(setNormalDir, lightDir) + 0.5; //半兰伯特模型
float base_1stShadow_mask = saturate(1.0 - (halfLambert - (_BaseColStep - _BaseShadeFeather)) / _BaseShadeFeather); //基本色到第一阴影色的插值参数
float _1st_2ndShadow_mask = saturate(1.0 - (halfLambert - (_ShadeColStep - _1st2nd_ShadesFeather)) / _1st2nd_ShadesFeather); //第一阴影色到第二阴影色的插值参数
float3 diffuse = lerp(baseMap_RGB, lerp(_1st_ShadowMap_RGB, _2nd_ShadowMap_RGB, _1st_2ndShadow_mask), base_1stShadow_mask); //插值实现颜色过渡

主要使用了两个lerp实现颜色过渡。

(2)High Color

1.HighColor Tex用于指定高光贴图;

2.HighColor Power控制高光强度;

3.Specular Mode决定是否使用正常的高光效果;

启用:

关闭:

这种高光边界分明,且颜色缺少渐变。

4.Color Blend Mode决定高光的混合方式;

Additive方式使颜色更亮,上面两者高光形式都可以使用:

Multiply方式使颜色更暗,只能用于第二种高光形式:

5.HighColor Mask用于指定高光遮罩,决定高光范围以及大小;HighColor Mask Level调节遮罩强度。

简单实现代码:

float4 highColorTex_var = tex2D(_HighColorTex, i.uv); //高光贴图
float4 highColorMask_var = tex2D(_HighColorMask, i.uv); //高光遮罩贴图
float3 halfDir = normalize(lightDir + viewDir); //半程向量
float specular = 0.5 * dot(halfDir, lerp(i.nDirWS, setNormalDir, _Is_NormalMapToHighColor)) + 0.5;
float tweakHighColorMask_var = saturate(highColorMask_var.g + _HighColorMaskLevel) * lerp(1.0 - step(specular, 1.0 - pow(_HighColorPower, 5)), pow(specular, exp2(lerp(11, 1, _HighColorPower))), _Is_SpecularToHighColor); //两种高光形式
float3 specualrCol = (highColorTex_var * _HighColor * tweakHighColorMask_var).rgb;
diffuseCol = lerp(saturate(diffuseCol - tweakHighColorMask_var), diffuseCol, lerp(_Is_BlendAddToHighColor, 1, _Is_SpecularToHighColor)); //和漫反射的混合方式

(3)Normal Map

Normal Map的使用不多说,重点说一下用不同按钮实现对法线是否影响不同光效果的控制:

3 Basic Color按钮

High Color按钮

主要使用Lerp函数来决定要不要使用法线贴图。

参考:游戏诞生之日09 - 美术篇 卡通渲染着色器 UTS2 - 知乎 (zhihu.com)

猜你喜欢

转载自blog.csdn.net/qq_63133691/article/details/131376033