【Unity】HDRPでカスタムデプスバッファを使って壁の後ろのキャラを描画する #2

投稿者: | 2023-12-22

HDRPでカスタムデプスバッファを使って壁の後ろのキャラを描画する #1では、歩くときに地面に少し埋まる部分が常にハイライトされてしまいました。

カメラ空間の位置を計算し、閾値を使って改良してみました。

カメラ空間位置のZ座標を比較

まず、2つの深度値からワールド位置を計算しました。

        float2 uv = posInput.positionNDC.xy;

        // 深度値からワールド空間位置を取得
        float3 worldPos = ComputeWorldSpacePosition(uv, depth, UNITY_MATRIX_I_VP);
        float3 worldPosCustomDepth = ComputeWorldSpacePosition(uv, customDepth, UNITY_MATRIX_I_VP);

これをビュー変換します。

        // ビュー空間位置に変換
        float3 viewPos = mul(UNITY_MATRIX_V, worldPos);
        float3 viewPosCustomDepth = mul(UNITY_MATRIX_V, worldPosCustomDepth);

Z座標の距離を比較して描画する色を決定します。

        // 距離を計算
        float zAxisDistance = viewPos.z - viewPosCustomDepth.z;

        // 遮蔽されていない部分
        if ((zAxisDistance <= _Threshold) || customDepth <= 0)
        {
            // カメラカラーバッファを読み込む
            return float4(CustomPassLoadCameraColor(varyings.positionCS.xy, 0), 1);
        }
        // 遮蔽されている部分
        else
        {
            // 白を描画
            return float4(1, 1, 1, 1);   
        }

角度がきついとき

閾値をかなり上げても、地面に近い高さにカメラがあると少しハイライトが見えてしまいます。

見える
見えない

もう少し改良が必要かもしれません。

深度値を比較

深度値をそのまま比較した場合、距離によって見え方が変わったり、表示が安定しなくなりました。

        float depthDifference = abs(customDepth - depth);

        // 遮蔽されていない部分
        if ((depthDifference <= _Threshold) || customDepth <= 0)
        {
            // カメラカラーバッファを読み込む
            return float4(CustomPassLoadCameraColor(varyings.positionCS.xy, 0), 1);
        }
表示が不安定
参考:
https://docs.unity3d.com/ja/Packages/com.unity.render-pipelines.universal@14.0/manual/writing-shaders-urp-reconstruct-world-position.html

コメントを残す

メールアドレスが公開されることはありません。