source: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/shaders/deferred.cg @ 3136

Revision 3136, 7.5 KB checked in by mattausch, 16 years ago (diff)

fixed antialiasing, but ssao not working at that point (depth)

RevLine 
[2966]1#include "../shaderenv.h"
2
3
[2876]4struct fragment
5{
6         // normalized screen position
7        float4 pos: WPOS;
[3009]8        float2 texCoord: TEXCOORD0;
9        float3 view: TEXCOORD1;
[2876]10};
11
12
13struct pixel
14{
15        float4 color: COLOR0;
16};
17
18
[2944]19float2 myreflect(float2 pt, float2 n)
20{
21        // distance to plane
22        float d = dot(n, pt);
23        // reflect around plane
24        float2 rpt = pt - d * 2.0f * n;
25
26        return rpt;
27}
28
29
[2876]30/** function for standard deferred shading
31*/
32float4 shade(fragment IN,
33                         uniform float4 color,
34                         uniform float3 normal,
[2952]35                         float3 lightDir)
[2876]36{
[2954]37        // diffuse intensity
38        const float angle = saturate(dot(normal, lightDir));
39       
40        float4 lightDiffuse = glstate.light[0].diffuse;
41        float4 diffuse = angle * lightDiffuse;
[2876]42
43        // global ambient
[2954]44        const float4 ambient = glstate.light[0].ambient;
45       
[2968]46        float4 outColor;
[2967]47
[3005]48        // hack: prevent shading the sky
[3009]49        if (color.w > 1e19f) outColor = color;
[2974]50        else outColor = (ambient + diffuse) * color;
[2968]51
52        return outColor;
[2876]53}
54
55
56
57/** The mrt shader for standard rendering
58*/
[2874]59pixel main(fragment IN,
60                   uniform sampler2D colors,
[2952]61                   uniform sampler2D normals,
[2991]62                   uniform float3 lightDir
[2874]63                   )
64{
65        pixel OUT;
66
[3009]67        float4 norm = tex2D(normals, IN.texCoord);
68        float4 color = tex2Dlod(colors, float4(IN.texCoord, 0, 0));
69       
[2945]70        float3 normal = normalize(norm.xyz);
[3089]71        float4 col = shade(IN, color, normal, lightDir);
[2874]72       
[3099]73        OUT.color = col;
74        //OUT.color.xyz = normal * 0.5f + 0.5f;
[3095]75        // store scaled view vector so wie don't have to normalize for e.g., ssao
[3136]76        OUT.color.w = color.w;// / length(IN.view);
[3098]77       
[2874]78        return OUT;
[2876]79}
[2892]80
[2944]81
82float CalcShadowTerm(fragment IN,
83                                         uniform sampler2D shadowMap,
[3025]84                                         uniform float scale,
[2944]85                                         uniform float2 lightSpacePos,
[2952]86                                         uniform float depth,
[2966]87                                         uniform float2 samples[NUM_PCF_TABS],
[3025]88                                         uniform float weights[NUM_PCF_TABS],
[2944]89                                         uniform sampler2D noiseTexture
90                                         )
91{
[2954]92        //float shadowDepth = tex2D(shadowMap, lightSpacePos).x;
93        //return step(depth, shadowDepth);
[2944]94
[3025]95        float total_d = .0f;
96        float total_w = .0f;
97
[2966]98        for (int i = 0; i < NUM_PCF_TABS; ++ i)
[2944]99        {
100                const float2 offset = samples[i];
[3025]101                const float w = weights[i];
[2944]102
103#if 1
104                ////////////////////
105                //-- add random noise: reflect around random normal vector (warning: slow!)
106
[3009]107                float2 mynoise = tex2D(noiseTexture, IN.texCoord).xy;
[2944]108                const float2 offsetTransformed = myreflect(offset, mynoise);
109#else
110                const float2 offsetTransformed = offset;
111#endif
112                // weight with projected coordinate to reach similar kernel size for near and far
[3025]113                float2 texcoord = lightSpacePos + offsetTransformed * scale;
[2944]114
115                float shadowDepth = tex2D(shadowMap, texcoord).x;
116
[3025]117                total_d += w * step(depth, shadowDepth);
118                total_w += w;
[2944]119        }
120
[3025]121        total_d /= (float)total_w;
[2944]122
123        return total_d;
124}
125
[3025]126
[3009]127inline float3 Interpol(float2 w, float3 bl, float3 br, float3 tl, float3 tr)
128{
129        float3 x1 = lerp(bl, tl, w.y);
130        float3 x2 = lerp(br, tr, w.y);
[3095]131        float3 v  = lerp(x1, x2, w.x);
[2944]132
[3009]133        return v;
134}
135
136
[2892]137pixel main_shadow(fragment IN,
138                                  uniform sampler2D colors,
139                                  uniform sampler2D positions,
140                                  uniform sampler2D normals,               
141                                  uniform sampler2D shadowMap,
[2893]142                                  uniform float4x4 shadowMatrix,
[2952]143                                  uniform float sampleWidth,
[3092]144                                  uniform sampler2D noiseTex,
[2966]145                                  uniform float2 samples[NUM_PCF_TABS],
[3024]146                                  uniform float weights[NUM_PCF_TABS],
[3009]147                                  uniform float3 lightDir,
148                                  uniform float3 eyePos,
149                                  uniform float3 bl,
150                                  uniform float3 br,
151                                  uniform float3 tl,
152                                  uniform float3 tr
[2944]153                                  )
[2928]154{
155        pixel OUT;
[2944]156
157        float4 norm = tex2D(normals, IN.texCoord.xy);
[2945]158        const float3 normal = normalize(norm.xyz);
[2944]159
[3009]160        float4 color = tex2Dlod(colors, float4(IN.texCoord, 0, 0));
161
162        /// reconstruct position from the eye space depth
163        float3 viewDir = IN.view;
[3018]164        const float lenView = length(viewDir);
165        viewDir /= lenView;
166
[3009]167        const float eyeDepth = tex2Dlod(colors, float4(IN.texCoord, 0, 0)).w;
168
[3034]169        const float4 worldPos = float4(eyePos - viewDir * eyeDepth, 1);
[3009]170       
[2945]171        // diffuse intensity
172        const float angle = saturate(dot(normal, lightDir));
[2959]173        const float4 lightDiffuse = glstate.light[0].diffuse;
[3017]174       
[2954]175        float4 diffuse = lightDiffuse * angle;
176
[3009]177        // hack: prevent shadowing the sky     
178        const bool useShading = (color.w < 1e19f);
179
[2945]180        // calc diffuse illumination + shadow term
[3009]181        if (useShading &&
182                (angle > 1e-3f) // shadow only if diffuse color has some minimum intensity
[2945]183                )
184        {
[3034]185                float4 lightSpacePos = mul(shadowMatrix, worldPos);
[2945]186                lightSpacePos /= lightSpacePos.w;
[2944]187
[3092]188                float shadowTerm = CalcShadowTerm(IN, shadowMap, sampleWidth, lightSpacePos.xy, lightSpacePos.z, samples, weights, noiseTex);
[3136]189       
[2945]190                diffuse *= shadowTerm;
[2944]191        }
[2945]192
[2974]193        // light ambient term
[2954]194        const float4 ambient = glstate.light[0].ambient;
[3009]195        // compute shading
196        OUT.color = useShading ? (ambient + diffuse) * color : color;
[3087]197        // store scaled view vector from now on so wie don't have to normalize later (e.g., for ssao)
[3018]198        OUT.color.w = color.w / lenView;
[2991]199
[2928]200        return OUT;
201}
[2965]202
[3081]203#if 0
204/** This shader computes the reprojection and stores reprojected color / depth values
205        as well as a boolean that
206*/
[3087]207pixel Reproject(fragment IN,
208                                uniform sampler2D colors,
209                                uniform sampler2D normals)
[3081]210{
211        float4 norm = tex2Dlod(normals, float4(IN.texCoord, 0 ,0));
212        const float3 normal = normalize(norm.xyz);
213
214        /// reconstruct position from the eye space depth
215        float3 viewDir = IN.view;
216        const float eyeDepth = tex2Dlod(colors, float4(IN.texCoord, 0, 0)).w;
217        const float3 eyeSpacePos = -viewDir * eyeDepth;
218        const float4 worldPos = float4(eyePos + eyeSpacePos, 1.0f);
219
220
221        ////////////////
222        //-- calculcate the current projected posiion (also used for next frame)
223       
224        float4 currentPos = mul(modelViewProj, worldPos);
225       
226        const float w = SAMPLE_RADIUS / currentPos.w;
227        currentPos /= currentPos.w;
228       
229        const float precisionScale = 1e-3f;
230        const float currentDepth = currentPos.z * precisionScale;
231
[3104]232        const float2 ao = ssao(IN, colors, noiseTex, samples, normal,
[3092]233                                   eyeSpacePos, w, bl, br, tl, tr, normalize(viewDir));
[3081]234
235
236        /////////////////
237        //-- compute temporally smoothing
238
239
240        // reproject new frame into old one
241       
242        // calculate projected depth
243        float4 projPos = mul(oldModelViewProj, worldPos);
244        projPos /= projPos.w;
245       
246        // the current depth projected into the old frame
247        const float projDepth = projPos.z * precisionScale;
248        // fit from unit cube into 0 .. 1
249        const float2 tex = projPos.xy * 0.5f + 0.5f;
250        // retrieve the sample from the last frame
251        float4 oldCol = tex2D(oldTex, tex);
252
253        const float oldDepth = oldCol.z;
254        //const float depthDif = 1.0f - projDepth / oldDepth;
255        const float depthDif = projDepth - oldDepth;
256
257        //const float oldNumSamples = oldCol.y;
258        const float oldWeight = clamp(oldCol.y, 0, temporalCoherence);
259
260        float newWeight;
261
262        // the number of valid samples in this frame
263        //const float newNumSamples = ao.y;
264
265        if ((temporalCoherence > 0)
266                && (tex.x >= 0.0f) && (tex.x < 1.0f)
267                && (tex.y >= 0.0f) && (tex.y < 1.0f)
268                && (abs(depthDif) < MIN_DEPTH_DIFF)
269                && (abs(oldCol.x - ao.x) < 0.1f)
270                // if visibility changed in the surrounding area we have to recompute
271                //&& (oldNumSamples > 0.8f * newNumSamples)
272                )
273        {
274                // increase the weight for convergence
275                newWeight = oldWeight + 1.0f;
276                OUT.illum_col.x = (ao.x + oldCol.x * oldWeight) / newWeight;
277                //if (!(oldNumSamples > ao.y - 1.5f)) newWeight = 0;
278        }
279        else
280        {       
281                OUT.illum_col.x = ao.x;
282                newWeight = .0f;
283        }
284
285        OUT.illum_col.y = newWeight;
286        OUT.illum_col.z = currentDepth;
287
288        return OUT;
289}
290
[3134]291#endif
292
293
294float4 Output(fragment IN, uniform sampler2D colors): COLOR
295{   
296        // let bilinear filtering do its work
297        return tex2Dlod(colors, float4(IN.texCoord, 0, 0));
298}
Note: See TracBrowser for help on using the repository browser.