GameTech/URP 渲染实战
源码 / shaders/Ch29/OverdrawHeatmap.glsl
shaders/Ch29/OverdrawHeatmap.glsl
// 案例 29.5:把 Overdraw 计数映射成热度图(全屏 Pass,源纹理是计数 RT)。(GLSL 版,对应 Ch29/OverdrawHeatmap.shader)
// 色阶:0 黑 → 1 深蓝 → 2 青 → 3 绿 → 4 黄 → 6 橙 → 8 红 → 12+ 白
Shader "Cookbook/Ch29/OverdrawHeatmap"
{
    SubShader
    {
        Tags { "RenderType"="Opaque" "RenderPipeline"="UniversalPipeline" }
        ZWrite Off ZTest Always Cull Off Blend Off
        Pass
        {
            Name "Heatmap"
            GLSLPROGRAM
            uniform float _MaxCount;

            // Blit.hlsl 的 Vert:全屏三角形,_BlitTexture 由引擎提供
            VARYING vec2 texcoord;
            #ifdef VERTEX
            void main()
            {
                vec2 p = vec2((gl_VertexID << 1) & 2, gl_VertexID & 2);
                texcoord = p * _BlitScaleBias.xy + _BlitScaleBias.zw;
                gl_Position = vec4(p * 2.0 - 1.0, 0.0, 1.0);
            }
            #endif

            #ifdef FRAGMENT
            vec3 HeatRamp(float n)
            {
                const vec3 c[8] = vec3[8](
                    vec3(0, 0, 0), vec3(0.05, 0.1, 0.55), vec3(0.0, 0.6, 0.8), vec3(0.1, 0.75, 0.2),
                    vec3(0.95, 0.9, 0.1), vec3(1.0, 0.5, 0.05), vec3(0.9, 0.08, 0.05), vec3(1, 1, 1));
                const float k[8] = float[8](0.0, 1.0, 2.0, 3.0, 4.0, 6.0, 8.0, 12.0);
                n = min(n, k[7] * _MaxCount / 12.0);
                vec3 col = c[7];
                for (int i = 0; i < 7; i++)
                {
                    float a = k[i] * _MaxCount / 12.0, b = k[i + 1] * _MaxCount / 12.0;
                    if (n >= a && n < b) { col = mix(c[i], c[i + 1], (n - a) / (b - a)); break; }
                }
                return col;
            }

            void main()
            {
                // HLSL 用 sampler_PointClamp 点采样;GLSL 不能按调用选采样器,用 texelFetch 取整数像素
                float count = texelFetch(_BlitTexture, ivec2(texcoord * _BlitTexture_TexelSize.zw), 0).r;
                fragColor = vec4(HeatRamp(count), 1.0);
            }
            #endif
            ENDGLSL
        }
    }
}