OpenGL Test
Opengl中测试共分为几个阶段 裁剪 apha 测试 模板测试 和深度测试,OpenGL可以为像素保存颜色、深度值和模板值,利用混合实现透明时,像素颜色不发生变化,但深度值则会可能变化,模板值受glStencilFunc函数中第三个参数影响;利用测试操作实现透明时,像素颜色不发生变化,深度值也不发生变化。
Unity Alphatest
unity 中通过 AlphaTest comparison AlphaValue 来进行alpha值的比较来丢弃一些alpha值 不符合的像素。比如我们在渲染树叶的时候
着由于不透明物体和透明物体共存,需要用alphatest来进行渲染,为了防止近处的物体遮挡住远方的物体我们需要关闭深度写入来进行
alpha混合。但由于在进行alphtest时候 会不可避免的对边缘产生比较生硬(alpha测试对边缘像素过度产生影响)。因此通常的做法是
采用两个通道 并设定一个alpha临界值第一个通道只渲染alpha值大于这个临界值的物体(即半透明物体)然后在第二个通道中渲染半透明
物体,关闭深度写入,为了不重复渲染在第一个通道中渲染过的物体需要开启ztest lequal,同时采用blend混合的方式来渲染。详细官方
文档
基于以上渲染原因出现了
Alpha-to-coverage AlphaToMask On, at 4xMSAA
工作在msaa上,主要在大部分透明或者不透明只有一小部分透明的物体上,比如树叶草地等。
inside SubShaderTags { "Queue"="AlphaTest" "RenderType"="TransparentCutout" "IgnoreProjector"="True" }
inside PassAlphaToMask On
下面是关于unity文档中有关透明物体渲染的其他方法:
AlphaTest本质是渲染了一个不透明物体,而不透明物体是渲染顺序无关的,但是硬边明显,而AlphaBlend本质是渲染一个透明物体,
而透明物体虽然边缘平滑但是渲染顺序相关。
Alpha blending, alpha testing, alpha-to-coverage 引用https://docs.unity3d.com/Manual/SL-Blend.html
Alpha blending
这就意味着 物体就被认为是半透明物体会关闭深度写入,因此不能使用一些渲染得到特性比如 后处理shader不能接受光照,凹面的或者像素重叠就会产生性能问题。
shader通常是这样的
SubShader :Tags { "Queue"="Transparent" "RenderType"="Transparent" "IgnoreProjector"="True" }
Pass: ZWrite OffBlend SrcAlpha OneMinusSrcAlpha
Alpha testing/cutout
在像素着色器 中使用 hlsl特征clip() ,一个像素会根据alpha值会被剔除掉,这样就没有渲染顺序问题了。这也意味着所有的像素都会被认为是全透明或者全部不透明。shader通常是这样的
//inside SubShader
Tags { "Queue"="AlphaTest" "RenderType"="TransparentCutout" "IgnoreProjector"="True" }
// inside CGPROGRAM in the fragment Shader:
clip(textureColor.a - alphaCutoffValue);
参考: https://blog.csdn.net/Crazyjumper/article/details/196856
https://docs.unity3d.com/Manual/SL-AlphaTest.html