多层融合地形Shader

一、多层融合地形Shader介绍

所谓多层融合地形Shader,即多层地形效果过渡融合的Shader,比如黄色的土地上,融合淡绿色的草地,然后再点缀红色的花,这样就是三层效果融合。虽然,该效果常用在地形上,但是并不局限于地形,普通的场景模型等照样可以使用这样方式融合多层效果,比如静态的雪地,就可以使用该技术达到很精细的效果。
对于单独的一层效果,可以是PBR也可以是BlingPhong,甚至可以是Matcap。关键在于,如何将多层效果比较自然得融合起来。
类似下面的地形Shader效果:

可以看出该Shader,支持权重混合和高度混合,同时支持四层融合。

二、多层融合效果的基本实现思路

概况的说,一句话可以总结:对着色模型或者说光照模型的输入进行多层混合。比如,PBR的基本输入是基础色、法线、金属度、粗糙度、AO;BlingPhong的基本输入是基础色、法线、AO。其它的着色模型也是类似的思路,同样可以对Matcap和卡通渲染进行多层融合。

二、权重融合


权重融合的实现方式比较简单,用一个权重贴图控制四层的权重,同时提供数值缩放。这样,第一层的权重就是权重贴图的R通道乘以第一层的缩放(First Layer Weight),以此类推。然后,用得到的四个权重,应用到四层的基本输入上做加权平均,得到最终的输入。

三、高度融合

权重融合的缺点是边界过渡比较生硬,无法实现平滑的过渡。而高度融合是解决过渡生硬的一个好的方式。效果和思路可以参考文章:基于高度的纹理混合shader
基本思路:

  1. 求四层最大高度。
  2. 用最大权重减去过渡因子作为开始高度。
  3. 每一层的高度减去开始高度作为该层权重。
  4. 然后进行四层加权混合。
    具体代码可以参考下面函数:
    1
    2
    3
    4
    5
    6
    7
    8
    9
    half LayerHeightBlend(half4 height, half input1, half input2, half input3, half input4)
    {
    half heightStart = max(max(height.r, height.g), max(height.b, height.a)) - _HeightBlendFactor;
    half b1 = max(height.r - heightStart, 0);
    half b2 = max(height.g - heightStart, 0);
    half b3 = max(height.b - heightStart, 0);
    half b4 = max(height.a - heightStart, 0);
    return max((input1 * b1 + input2 * b2 + input3 * b3 + input4 * b4) / (b1 + b2 + b3 + b4), 0.0001);
    }
    效果对比:

第二个效果与第一个效果对比,有明显的过渡区域,而且过渡区域是有明显融合的,而单纯的权重融合只是效果的加权平均。

四、融合控制贴图编辑工具

为了方便美术所见即所得的编辑和预览最终的混合效果,那么实现一个编辑器工具,方便美术用笔刷实时来修改效果,同时在Unity编辑器内预览最终效果是非常有意义的,可以显著提高生产效率。
类似如下工具:

该工具的功能并不复杂,读取地形材质的设置,比如控制贴图信息和四层的贴图信息,提供笔刷功能,在Scene窗口去刷模型,壁画操作的结果再写回控制贴图。由于当前模型使用的正是笔刷引用的地形材质和控制贴图,因此就可以实时预览最终的渲染效果。
网上应该也有类似的插件或者开源代码。这里只是抛砖引玉,具体代码不会提供。