Unity3d深度图

文章目录

深度图原理

移步:深度测试,这篇文章讲了深度图的概念。

深度重建

深度图是经过NDC坐标空间后渲染出来的,深度存储时不是线性的,因此需要进行重建。幸运的是,Unity3D ShaderLab中提供了这个函数接口。

// vert
o.vertex = UnityObjectToClipPos(v.vertex);	// mvp变换
o.screenPos = ComputeScreenPos(o.vertex);	// 获取屏幕空间坐标
COMPUTE_EYEDEPTH(o.screenPos.z);			// 获取模型在View空间的z

// frag
float screenZ = LinearEyeDepth(SAMPLE_DEPTH_TEXTURE_PROJ(_CameraDepthTexture, UNITY_PROJ_COORD(i.screenPos)));
float depth = Linear01Depth(SAMPLE_DEPTH_TEXTURE_PROJ(_CameraDepthTexture, UNITY_PROJ_COORD(i.screenPos)));

深度写入

注意:RenderQueue <= 2450

Pass {
    Name "ShadowCaster"
    Tags { "LightMode" = "ShadowCaster" }

    ZWrite On ZTest LEqual Cull Off

    CGPROGRAM
    #pragma vertex vert
    #pragma fragment frag
    #pragma target 2.0
    #pragma multi_compile_shadowcaster
    #include "UnityCG.cginc"

    struct v2f {
        V2F_SHADOW_CASTER;
        UNITY_VERTEX_OUTPUT_STEREO
    };

    v2f vert(appdata_base v)
    {
        v2f o;
        UNITY_SETUP_INSTANCE_ID(v);
        UNITY_INITIALIZE_VERTEX_OUTPUT_STEREO(o);
        TRANSFER_SHADOW_CASTER_NORMALOFFSET(o)
        return o;
    }

    float4 frag(v2f i) : SV_Target
    {
        SHADOW_CASTER_FRAGMENT(i)
    }
    ENDCG
}

一些遇到的坑

  1. 深度图 != 深度缓冲,深度图和深度缓存不同,zwrite off可以关闭写入深度缓存,但还会写入深度图。_CameraDepthTexture本身是渲染得到的屏幕纹理,和zwrite并没有直接联系
上一篇:bzoj4665 小w的喜糖(dp+容斥)


下一篇:A protocol for recording provenance in service-oriented Grids(面向服务网格中记录起源的协议论文阅读)