GrabPass は、フレームバッファのコンテンツをテクスチャに取り込む特別なタイプのパスを作成するコマンドです。このテクスチャを後続のパスで使用して、画像ベースの高度な効果を実現できます。
このコマンドは、CPU と GPU の両方のフレームタイムを大幅に増加させます。高速なプロトタイピング以外のためにこのコマンドを使用することは避け、他の方法で効果を得るようにしてください。このコマンドを使用する場合は、このコマンドの使用を減らすか、該当する場合は画面を名前付きテクスチャに取り込む署名を使用して、画面の取り込み操作の回数をできる限り減らすようにしてください。
| 機能名 | ビルトインレンダーパイプライン | ユニバーサルレンダーパイプライン (URP) | HD レンダーパイプライン (HDRP) | カスタム SRP | 
|---|---|---|---|---|
| GrabPass | はい | なし | なし | なし | 
このコマンドは SubShader ブロックで使用します。
GrabPass はフレームバッファに対してのみ動作します。このコマンドを使って、他のレンダリングターゲットや深度バッファなどのコンテンツを取得することはできません。
この 2 つの異なるシグネチャは機能が異なり、パフォーマンスにも影響も異なります。名前付きのテクスチャを使用すると、スクリーンの取り込み操作が大幅に少なくなるため、リソースを大量に消費するこのコマンドの影響を軽減することができます。
| シグネチャ | 機能 | 
|---|---|
| GrabPass { } | フレームバッファのコンテンツをテクスチャに取得し、同じサブシェーダーの後続のパスで使用できます。 名前 _ GrabTexture を使ってテクスチャを参照します。 このシグネチャを使用すると、Unity はこのコマンドを含むバッチをレンダリングするたびに画面を取得します。つまり、Unity はフレームごとに複数回、つまりバッチごとに 1 回、画面を取り込むことができます。 | 
| GrabPass { "ExampleTextureName" } | フレームバッファのコンテンツをテクスチャに取得し、同じフレームの複数のサブシェーダーの後続のパスで使用できます。 指定した名前を使ってテクスチャを参照します。 このシグネチャを使用すると、Unity はフレーム内で初めて画面を取得し、指定したテクスチャ名でこのコマンドを含むバッチをレンダリングします。 | 
このビルトインレンダーパイプラインの例では、GrabPass を使って、レンダーターゲットの色を反転させます。これは、この効果を得るための効率的な方法ではなく、GrabPass の使用方法を説明するためです。同じ効果は、反転ブレンドモードを使用してより効率的に行えます。
Shader "GrabPassInvert"
{
    SubShader
    {
        // すべての不透明なジオメトリの後に描画します
        Tags { "Queue" = "Transparent" }
        // オブジェクトの背後にある画面を _BackgroundTexture に取り込みます
        GrabPass
        {
            "_BackgroundTexture"
        }
        // 上で生成されたテクスチャでオブジェクトをレンダリングし、色を反転します
        Pass
        {
            CGPROGRAM
            #pragma vertex vert
            #pragma fragment frag
            #include "UnityCG.cginc"
            struct v2f
            {
                float4 grabPos : TEXCOORD0;
                float4 pos : SV_POSITION;
            };
            v2f vert(appdata_base v) {
                v2f o;
                // UnityCG.cginc の UnityObjectToClipPos を使用して、
                //頂点のクリップスペースを計算します
                o.pos = UnityObjectToClipPos(v.vertex);
                // UnityCG.cginc の ComputeGrabScreenPos 関数を使用して、
                //正しいテクスチャ座標を取得します
                o.grabPos = ComputeGrabScreenPos(o.pos);
                return o;
            }
            sampler2D _BackgroundTexture;
            half4 frag(v2f i) : SV_Target
            {
                half4 bgcolor = tex2Dproj(_BackgroundTexture, i.grabPos);
                return 1 - bgcolor;
            }
            ENDCG
        }
    }
}