source: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/DeferredRenderer.cpp @ 2984

Revision 2984, 36.1 KB checked in by mattausch, 16 years ago (diff)

added eye space depth

Line 
1#include "DeferredRenderer.h"
2#include "FrameBufferObject.h"
3#include "RenderState.h"
4#include "SampleGenerator.h"
5#include "Vector3.h"
6#include "Camera.h"
7#include "shaderenv.h"
8#include "Halton.h"
9#include "ShadowMapping.h"
10#include "Light.h"
11
12
13using namespace std;
14
15
16namespace CHCDemoEngine
17{
18
19static CGprogram sCgSsaoProgram = NULL;
20static CGprogram sCgGiProgram = NULL;
21
22static CGprogram sCgDeferredProgram = NULL;
23static CGprogram sCgAntiAliasingProgram = NULL;
24static CGprogram sCgDeferredShadowProgram = NULL;
25
26static CGparameter sColorsTexCombineParam;
27static CGparameter sSsaoTexCombineParam;
28
29static CGparameter sColorsTexDeferredParam;
30static CGparameter sOldColorsTexDeferredParam;
31static CGparameter sOldColorsTexShadowParam;
32
33static CGparameter sPositionsTexDeferredParam;
34static CGparameter sNormalsTexDeferredParam;
35
36static CGprogram sCgCombinedSsaoProgram = NULL;
37static CGprogram sCgCombinedIllumProgram = NULL;
38
39
40static CGprogram sCgInitialIntensityProgram;
41static CGprogram sCgDownSampleProgram;
42static CGprogram sCgToneProgram;
43
44
45///////////////////////////////////////
46
47
48static CGparameter sColorsTexParam;
49static CGparameter sPositionsTexParam;
50static CGparameter sNormalsTexParam;
51
52static CGparameter sOldModelViewProjMatrixParam;
53static CGparameter sModelViewProjMatrixParam;
54static CGparameter sMaxDepthParam;
55static CGparameter sSamplesParam;
56static CGparameter sOldTexParam;
57static CGparameter sNoiseTexParam;
58static CGparameter sTemporalCoherenceParam;
59
60
61///////////////////////////////////////
62
63
64static CGparameter sColorsTexGiParam;
65static CGparameter sPositionsTexGiParam;
66static CGparameter sNormalsTexGiParam;
67
68
69static CGparameter sOldModelViewProjMatrixGiParam;
70static CGparameter sMaxDepthGiParam;
71static CGparameter sSamplesGiParam;
72static CGparameter sOldSsaoTexGiParam;
73static CGparameter sOldIllumTexGiParam;
74static CGparameter sNoiseTexGiParam;
75static CGparameter sTemporalCoherenceGiParam;
76
77
78static CGparameter sColorsTexCombinedIllumParam;
79static CGparameter sSsaoTexCombinedIllumParam;
80static CGparameter sIllumTexCombinedIllumParam;
81
82static CGparameter sColorsTexCombinedSsaoParam;
83static CGparameter sSsaoTexCombinedSsaoParam;
84static CGparameter sPositionsTexCombinedSsaoParam;
85
86
87////////////
88
89static CGparameter sColorsTexAntiAliasingParam;
90static CGparameter sNormalsTexAntiAliasingParam;
91
92
93static CGparameter sShadowMapParam;
94static CGparameter sPositionsTexShadowParam; 
95static CGparameter sColorsTexShadowParam; 
96static CGparameter sNormalsTexShadowParam;
97
98static CGparameter sShadowMatrixParam;
99static CGparameter sMaxDepthShadowParam;
100static CGparameter sSampleWidthParam;
101
102static CGparameter sNoiseTexShadowParam;
103static CGparameter sSamplesShadowParam;
104
105static CGparameter sLightDirParam;
106static CGparameter sLightDirShadowParam;
107static CGparameter sImageKeyParam;
108static CGparameter sMiddleGreyParam;
109static CGparameter sWhiteLumParam;
110
111
112static CGparameter sColorsTexInitialParam;
113static CGparameter sColorsTexToneParam;
114static CGparameter sIntensityTexDownSampleParam;
115
116//#define USE_3D_SSAO
117
118
119static GLuint noiseTex = 0;
120
121// ssao random spherical samples
122#ifdef USE_3D_SSAO
123static Sample2 samples3[NUM_SAMPLES];
124#else
125static Sample2 samples2[NUM_SAMPLES];
126#endif
127
128// number of pcf tabs
129Sample2 pcfSamples[NUM_PCF_TABS];
130
131int DeferredRenderer::colorBufferIdx = 0;
132
133static void PrintGLerror(char *msg)
134{
135        GLenum errCode;
136        const GLubyte *errStr;
137       
138        if ((errCode = glGetError()) != GL_NO_ERROR)
139        {
140                errStr = gluErrorString(errCode);
141                fprintf(stderr,"OpenGL ERROR: %s: %s\n", errStr, msg);
142        }
143}
144
145static int computeSize(int level)
146{
147        // Compute total image size.
148        float w = 1024;
149        float h = 768;
150
151        int mipmapSize = max(1, w / (1 << level) ) *
152                             max(1, h / (1 << level) ) * sizeof(float) * 4;
153
154        return mipmapSize;
155}
156
157
158
159/** Generate poisson disc distributed sample points on the unit disc
160*/
161static void GenerateSamples(int sampling)
162{
163#ifdef USE_3D_SSAO
164
165        SphericalSampleGenerator sph(NUM_SAMPLES, 1.0f);
166        sph.Generate((float *)samples3);
167
168#else
169        switch (sampling)
170        {
171        case DeferredRenderer::SAMPLING_POISSON:
172                {
173                        PoissonDiscSampleGenerator2 poisson(NUM_SAMPLES, 1.0f);
174                        poisson.Generate((float *)samples2);
175                }
176                break;
177        case DeferredRenderer::SAMPLING_QUADRATIC:
178                {
179                        QuadraticDiscSampleGenerator2 g(NUM_SAMPLES, 1.0f);
180                        g.Generate((float *)samples2);
181                }
182                break;
183        default: // SAMPLING_DEFAULT
184
185                RandomSampleGenerator2 g(NUM_SAMPLES, 1.0f);
186                g.Generate((float *)samples2);
187        }
188#endif
189}
190
191
192static void CreateNoiseTex2D(int w, int h)
193{
194        //GLubyte *randomNormals = new GLubyte[mWidth * mHeight * 3];
195        float *randomNormals = new float[w * h * 3];
196
197        static HaltonSequence halton;
198        float r[2];
199
200        for (int i = 0; i < w * h * 3; i += 3)
201        {
202               
203#ifdef USE_3D_SSAO
204                //halton.GetNext(2, r);
205                r[0] = RandomValue(0, 1);
206                r[1] = RandomValue(0, 1);
207
208                const float theta = 2.0f * acos(sqrt(1.0f - r[0]));
209                const float phi = 2.0f * M_PI * r[1];
210
211                randomNormals[i + 0] = sin(theta) * cos(phi);
212                randomNormals[i + 1] = sin(theta) * sin(phi);
213                randomNormals[i + 2] = cos(theta);
214#else
215                // create random samples on a circle
216                r[0] = RandomValue(0, 1);
217                //halton.GetNext(1, r);
218
219                const float theta = 2.0f * acos(sqrt(1.0f - r[0]));
220               
221                randomNormals[i + 0] = cos(theta);
222                randomNormals[i + 1] = sin(theta);
223                randomNormals[i + 2] = 0;
224#endif
225        }
226
227        glEnable(GL_TEXTURE_2D);
228        glGenTextures(1, &noiseTex);
229        glBindTexture(GL_TEXTURE_2D, noiseTex);
230               
231        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
232        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
233        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
234        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
235
236        //glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB8, w, h, 0, GL_RGB, GL_UNSIGNED_BYTE, randomNormals);
237        glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA16F_ARB, w, h, 0, GL_RGB, GL_FLOAT, randomNormals);
238
239        glBindTexture(GL_TEXTURE_2D, 0);
240        glDisable(GL_TEXTURE_2D);
241
242        delete [] randomNormals;
243
244        cout << "created noise texture" << endl;
245
246        PrintGLerror("noisetexture");
247}
248
249
250DeferredRenderer::DeferredRenderer(int w, int h, Camera *cam, float scaleFactor):
251mWidth(w), mHeight(h),
252mCamera(cam),
253mScaleFactor(scaleFactor),
254mUseTemporalCoherence(true),
255mRegenerateSamples(true),
256mSamplingMethod(SAMPLING_POISSON),
257mShadingMethod(DEFAULT),
258mFboIndex(0)
259{
260        // create noise texture for ssao
261        CreateNoiseTex2D(w, h);
262
263
264        ///////////
265        //-- the flip-flop fbos
266
267        mFbo = new FrameBufferObject(w, h, FrameBufferObject::DEPTH_NONE);
268
269        mFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR);
270        mFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR);
271        mFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR);
272        mFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR);
273}
274
275
276DeferredRenderer::~DeferredRenderer()
277{
278        if (sCgSsaoProgram)     cgDestroyProgram(sCgSsaoProgram);
279        if (sCgDeferredProgram) cgDestroyProgram(sCgDeferredProgram);
280        if (sCgSsaoProgram)     cgDestroyProgram(sCgSsaoProgram);
281        if (sCgGiProgram) cgDestroyProgram(sCgGiProgram);
282        if (sCgAntiAliasingProgram) cgDestroyProgram(sCgAntiAliasingProgram);
283
284        DEL_PTR(mFbo);
285
286        glDeleteTextures(1, &noiseTex);
287}
288
289
290void DeferredRenderer::SetUseTemporalCoherence(bool temporal)
291{
292        mUseTemporalCoherence = temporal;
293}
294
295
296void DeferredRenderer::Init(CGcontext context)
297{       
298        sCgDeferredProgram =
299                cgCreateProgramFromFile(context,
300                                                                CG_SOURCE,
301                                                                "src/shaders/deferred.cg",
302                                                                RenderState::sCgFragmentProfile,
303                                                                "main",
304                                                                NULL);
305
306        if (sCgDeferredProgram != NULL)
307        {
308                cgGLLoadProgram(sCgDeferredProgram);
309
310                // we need size of texture for scaling
311                sPositionsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "positions"); 
312                sColorsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "colors"); 
313                sOldColorsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "oldColors");
314                sNormalsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "normals");
315               
316                sLightDirParam = cgGetNamedParameter(sCgDeferredProgram, "lightDir");
317        }
318        else
319                cerr << "deferred program failed to load" << endl;
320
321
322        ///////////////
323
324        sCgSsaoProgram =
325                cgCreateProgramFromFile(context,
326                                                                CG_SOURCE,
327#ifdef USE_3D_SSAO
328                                                                "src/shaders/ssao3d.cg",
329#else
330                                                                "src/shaders/ssao.cg",
331#endif
332                                                                RenderState::sCgFragmentProfile,
333                                                                "main",
334                                                                NULL);
335
336        if (sCgSsaoProgram != NULL)
337        {
338                cgGLLoadProgram(sCgSsaoProgram);
339
340                sPositionsTexParam = cgGetNamedParameter(sCgSsaoProgram, "positions"); 
341                sColorsTexParam = cgGetNamedParameter(sCgSsaoProgram, "colors"); 
342                sNormalsTexParam = cgGetNamedParameter(sCgSsaoProgram, "normals"); 
343                sNoiseTexParam = cgGetNamedParameter(sCgSsaoProgram, "noiseTexture");
344               
345                sOldModelViewProjMatrixParam = cgGetNamedParameter(sCgSsaoProgram, "oldModelViewProj");
346                sModelViewProjMatrixParam = cgGetNamedParameter(sCgSsaoProgram, "mymodelViewProj");
347                sMaxDepthParam = cgGetNamedParameter(sCgSsaoProgram, "maxDepth");
348                sTemporalCoherenceParam = cgGetNamedParameter(sCgSsaoProgram, "temporalCoherence");
349
350                sOldTexParam = cgGetNamedParameter(sCgSsaoProgram, "oldTex"); 
351                sSamplesParam = cgGetNamedParameter(sCgSsaoProgram, "samples");
352        }
353        else
354                cerr << "ssao program failed to load" << endl;
355
356        sCgGiProgram =
357                cgCreateProgramFromFile(context,
358                                                                CG_SOURCE,
359                                                                "src/shaders/globillum.cg",
360                                                                RenderState::sCgFragmentProfile,
361                                                                "main",
362                                                                NULL);
363
364        if (sCgGiProgram != NULL)
365        {
366                cgGLLoadProgram(sCgGiProgram);
367
368                // we need size of texture for scaling
369                sPositionsTexGiParam = cgGetNamedParameter(sCgGiProgram, "positions"); 
370                sColorsTexGiParam = cgGetNamedParameter(sCgGiProgram, "colors"); 
371                sNormalsTexGiParam = cgGetNamedParameter(sCgGiProgram, "normals"); 
372               
373                sOldModelViewProjMatrixGiParam = cgGetNamedParameter(sCgGiProgram, "oldModelViewProj");
374                sMaxDepthGiParam = cgGetNamedParameter(sCgGiProgram, "maxDepth");
375                sTemporalCoherenceGiParam = cgGetNamedParameter(sCgGiProgram, "temporalCoherence");
376
377                sNoiseTexGiParam = cgGetNamedParameter(sCgGiProgram, "noiseTexture");
378                sSamplesGiParam = cgGetNamedParameter(sCgGiProgram, "samples");
379               
380                sOldSsaoTexGiParam = cgGetNamedParameter(sCgGiProgram, "oldSsaoTex"); 
381                sOldIllumTexGiParam = cgGetNamedParameter(sCgGiProgram, "oldIllumTex"); 
382        }
383        else
384                cerr << "globillum program failed to load" << endl;
385
386        sCgCombinedIllumProgram =
387                cgCreateProgramFromFile(context,
388                                                                CG_SOURCE,
389                                                                "src/shaders/globillum.cg",
390                                                                RenderState::sCgFragmentProfile,
391                                                                "combine",
392                                                                NULL);
393
394        if (sCgCombinedIllumProgram != NULL)
395        {
396                cgGLLoadProgram(sCgCombinedIllumProgram);
397
398                sColorsTexCombinedIllumParam = cgGetNamedParameter(sCgCombinedIllumProgram, "colors"); 
399                sSsaoTexCombinedIllumParam = cgGetNamedParameter(sCgCombinedIllumProgram, "ssaoTex");
400                sIllumTexCombinedIllumParam = cgGetNamedParameter(sCgCombinedIllumProgram, "illumTex");
401        }
402        else
403                cerr << "combined illum program failed to load" << endl;
404
405
406        sCgCombinedSsaoProgram =
407                cgCreateProgramFromFile(context,
408                                                                CG_SOURCE,
409                                                                "src/shaders/ssao.cg",
410                                                                RenderState::sCgFragmentProfile,
411                                                                "combine",
412                                                                NULL);
413
414        if (sCgCombinedSsaoProgram != NULL)
415        {
416                cgGLLoadProgram(sCgCombinedSsaoProgram);
417
418                sColorsTexCombinedSsaoParam = cgGetNamedParameter(sCgCombinedSsaoProgram, "colors"); 
419                sSsaoTexCombinedSsaoParam = cgGetNamedParameter(sCgCombinedSsaoProgram, "ssaoTex");
420                sPositionsTexCombinedSsaoParam = cgGetNamedParameter(sCgCombinedSsaoProgram, "positions");
421        }
422        else
423                cerr << "combied illum program failed to load" << endl;
424
425       
426        sCgAntiAliasingProgram =
427                cgCreateProgramFromFile(context,
428                                                                CG_SOURCE,
429                                                                "src/shaders/antialiasing.cg",
430                                                                RenderState::sCgFragmentProfile,
431                                                                "main",
432                                                                NULL);
433
434        if (sCgAntiAliasingProgram != NULL)
435        {
436                cgGLLoadProgram(sCgAntiAliasingProgram);
437
438                sColorsTexAntiAliasingParam = cgGetNamedParameter(sCgAntiAliasingProgram, "colors"); 
439                sNormalsTexAntiAliasingParam = cgGetNamedParameter(sCgAntiAliasingProgram, "normals");
440        }
441        else
442                cerr << "antialiasing program failed to load" << endl;
443
444        sCgDeferredShadowProgram =
445                cgCreateProgramFromFile(context,
446                                                                CG_SOURCE,
447                                                                "src/shaders/deferred.cg",
448                                                                RenderState::sCgFragmentProfile,
449                                                                "main_shadow",
450                                                                NULL);
451
452        if (sCgDeferredShadowProgram != NULL)
453        {
454                cgGLLoadProgram(sCgDeferredShadowProgram);
455
456                // we need size of texture for scaling
457                sPositionsTexShadowParam = cgGetNamedParameter(sCgDeferredShadowProgram, "positions"); 
458                sColorsTexShadowParam = cgGetNamedParameter(sCgDeferredShadowProgram, "colors"); 
459                sNormalsTexShadowParam = cgGetNamedParameter(sCgDeferredShadowProgram, "normals");
460
461                sShadowMapParam = cgGetNamedParameter(sCgDeferredShadowProgram, "shadowMap"); 
462                sMaxDepthShadowParam = cgGetNamedParameter(sCgDeferredShadowProgram, "maxDepth");
463                sSampleWidthParam = cgGetNamedParameter(sCgDeferredShadowProgram, "sampleWidth");
464                sShadowMatrixParam = cgGetNamedParameter(sCgDeferredShadowProgram, "shadowMatrix");
465
466                sNoiseTexShadowParam = cgGetNamedParameter(sCgDeferredShadowProgram, "noiseTexture");
467                sSamplesShadowParam = cgGetNamedParameter(sCgDeferredShadowProgram, "samples");
468
469                sLightDirShadowParam = cgGetNamedParameter(sCgDeferredShadowProgram, "lightDir");
470
471                sOldColorsTexShadowParam = cgGetNamedParameter(sCgDeferredShadowProgram, "oldColors");
472
473
474                PoissonDiscSampleGenerator2 poisson(NUM_PCF_TABS, 1.0f);
475                poisson.Generate((float *)pcfSamples);
476
477                cgGLSetParameterArray2f(sSamplesShadowParam, 0, NUM_PCF_TABS, (const float *)pcfSamples);
478        }
479        else
480                cerr << "deferred program failed to load" << endl;
481
482        sCgToneProgram =
483                cgCreateProgramFromFile(context,
484                                                                CG_SOURCE,
485                                                                "src/shaders/tonemap.cg",
486                                                                RenderState::sCgFragmentProfile,
487                                                                "ToneMap",
488                                                                NULL);
489
490        if (sCgToneProgram != NULL)
491        {
492                cgGLLoadProgram(sCgToneProgram);
493
494                sImageKeyParam = cgGetNamedParameter(sCgToneProgram, "imageKey");
495                sMiddleGreyParam = cgGetNamedParameter(sCgToneProgram, "middleGrey");
496                sWhiteLumParam = cgGetNamedParameter(sCgToneProgram, "whiteLum");
497
498                sColorsTexToneParam = cgGetNamedParameter(sCgToneProgram, "colors"); 
499        }
500        else
501                cerr << "tone program failed to load" << endl;
502
503        sCgInitialIntensityProgram =
504                cgCreateProgramFromFile(context,
505                                                                CG_SOURCE,
506                                                                "src/shaders/tonemap.cg",
507                                                                RenderState::sCgFragmentProfile,
508                                                                "GreyScaleDownSample",
509                                                                NULL);
510
511        if (sCgInitialIntensityProgram != NULL)
512        {
513                cgGLLoadProgram(sCgInitialIntensityProgram);
514
515                // we need size of texture for scaling
516                sColorsTexInitialParam = cgGetNamedParameter(sCgInitialIntensityProgram, "colors"); 
517        }
518        else
519                cerr << "intensity program failed to load" << endl;
520
521
522
523        PrintGLerror("init");
524}
525
526
527void DeferredRenderer::Render(FrameBufferObject *fbo,
528                                                          const Matrix4x4 &oldProjViewMatrix,
529                                                          const Matrix4x4 &projViewMatrix,
530                                                          float tempCohFactor,
531                                                          DirectionalLight *light,
532                                                          ShadowMap *shadowMap)
533{
534        // switch roles of old and new fbo
535        // the algorihm uses two input fbos, where the one
536        // contais the color buffer from the last frame,
537        // the other one will be written
538
539        mFboIndex = 2 - mFboIndex;
540       
541        FrameBufferObject::Release();
542
543        cgGLEnableProfile(RenderState::sCgFragmentProfile);
544
545        glDisable(GL_ALPHA_TEST);
546        glDisable(GL_TEXTURE_2D);
547        glDisable(GL_LIGHTING);
548
549        glPushAttrib(GL_VIEWPORT_BIT);
550        glViewport(0, 0, mWidth, mHeight);
551
552        glMatrixMode(GL_PROJECTION);
553        glPushMatrix();
554        glLoadIdentity();
555
556        const float offs = 0.5f;
557        glOrtho(-offs, offs, -offs, offs, 0, 1);
558
559        glMatrixMode(GL_MODELVIEW);
560        glPushMatrix();
561        glLoadIdentity();
562
563        if (shadowMap)
564                FirstPassShadow(fbo, light, shadowMap);
565        else
566                FirstPass(fbo, light);
567
568        switch (mShadingMethod)
569        {
570        case SSAO:
571                ComputeSsao(fbo, tempCohFactor, oldProjViewMatrix, projViewMatrix);
572                CombineSsao(fbo);
573                break;
574        case GI:
575                ComputeGlobIllum(fbo, tempCohFactor, oldProjViewMatrix);
576                CombineIllum(fbo);
577                break;
578        default: // DEFAULT
579                // do nothing: standard deferred shading
580                break;
581        }
582
583        float imageKey, whiteLum, middleGrey;
584/*
585        glPixelStorei(GL_PACK_ALIGNMENT, 1);
586        // generate mip map levels for average loglum and tone mapping
587        glBindTexture(GL_TEXTURE_2D, fbo->GetColorBuffer(colorBufferIdx)->GetTexture());
588        glGenerateMipmapEXT(GL_TEXTURE_2D);
589       
590        ComputeToneParameters(fbo, light, imageKey, whiteLum, middleGrey);
591        ToneMap(fbo, light, imageKey, whiteLum, middleGrey);
592*/
593        AntiAliasing(fbo, light);
594
595        glEnable(GL_LIGHTING);
596        glDisable(GL_TEXTURE_2D);
597
598        glMatrixMode(GL_PROJECTION);
599        glPopMatrix();
600
601        glMatrixMode(GL_MODELVIEW);
602        glPopMatrix();
603
604        glPopAttrib();
605
606        cgGLDisableProfile(RenderState::sCgFragmentProfile);
607}
608
609
610void DeferredRenderer::ComputeSsao(FrameBufferObject *fbo,
611                                                                   float tempCohFactor,
612                                                                   const Matrix4x4 &oldProjViewMatrix,
613                                                                   const Matrix4x4 &projViewMatrix
614                                                                   )
615{
616#ifdef USE_3D_SSAO
617        // bias from [-1, 1] to [0, 1]
618        static Matrix4x4 biasMatrix(0.5f, 0.0f, 0.0f, 0.5f,
619                                                                0.0f, 0.5f, 0.0f, 0.5f,
620                                                                0.0f, 0.0f, 0.5f, 0.5f,
621                                                                0.0f, 0.0f, 0.0f, 1.0f);
622
623        Matrix4x4 m = projViewMatrix * biasMatrix;
624
625        cgGLSetMatrixParameterfc(sModelViewProjMatrixParam, (const float *)m.x);
626#endif
627
628        cgGLSetMatrixParameterfc(sOldModelViewProjMatrixParam, (const float *)oldProjViewMatrix.x);
629
630        GLuint colorsTex = fbo->GetColorBuffer(colorBufferIdx)->GetTexture();
631        GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
632        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
633
634        // generate mip map levels of position texture
635        glBindTexture(GL_TEXTURE_2D, positionsTex);
636        glGenerateMipmapEXT(GL_TEXTURE_2D);
637       
638
639        // read the second buffer, write to the first buffer
640        mFbo->Bind();
641        glDrawBuffers(1, mrt + mFboIndex);
642
643        GLuint oldTex = mFbo->GetColorBuffer(2 - mFboIndex)->GetTexture();
644
645        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
646
647        cgGLEnableProfile(RenderState::sCgFragmentProfile);
648        cgGLBindProgram(sCgSsaoProgram);
649
650        cgGLSetTextureParameter(sPositionsTexParam, positionsTex);
651        cgGLEnableTextureParameter(sPositionsTexParam);
652
653        cgGLSetTextureParameter(sColorsTexParam, colorsTex);
654        cgGLEnableTextureParameter(sColorsTexParam);
655
656        cgGLSetTextureParameter(sNormalsTexParam, normalsTex);
657        cgGLEnableTextureParameter(sNormalsTexParam);
658
659        cgGLSetTextureParameter(sNoiseTexParam, noiseTex);
660        cgGLEnableTextureParameter(sNoiseTexParam);
661
662        cgGLSetTextureParameter(sOldTexParam, oldTex);
663        cgGLEnableTextureParameter(sOldTexParam);
664       
665        cgGLSetParameter1f(sMaxDepthParam, mScaleFactor);
666       
667        cgGLSetParameter1f(sTemporalCoherenceParam, (mUseTemporalCoherence && !mRegenerateSamples) ? tempCohFactor : 0);
668
669        if (mUseTemporalCoherence || mRegenerateSamples)
670        {
671                mRegenerateSamples = false;
672
673                // q: should we generate new samples or only rotate the old ones?
674                // in the first case, the sample patterns look nicer, but the kernel
675                // needs longer to converge
676                GenerateSamples(mSamplingMethod);
677
678#ifdef USE_3D_SSAO
679                cgGLSetParameterArray3f(sSamplesParam, 0, NUM_SAMPLES, (const float *)samples3);
680#else
681                cgGLSetParameterArray2f(sSamplesParam, 0, NUM_SAMPLES, (const float *)samples2);
682#endif
683        }
684
685        Vector3 tl, tr, bl, br;
686        ComputeViewVectors(tl, tr, bl, br);
687
688        glBegin(GL_QUADS);
689
690        // note: slightly larger texture could hide ambient occlusion error on border but costs resolution
691        const float offs = 0.5f;
692       
693        glTexCoord2f(0, 0); glMultiTexCoord3fARB(GL_TEXTURE1_ARB, bl.x, bl.y, bl.z); glVertex3f(-offs, -offs, -0.5f);
694        glTexCoord2f(1, 0); glMultiTexCoord3fARB(GL_TEXTURE1_ARB, br.x, br.y, br.z); glVertex3f( offs, -offs, -0.5f);
695        glTexCoord2f(1, 1); glMultiTexCoord3fARB(GL_TEXTURE1_ARB, tr.x, tr.y, tr.z); glVertex3f( offs,  offs, -0.5f);
696        glTexCoord2f(0, 1); glMultiTexCoord3fARB(GL_TEXTURE1_ARB, tl.x, tl.y, tl.z); glVertex3f(-offs,  offs, -0.5f);
697
698        glEnd();
699
700        cgGLDisableTextureParameter(sColorsTexParam);
701        cgGLDisableTextureParameter(sPositionsTexParam);
702        cgGLDisableTextureParameter(sNormalsTexParam);
703        cgGLDisableTextureParameter(sNoiseTexParam);
704        cgGLDisableTextureParameter(sOldTexParam);
705
706
707        FrameBufferObject::Release();
708
709        PrintGLerror("ssao first pass");
710}
711
712
713void DeferredRenderer::ComputeViewVectors(Vector3 &tl, Vector3 &tr, Vector3 &bl, Vector3 &br)
714{
715        Vector3 ftl, ftr, fbl, fbr, ntl, ntr, nbl, nbr;
716
717        mCamera->ComputePoints(ftl, ftr, fbl, fbr, ntl, ntr, nbl, nbr);
718
719        bl = Normalize(nbl - fbl);
720        br = Normalize(nbr - fbr);
721        tl = Normalize(ntl - ftl);
722        tr = Normalize(ntr - ftr);
723}
724
725
726
727static void SetVertex(float x, float y, float x_offs, float y_offs)
728{
729        glMultiTexCoord2fARB(GL_TEXTURE0_ARB, x, y); // center
730        glMultiTexCoord2fARB(GL_TEXTURE1_ARB, x - x_offs, y + y_offs); // left top
731        glMultiTexCoord2fARB(GL_TEXTURE2_ARB, x + x_offs, y - y_offs); // right bottom
732        glMultiTexCoord2fARB(GL_TEXTURE3_ARB, x + x_offs, y + y_offs); // right top
733        glMultiTexCoord2fARB(GL_TEXTURE4_ARB, x - x_offs, y - y_offs); // left bottom
734
735        glMultiTexCoord4fARB(GL_TEXTURE5_ARB, x - x_offs, y, x + x_offs, y); // left right
736        glMultiTexCoord4fARB(GL_TEXTURE6_ARB, x, y + y_offs, x, y - y_offs); // top bottom
737
738        glVertex3f(x - 0.5f, y - 0.5f, -0.5f);
739}
740
741
742void DeferredRenderer::AntiAliasing(FrameBufferObject *fbo, DirectionalLight *light)
743{
744        ColorBufferObject *colorBuffer = fbo->GetColorBuffer(colorBufferIdx);
745
746        GLuint colorsTex = colorBuffer->GetTexture();
747        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
748       
749        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
750
751        cgGLEnableProfile(RenderState::sCgFragmentProfile);
752        cgGLBindProgram(sCgAntiAliasingProgram);
753       
754        cgGLSetTextureParameter(sColorsTexAntiAliasingParam, colorsTex);
755        cgGLEnableTextureParameter(sColorsTexAntiAliasingParam);
756
757        cgGLSetTextureParameter(sNormalsTexAntiAliasingParam, normalsTex);
758        cgGLEnableTextureParameter(sNormalsTexAntiAliasingParam);
759
760
761        glColor3f(1.0f, 1.0f, 1.0f);
762
763        glBegin(GL_QUADS);
764
765        // the neighbouring texels
766        float x_offs = 1.0f / mWidth;
767        float y_offs = 1.0f / mHeight;
768
769        SetVertex(0, 0, x_offs, y_offs);
770        SetVertex(1, 0, x_offs, y_offs);
771        SetVertex(1, 1, x_offs, y_offs);
772        SetVertex(0, 1, x_offs, y_offs);
773
774        glEnd();
775
776        cgGLDisableTextureParameter(sColorsTexAntiAliasingParam);
777        cgGLDisableTextureParameter(sNormalsTexAntiAliasingParam);
778
779        PrintGLerror("antialiasing");
780}
781
782
783void DeferredRenderer::FirstPass(FrameBufferObject *fbo, DirectionalLight *light)
784{
785        GLuint colorsTex = fbo->GetColorBuffer(colorBufferIdx)->GetTexture();
786        GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
787        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
788
789        GLuint oldColorsTex = fbo->GetColorBuffer(3 - colorBufferIdx)->GetTexture();
790
791        fbo->Bind();
792
793        colorBufferIdx = 3 - colorBufferIdx;
794        glDrawBuffers(1, mrt + colorBufferIdx);
795
796        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
797       
798        cgGLEnableProfile(RenderState::sCgFragmentProfile);
799
800        cgGLBindProgram(sCgDeferredProgram);
801
802        cgGLSetTextureParameter(sColorsTexDeferredParam, colorsTex);
803        cgGLEnableTextureParameter(sColorsTexDeferredParam);
804
805        cgGLSetTextureParameter(sOldColorsTexDeferredParam, oldColorsTex);
806        cgGLEnableTextureParameter(sOldColorsTexDeferredParam);
807
808        cgGLSetTextureParameter(sPositionsTexDeferredParam, positionsTex);
809        cgGLEnableTextureParameter(sPositionsTexDeferredParam);
810
811        cgGLSetTextureParameter(sNormalsTexDeferredParam, normalsTex);
812        cgGLEnableTextureParameter(sNormalsTexDeferredParam);
813       
814        Vector3 lightDir = -light->GetDirection();
815        cgGLSetParameter3f(sLightDirParam, lightDir.x, lightDir.y, lightDir.z);
816
817
818        glColor3f(1.0f, 1.0f, 1.0f);
819
820        const float offs = 0.5f;
821
822        glBegin(GL_QUADS);
823
824        glTexCoord2f(0, 0); glVertex3f(-offs, -offs, -0.5f);
825        glTexCoord2f(1, 0); glVertex3f( offs, -offs, -0.5f);
826        glTexCoord2f(1, 1); glVertex3f( offs,  offs, -0.5f);
827        glTexCoord2f(0, 1); glVertex3f(-offs,  offs, -0.5f);
828
829        glEnd();
830
831        cgGLDisableTextureParameter(sColorsTexDeferredParam);
832        cgGLDisableTextureParameter(sOldColorsTexDeferredParam);
833        cgGLDisableTextureParameter(sPositionsTexDeferredParam);
834        cgGLDisableTextureParameter(sNormalsTexDeferredParam);
835
836        cgGLDisableProfile(RenderState::sCgFragmentProfile);
837
838        FrameBufferObject::Release();
839
840        PrintGLerror("deferred shading");
841}
842
843
844
845void DeferredRenderer::ComputeGlobIllum(FrameBufferObject *fbo,
846                                                                                float tempCohFactor,
847                                                                                const Matrix4x4 &oldProjViewMatrix)
848{
849        cgGLSetMatrixParameterfc(sOldModelViewProjMatrixGiParam, (const float *)oldProjViewMatrix.x);
850
851        GLuint colorsTex = fbo->GetColorBuffer(colorBufferIdx)->GetTexture();
852        GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
853        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
854
855        // generate mip map levels for position texture
856        //glBindTexture(GL_TEXTURE_2D, positionsTex);
857        //glGenerateMipmapEXT(GL_TEXTURE_2D);
858
859        // read the second buffer, write to the first buffer
860        mFbo->Bind();
861
862        glDrawBuffers(2, mrt + mFboIndex);
863
864        GLuint oldSsaoTex = mFbo->GetColorBuffer(2 - mFboIndex)->GetTexture();
865        GLuint oldIllumTex = mFbo->GetColorBuffer(2 - mFboIndex + 1)->GetTexture();
866
867        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
868
869        cgGLEnableProfile(RenderState::sCgFragmentProfile);
870        cgGLBindProgram(sCgGiProgram);
871
872        cgGLSetTextureParameter(sPositionsTexGiParam, positionsTex);
873        cgGLEnableTextureParameter(sPositionsTexGiParam);
874
875        cgGLSetTextureParameter(sColorsTexGiParam, colorsTex);
876        cgGLEnableTextureParameter(sColorsTexGiParam);
877
878        cgGLSetTextureParameter(sNormalsTexGiParam, normalsTex);
879        cgGLEnableTextureParameter(sNormalsTexGiParam);
880
881        cgGLSetTextureParameter(sNoiseTexGiParam, noiseTex);
882        cgGLEnableTextureParameter(sNoiseTexGiParam);
883
884        cgGLSetTextureParameter(sOldSsaoTexGiParam, oldSsaoTex);
885        cgGLEnableTextureParameter(sOldSsaoTexGiParam);
886
887        cgGLSetTextureParameter(sOldIllumTexGiParam, oldIllumTex);
888        cgGLEnableTextureParameter(sOldIllumTexGiParam);
889
890        cgGLSetParameter1f(sMaxDepthGiParam, mScaleFactor);
891
892        cgGLSetParameter1f(sTemporalCoherenceGiParam, (mUseTemporalCoherence && !mRegenerateSamples) ? tempCohFactor : 0);
893
894
895        if (mUseTemporalCoherence || mRegenerateSamples)
896        {
897                mRegenerateSamples = false;
898
899                // q: should we generate new samples or only rotate the old ones?
900                // in the first case, the sample patterns look nicer, but the kernel
901                // needs longer to converge
902                GenerateSamples(mSamplingMethod);
903
904#ifdef USE_3D_SSAO
905                cgGLSetParameterArray3f(sSamplesGiParam, 0, NUM_SAMPLES, (const float *)samples3);
906#else
907                cgGLSetParameterArray2f(sSamplesGiParam, 0, NUM_SAMPLES, (const float *)samples2);
908#endif
909        }
910
911
912        Vector3 tl, tr, bl, br;
913        ComputeViewVectors(tl, tr, bl, br);
914
915        glBegin(GL_QUADS);
916
917        // note: slightly larger texture hides ambient occlusion error on border but costs resolution
918        //const float new_offs = 0.55f;
919        const float new_offs = 0.5f;
920               
921        glTexCoord2f(0, 0); glMultiTexCoord3fARB(GL_TEXTURE1_ARB, bl.x, bl.y, bl.z); glVertex3f(-new_offs, -new_offs, -0.5f);
922        glTexCoord2f(1, 0); glMultiTexCoord3fARB(GL_TEXTURE1_ARB, br.x, br.y, br.z); glVertex3f( new_offs, -new_offs, -0.5f);
923        glTexCoord2f(1, 1); glMultiTexCoord3fARB(GL_TEXTURE1_ARB, tr.x, tr.y, tr.z); glVertex3f( new_offs,  new_offs, -0.5f);
924        glTexCoord2f(0, 1); glMultiTexCoord3fARB(GL_TEXTURE1_ARB, tl.x, tl.y, tl.z); glVertex3f(-new_offs,  new_offs, -0.5f);
925
926        glEnd();
927
928        cgGLDisableTextureParameter(sColorsTexGiParam);
929        cgGLDisableTextureParameter(sPositionsTexGiParam);
930        cgGLDisableTextureParameter(sNormalsTexGiParam);
931        cgGLDisableTextureParameter(sNoiseTexGiParam);
932        cgGLDisableTextureParameter(sOldSsaoTexGiParam);
933        cgGLDisableTextureParameter(sOldIllumTexGiParam);
934
935        FrameBufferObject::Release();
936
937        PrintGLerror("globillum first pass");
938}
939
940
941void DeferredRenderer::CombineIllum(FrameBufferObject *fbo)
942{
943        GLuint colorsTex = fbo->GetColorBuffer(colorBufferIdx)->GetTexture();
944
945        GLuint ssaoTex = mFbo->GetColorBuffer(mFboIndex)->GetTexture();
946        GLuint illumTex = mFbo->GetColorBuffer(mFboIndex + 1)->GetTexture();
947
948
949        fbo->Bind();
950
951        // overwrite old color texture
952        colorBufferIdx = 3 - colorBufferIdx;
953
954        glDrawBuffers(1, mrt + colorBufferIdx);
955
956        cgGLEnableProfile(RenderState::sCgFragmentProfile);
957
958        cgGLBindProgram(sCgCombinedIllumProgram);
959
960        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
961       
962
963        cgGLSetTextureParameter(sColorsTexCombinedIllumParam, colorsTex);
964        cgGLEnableTextureParameter(sColorsTexCombinedIllumParam);
965
966        cgGLSetTextureParameter(sSsaoTexCombinedIllumParam, ssaoTex);
967        cgGLEnableTextureParameter(sSsaoTexCombinedIllumParam);
968
969        cgGLSetTextureParameter(sIllumTexCombinedIllumParam, illumTex);
970        cgGLEnableTextureParameter(sIllumTexCombinedIllumParam);
971       
972        glColor3f(1.0f, 1.0f, 1.0f);
973
974        const float offs = 0.5f;
975
976        glBegin(GL_QUADS);
977
978        glTexCoord2f(0, 0); glVertex3f(-offs, -offs, -0.5f);
979        glTexCoord2f(1, 0); glVertex3f( offs, -offs, -0.5f);
980        glTexCoord2f(1, 1); glVertex3f( offs,  offs, -0.5f);
981        glTexCoord2f(0, 1); glVertex3f(-offs,  offs, -0.5f);
982
983        glEnd();
984
985        cgGLDisableTextureParameter(sColorsTexCombinedIllumParam);
986        cgGLDisableTextureParameter(sSsaoTexCombinedIllumParam);
987        cgGLDisableTextureParameter(sIllumTexCombinedIllumParam);
988
989        cgGLDisableProfile(RenderState::sCgFragmentProfile);
990
991        FrameBufferObject::Release();
992
993        PrintGLerror("combine");
994}
995
996
997void DeferredRenderer::CombineSsao(FrameBufferObject *fbo)
998{
999        fbo->Bind();
1000
1001        GLuint colorsTex = fbo->GetColorBuffer(colorBufferIdx)->GetTexture();
1002        GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
1003        GLuint ssaoTex = mFbo->GetColorBuffer(mFboIndex)->GetTexture();
1004
1005        // overwrite old color texture
1006        colorBufferIdx = 3 - colorBufferIdx;
1007        glDrawBuffers(1, mrt + colorBufferIdx);
1008
1009        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
1010       
1011        cgGLEnableProfile(RenderState::sCgFragmentProfile);
1012
1013        cgGLBindProgram(sCgCombinedSsaoProgram);
1014
1015        cgGLSetTextureParameter(sColorsTexCombinedSsaoParam, colorsTex);
1016        cgGLEnableTextureParameter(sColorsTexCombinedSsaoParam);
1017
1018        cgGLSetTextureParameter(sSsaoTexCombinedSsaoParam, ssaoTex);
1019        cgGLEnableTextureParameter(sSsaoTexCombinedSsaoParam);
1020
1021        cgGLSetTextureParameter(sPositionsTexCombinedSsaoParam, positionsTex);
1022        cgGLEnableTextureParameter(sPositionsTexCombinedSsaoParam);
1023       
1024        glColor3f(1.0f, 1.0f, 1.0f);
1025
1026        const float offs = 0.5f;
1027
1028        glBegin(GL_QUADS);
1029
1030        glTexCoord2f(0, 0); glVertex3f(-offs, -offs, -0.5f);
1031        glTexCoord2f(1, 0); glVertex3f( offs, -offs, -0.5f);
1032        glTexCoord2f(1, 1); glVertex3f( offs,  offs, -0.5f);
1033        glTexCoord2f(0, 1); glVertex3f(-offs,  offs, -0.5f);
1034
1035        glEnd();
1036
1037        cgGLDisableTextureParameter(sColorsTexCombinedSsaoParam);
1038        cgGLDisableTextureParameter(sSsaoTexCombinedSsaoParam);
1039        cgGLDisableTextureParameter(sPositionsTexCombinedSsaoParam);
1040       
1041        cgGLDisableProfile(RenderState::sCgFragmentProfile);
1042
1043        FrameBufferObject::Release();
1044
1045        PrintGLerror("combine ssao");
1046}
1047
1048
1049void DeferredRenderer::FirstPassShadow(FrameBufferObject *fbo,
1050                                                                           DirectionalLight *light,
1051                                                                           ShadowMap *shadowMap)
1052{
1053        fbo->Bind();
1054
1055        GLuint colorsTex = fbo->GetColorBuffer(colorBufferIdx)->GetTexture();
1056
1057        GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
1058        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
1059        GLuint shadowTex = shadowMap->GetDepthTexture();
1060
1061        GLuint oldColorsTex = fbo->GetColorBuffer(3 - colorBufferIdx)->GetTexture();
1062
1063        Matrix4x4 shadowMatrix;
1064        shadowMap->GetTextureMatrix(shadowMatrix);
1065
1066        colorBufferIdx = 3 - colorBufferIdx;
1067        glDrawBuffers(1, mrt + colorBufferIdx);
1068
1069       
1070        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
1071
1072        cgGLBindProgram(sCgDeferredShadowProgram);
1073
1074        cgGLSetTextureParameter(sColorsTexShadowParam, colorsTex);
1075        cgGLEnableTextureParameter(sColorsTexShadowParam);
1076
1077        cgGLSetTextureParameter(sPositionsTexShadowParam, positionsTex);
1078        cgGLEnableTextureParameter(sPositionsTexShadowParam);
1079
1080        cgGLSetTextureParameter(sNormalsTexShadowParam, normalsTex);
1081        cgGLEnableTextureParameter(sNormalsTexShadowParam);
1082       
1083        cgGLSetTextureParameter(sShadowMapParam, shadowTex);
1084        cgGLEnableTextureParameter(sShadowMapParam);
1085
1086        cgGLSetTextureParameter(sOldColorsTexShadowParam, oldColorsTex);
1087        cgGLEnableTextureParameter(sOldColorsTexShadowParam);
1088
1089        cgGLSetParameter1f(sMaxDepthShadowParam, mScaleFactor);
1090
1091        //cgGLSetParameter1f(sSampleWidthParam, 10.0f / shadowMap->GetSize());
1092        cgGLSetParameter1f(sSampleWidthParam, 2.0f / shadowMap->GetSize());
1093       
1094         
1095        cgGLSetMatrixParameterfc(sShadowMatrixParam, (const float *)shadowMatrix.x);
1096
1097        cgGLSetTextureParameter(sNoiseTexShadowParam, noiseTex);
1098        cgGLEnableTextureParameter(sNoiseTexShadowParam);
1099
1100        Vector3 lightDir = -light->GetDirection();
1101        cgGLSetParameter3f(sLightDirShadowParam, lightDir.x, lightDir.y, lightDir.z);
1102
1103
1104        glColor3f(1.0f, 1.0f, 1.0f);
1105       
1106        glBegin(GL_QUADS);
1107
1108        float offs2 = 0.5f;
1109
1110        glTexCoord2f(0, 0); glVertex3f(-offs2, -offs2, -0.5f);
1111        glTexCoord2f(1, 0); glVertex3f( offs2, -offs2, -0.5f);
1112        glTexCoord2f(1, 1); glVertex3f( offs2,  offs2, -0.5f);
1113        glTexCoord2f(0, 1); glVertex3f(-offs2,  offs2, -0.5f);
1114
1115        glEnd();
1116
1117        cgGLDisableTextureParameter(sColorsTexShadowParam);
1118        cgGLDisableTextureParameter(sPositionsTexShadowParam);
1119        cgGLDisableTextureParameter(sNormalsTexShadowParam);
1120        cgGLDisableTextureParameter(sShadowMapParam);
1121
1122        cgGLDisableTextureParameter(sOldColorsTexShadowParam);
1123
1124        cgGLDisableTextureParameter(sNoiseTexShadowParam);
1125
1126        FrameBufferObject::Release();
1127
1128        PrintGLerror("deferred shading + shadows");
1129}
1130
1131
1132void DeferredRenderer::SetSamplingMethod(SAMPLING_METHOD s)
1133{
1134        if (s != mSamplingMethod)
1135        {
1136                mSamplingMethod = s;
1137                mRegenerateSamples = true;
1138        }
1139}
1140
1141
1142void DeferredRenderer::SetShadingMethod(SHADING_METHOD s)
1143{
1144        if (s != mShadingMethod)
1145        {
1146                mShadingMethod = s;
1147                mRegenerateSamples = true;
1148        }
1149}
1150
1151
1152void DeferredRenderer::ComputeToneParameters(FrameBufferObject *fbo,
1153                                                                                         DirectionalLight *light,
1154                                                                                         float &imageKey,
1155                                                                                         float &whiteLum,
1156                                                                                         float &middleGrey)
1157{
1158        // hack: estimate value where sky burns out
1159        whiteLum = log(1e4f);
1160       
1161        ////////////////////
1162        //-- linear interpolate brightness key depending on the current sun position
1163
1164        const float minKey = 0.09f;
1165        const float maxKey = 0.5f;
1166
1167        const float lightIntensity = DotProd(-light->GetDirection(), Vector3::UNIT_Z());
1168        middleGrey = lightIntensity * maxKey + (1.0f - lightIntensity) * minKey;
1169}
1170
1171
1172void DeferredRenderer::DownSample(FrameBufferObject *fbo)
1173{
1174        GLuint intensityTex=0;
1175       
1176        cgGLEnableProfile(RenderState::sCgFragmentProfile);
1177        cgGLBindProgram(sCgDownSampleProgram);
1178       
1179        cgGLSetTextureParameter(sIntensityTexDownSampleParam, intensityTex);
1180        cgGLEnableTextureParameter(sIntensityTexDownSampleParam);
1181}
1182
1183
1184void DeferredRenderer::ToneMap(FrameBufferObject *fbo,
1185                                                           DirectionalLight *light,
1186                                                           float imageKey,
1187                                                           float whiteLum,
1188                                                           float middleGrey)
1189{
1190        ColorBufferObject *colorBuffer = fbo->GetColorBuffer(colorBufferIdx);
1191
1192        fbo->Bind();
1193
1194        colorBufferIdx = 3 - colorBufferIdx;
1195        glDrawBuffers(1, mrt + colorBufferIdx);
1196
1197
1198        GLuint colorsTex = colorBuffer->GetTexture();
1199       
1200        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
1201
1202        cgGLEnableProfile(RenderState::sCgFragmentProfile);
1203        cgGLBindProgram(sCgToneProgram);
1204       
1205        cgGLSetTextureParameter(sColorsTexToneParam, colorsTex);
1206        cgGLEnableTextureParameter(sColorsTexToneParam);
1207
1208        cgGLSetParameter1f(sImageKeyParam, imageKey);
1209        cgGLSetParameter1f(sWhiteLumParam, whiteLum);
1210        cgGLSetParameter1f(sMiddleGreyParam, middleGrey);
1211
1212        glColor3f(1.0f, 1.0f, 1.0f);
1213
1214        glBegin(GL_QUADS);
1215
1216        // the neighbouring texels
1217        const float x_offs = 1.0f / mWidth;
1218        const float y_offs = 1.0f / mHeight;
1219
1220        SetVertex(0, 0, x_offs, y_offs);
1221        SetVertex(1, 0, x_offs, y_offs);
1222        SetVertex(1, 1, x_offs, y_offs);
1223        SetVertex(0, 1, x_offs, y_offs);
1224
1225        glEnd();
1226
1227        cgGLDisableTextureParameter(sColorsTexToneParam);
1228        FrameBufferObject::Release();
1229
1230        PrintGLerror("ToneMap");
1231}
1232
1233
1234
1235
1236} // namespace
Note: See TracBrowser for help on using the repository browser.