Unity Stencil模版测试的简单应用

在Unity中,Stencil Buffer(模板缓冲区)是一种图形渲染技术,用于控制在渲染过程中绘制像素的方式。Stencil Buffer通常用于实现一些高级的渲染效果,如轮廓描边、遮罩、投影阴影、镜面反射等。它允许您在绘制像素时根据特定条件进行控制,而不仅仅是基于颜色或深度。

Stencil Buffer实际上是一个与屏幕像素数量相同的附加缓冲区,每个像素都有一个对应的Stencil值。Stencil值可以被用来在渲染中的不同阶段进行检查和修改。通常情况下,Stencil值在绘制对象时被设置,然后在随后的绘制步骤中用来决定哪些像素应该被绘制,哪些像素应该被忽略,或者以不同的方式处理。

本文将实现一个有趣的立方体,如图:

可以理解为,立方体的每个面都有自己的世界,每面只显示自己世界里的东西。

比如第一张图右边的正方体和球体,只在左侧的面对应的“世界”中存在,在另一个面中就不会显示。

实现原理

我们先来看Unity中对一个材质的Stencil属性的示例:

Stencil
{
    Ref 1
    Comp Always
    Pass Replace
}

在我们的屏幕上,每一个像素都有自己的stencil值,默认是0。在实际应用中,我们可以通过stencil test来改变像素的stencil值,也可以通过stencil test来剔除一些像素的渲染。

图中就是一个改变像素stencil值的方法。

Ref:代表进行stencil测试时,与当前像素的stencil值进行比较的值。如这个实例代码中,我们的像素的stencil值会在深度测试时与1进行比较。

comp:代表比较过后什么情况可以通过。这里设为Always,代表所有情况都可以通过。如果不通过,则该像素不会被渲染

Pass: 通过之后做什么。这里填的是Replace,代表通过之后,用Ref的值替换当前缓冲的值。

所以我们可以得出这代码的意义:进行stencil test,结果总是通过。通过之后,就将该像素的stencil替换成ref里给出的值1。总结来说,就是对于当前模型覆盖的所有像素,都把像素中存的stencil值替换为1。

注意,stencil test是在深度测试之前进行的。如果stencil没通过,那么后面的渲染流程不会执行。

那么,利用这些原理,我们就可以实现这个效果了。

实现过程

在场景里创建两个plane,写一个shader如下

Shader "Examples/StencilAvatar"
{
    Properties
    {
        [IntRange] _StencilID("Stencil ID", Range(0, 255)) = 0
    }
    SubShader
    {
        Tags 
        {             
            "RenderType"="Geometry" 
            "RenderPipeline" = "UniversalPipeline"
            "Queue" = "Geometry"
        }
        
        Pass
        {
            //Blend Zero One
            ZWrite Off

            Stencil
            {
                Ref [_StencilID]
                Comp Always
                Pass Replace
                Fail Keep
            }
        }
    }
}

我们运用之前说的方法将所有这个模型覆盖的像素对应的stencil都替换成给出的_stencilID属性。stencil的值只有八位存储大小,所以范围是0到255。

然后创建2个材质,shader替换成我们写的这个shader。然后把两个shader的stencilID分别设为1,2。

 把这两个材质赋给两个plane上。

创建两个layer,叫stencil1, stencil2 。

在两个plane后边分别放一堆物体。把他们的layer设为我们新建的这两个。

然后打开你的renderer设置,通常在你project里的settings文件夹下。

在Filtering的两个选项中,把新建的两个层级都取消勾选。最后看到它们变成Mixed。此时你应该在场景里就看不到那些物体了。

 

点最下面的 Add Render Feature,选render object。

按图片这样设置。 在创建一个一样的,命名为Stencil2,Stencil的Value设为2,其他一样。

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值