source: GTP/trunk/App/Demos/Vis/FriendlyCulling/src/SsaoShader.cpp @ 2875

Revision 2875, 21.0 KB checked in by mattausch, 16 years ago (diff)
Line 
1#include "SsaoShader.h"
2#include "FrameBufferObject.h"
3#include "RenderState.h"
4#include "SampleGenerator.h"
5#include "Vector3.h"
6#include "Camera.h"
7
8
9using namespace std;
10
11static GLenum mymrt[] = {GL_COLOR_ATTACHMENT0_EXT, GL_COLOR_ATTACHMENT1_EXT, GL_COLOR_ATTACHMENT2_EXT};
12
13namespace CHCDemoEngine
14{
15
16// number of ssao samples
17#define NUM_SAMPLES 10
18
19
20static CGprogram sCgSsaoProgram = NULL;
21static CGprogram sCgGiProgram = NULL;
22
23static CGprogram sCgDeferredProgram = NULL;
24static CGprogram sCgAntiAliasingProgram = NULL;
25static CGprogram sCgCombineProgram = NULL;
26
27static CGparameter sColorsTexCombineParam;
28static CGparameter sSsaoTexCombineParam;
29
30static CGparameter sColorsTexDeferredParam;
31static CGparameter sPositionsTexDeferredParam;
32static CGparameter sNormalsTexDeferredParam;
33
34
35///////////////////////////////////////7
36
37
38static CGparameter sColorsTexParam;
39static CGparameter sPositionsTexParam;
40static CGparameter sNormalsTexParam;
41
42static CGparameter sOldModelViewProjMatrixParam;
43static CGparameter sMaxDepthParam;
44static CGparameter sSamplesParam;
45static CGparameter sOldTexParam;
46static CGparameter sNoiseTexParam;
47static CGparameter sNoiseMultiplierParam;
48static CGparameter sExpFactorParam;
49
50
51///////////////////////////////////////
52
53
54static CGparameter sColorsTexGiParam;
55static CGparameter sPositionsTexGiParam;
56static CGparameter sNormalsTexGiParam;
57
58
59static CGparameter sOldModelViewProjMatrixGiParam;
60static CGparameter sMaxDepthGiParam;
61static CGparameter sSamplesGiParam;
62static CGparameter sOldSsaoTexGiParam;
63static CGparameter sOldIllumTexGiParam;
64static CGparameter sNoiseTexGiParam;
65static CGparameter sNoiseMultiplierGiParam;
66static CGparameter sExpFactorGiParam;
67
68
69////////////
70
71static CGparameter sColorsTexAntiAliasingParam;
72static CGparameter sNormalsTexAntiAliasingParam;
73
74
75static GLuint noiseTex;
76
77// ssao random spherical samples
78static Sample2 samples[NUM_SAMPLES];
79
80
81static void PrintGLerror(char *msg)
82{
83        GLenum errCode;
84        const GLubyte *errStr;
85       
86        if ((errCode = glGetError()) != GL_NO_ERROR)
87        {
88                errStr = gluErrorString(errCode);
89                fprintf(stderr,"OpenGL ERROR: %s: %s\n", errStr, msg);
90        }
91}
92
93
94/** Generate poisson disc distributed sample points on the unit disc
95*/
96static void GenerateSamples()
97{
98        static PoissonDiscSampleGenerator poisson(NUM_SAMPLES, 1.0f);
99        poisson.Generate((Sample2 *)samples);
100}
101
102
103SsaoShader::SsaoShader(int w, int h, Camera *cam, float scaleFactor):
104mWidth(w), mHeight(h),
105mCamera(cam),
106mScaleFactor(scaleFactor),
107mUseTemporalCoherence(true),
108mUseGlobIllum(false)
109{
110        ///////////
111        //-- the flip-flop fbos
112
113        mNewFbo = new FrameBufferObject(w, h, FrameBufferObject::DEPTH_NONE);
114        // the diffuse color buffer
115        mNewFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, false);
116        mNewFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, false);
117        mNewFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, false);
118       
119        mOldFbo = new FrameBufferObject(w, h, FrameBufferObject::DEPTH_NONE);
120        // the diffuse color buffer
121        mOldFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, false);
122        mOldFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, false);
123        mOldFbo->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, false);
124       
125        mFbo3 = new FrameBufferObject(w, h, FrameBufferObject::DEPTH_NONE);
126        // the diffuse color buffer
127        mFbo3->AddColorBuffer(ColorBufferObject::BUFFER_FLOAT_32, ColorBufferObject::WRAP_CLAMP_TO_EDGE, ColorBufferObject::FILTER_LINEAR, false);
128               
129
130        // create noise texture for ssao
131        CreateNoiseTex2D();
132}
133
134
135SsaoShader::~SsaoShader()
136{
137        if (sCgSsaoProgram)
138                cgDestroyProgram(sCgSsaoProgram);
139
140        DEL_PTR(mNewFbo);
141        DEL_PTR(mOldFbo);
142
143        glDeleteTextures(1, &noiseTex);
144}
145
146
147void SsaoShader::SetUseGlobIllum(bool useGlobIllum)
148{
149        mUseGlobIllum = useGlobIllum;
150}
151
152
153void SsaoShader::SetUseTemporalCoherence(bool temporal)
154{
155        mUseTemporalCoherence = temporal;
156}
157
158
159void SsaoShader::Init(CGcontext context)
160{       
161        sCgDeferredProgram =
162                cgCreateProgramFromFile(context,
163                                                                CG_SOURCE,
164                                                                "src/shaders/deferred.cg",
165                                                                RenderState::sCgFragmentProfile,
166                                                                "main",
167                                                                NULL);
168
169        if (sCgDeferredProgram != NULL)
170        {
171                cgGLLoadProgram(sCgDeferredProgram);
172
173                // we need size of texture for scaling
174                sPositionsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "positions"); 
175                sColorsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "colors"); 
176                sNormalsTexDeferredParam = cgGetNamedParameter(sCgDeferredProgram, "normals");
177        }
178        else
179                cerr << "deferred program failed to load" << endl;
180
181
182        ///////////////
183
184        sCgSsaoProgram =
185                cgCreateProgramFromFile(context,
186                                                                CG_SOURCE,
187                                                                "src/shaders/ssao.cg",
188                                                                RenderState::sCgFragmentProfile,
189                                                                "main",
190                                                                NULL);
191
192        if (sCgSsaoProgram != NULL)
193        {
194                cgGLLoadProgram(sCgSsaoProgram);
195
196                // we need size of texture for scaling
197                sPositionsTexParam = cgGetNamedParameter(sCgSsaoProgram, "positions"); 
198                sColorsTexParam = cgGetNamedParameter(sCgSsaoProgram, "colors"); 
199                sNormalsTexParam = cgGetNamedParameter(sCgSsaoProgram, "normals"); 
200                sNoiseTexParam = cgGetNamedParameter(sCgSsaoProgram, "noiseTexture");
201                sNoiseMultiplierParam = cgGetNamedParameter(sCgSsaoProgram, "noiseMultiplier");
202               
203                sOldModelViewProjMatrixParam = cgGetNamedParameter(sCgSsaoProgram, "oldModelViewProj");
204                sMaxDepthParam = cgGetNamedParameter(sCgSsaoProgram, "maxDepth");
205                sExpFactorParam = cgGetNamedParameter(sCgSsaoProgram, "expFactor");
206
207                sSamplesParam = cgGetNamedParameter(sCgSsaoProgram, "samples");
208                sOldTexParam = cgGetNamedParameter(sCgSsaoProgram, "oldTex"); 
209               
210
211                // generate samples for ssao kernel
212                GenerateSamples();
213                cgGLSetParameterArray2f(sSamplesParam, 0, NUM_SAMPLES, (const float *)samples);
214
215                cgGLSetParameter1f(sNoiseMultiplierParam, RandomValue(3.0f, 17.0f));
216        }
217        else
218                cerr << "ssao program failed to load" << endl;
219
220        sCgGiProgram =
221                cgCreateProgramFromFile(context,
222                                                                CG_SOURCE,
223                                                                "src/shaders/globillum.cg",
224                                                                RenderState::sCgFragmentProfile,
225                                                                "main",
226                                                                NULL);
227
228        if (sCgGiProgram != NULL)
229        {
230                cgGLLoadProgram(sCgGiProgram);
231
232                // we need size of texture for scaling
233                sPositionsTexGiParam = cgGetNamedParameter(sCgGiProgram, "positions"); 
234                sColorsTexGiParam = cgGetNamedParameter(sCgGiProgram, "colors"); 
235                sNormalsTexGiParam = cgGetNamedParameter(sCgGiProgram, "normals"); 
236                sNoiseTexGiParam = cgGetNamedParameter(sCgGiProgram, "noiseTexture");
237                sNoiseMultiplierGiParam = cgGetNamedParameter(sCgGiProgram, "noiseMultiplier");
238               
239                sOldModelViewProjMatrixGiParam = cgGetNamedParameter(sCgGiProgram, "oldModelViewProj");
240                sMaxDepthGiParam = cgGetNamedParameter(sCgGiProgram, "maxDepth");
241                sExpFactorGiParam = cgGetNamedParameter(sCgGiProgram, "expFactor");
242
243                sSamplesGiParam = cgGetNamedParameter(sCgGiProgram, "samples");
244               
245                sOldSsaoTexGiParam = cgGetNamedParameter(sCgGiProgram, "oldSsaoTex"); 
246                sOldIllumTexGiParam = cgGetNamedParameter(sCgGiProgram, "oldIllumTex"); 
247
248                // generate samples for ssao kernel
249                GenerateSamples();
250                cgGLSetParameterArray2f(sSamplesGiParam, 0, NUM_SAMPLES, (const float *)samples);
251
252                cgGLSetParameter1f(sNoiseMultiplierGiParam, RandomValue(3.0f, 17.0f));
253        }
254        else
255                cerr << "globillum program failed to load" << endl;
256
257        sCgAntiAliasingProgram =
258                cgCreateProgramFromFile(context,
259                                                                CG_SOURCE,
260                                                                "src/shaders/antialiasing.cg",
261                                                                RenderState::sCgFragmentProfile,
262                                                                "main",
263                                                                NULL);
264
265        if (sCgAntiAliasingProgram != NULL)
266        {
267                cgGLLoadProgram(sCgAntiAliasingProgram);
268
269                sColorsTexAntiAliasingParam = cgGetNamedParameter(sCgAntiAliasingProgram, "colors"); 
270                sNormalsTexAntiAliasingParam = cgGetNamedParameter(sCgAntiAliasingProgram, "normals");
271        }
272        else
273                cerr << "antialiasing program failed to load" << endl;
274
275
276        PrintGLerror("init");
277}
278
279
280void SsaoShader::Render(FrameBufferObject *fbo,
281                                                const Matrix4x4 &oldProjViewMatrix,
282                                                float expFactor)
283{
284       
285        // switch roles of old and new fbo
286        // the algorihm uses two input fbos, where the one
287        // contais the color buffer from the last frame,
288        // the other one will be written
289        swap(mNewFbo, mOldFbo);
290
291
292        glPushAttrib(GL_VIEWPORT_BIT);
293        glViewport(0, 0, mWidth, mHeight);
294
295        FrameBufferObject::Release();
296
297        glDrawBuffers(1, mymrt);
298
299        cgGLEnableProfile(RenderState::sCgFragmentProfile);
300
301        glDisable(GL_ALPHA_TEST);
302        glDisable(GL_TEXTURE_2D);
303        glDisable(GL_LIGHTING);
304
305        glMatrixMode(GL_PROJECTION);
306        glPushMatrix();
307        glLoadIdentity();
308
309        glMatrixMode(GL_MODELVIEW);
310        glPushMatrix();
311        glLoadIdentity();
312
313        const float offs = 0.5f;
314        glOrtho(-offs, offs, -offs, offs, 0, 1);
315
316        FirstPass(fbo);
317       
318        if (!mUseGlobIllum)
319                ComputeSsao(fbo, expFactor, oldProjViewMatrix);
320        else
321                ComputeGlobIllum(fbo, expFactor, oldProjViewMatrix);
322
323        AntiAliasing(fbo);
324
325        glEnable(GL_LIGHTING);
326        glDisable(GL_TEXTURE_2D);
327
328        glMatrixMode(GL_PROJECTION);
329        glPopMatrix();
330
331        glMatrixMode(GL_MODELVIEW);
332        glPopMatrix();
333
334        glPopAttrib();
335
336        cgGLDisableProfile(RenderState::sCgFragmentProfile);
337}
338
339
340void SsaoShader::ComputeSsao(FrameBufferObject *fbo,
341                                                         float expFactor,
342                                                         const Matrix4x4 &oldProjViewMatrix
343                                                         )
344{
345        cgGLSetMatrixParameterfc(sOldModelViewProjMatrixParam, (const float *)oldProjViewMatrix.x);
346
347        GLuint colorsTex = mFbo3->GetColorBuffer(0)->GetTexture();
348        GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
349        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
350
351        if (1)
352        {
353                // generate mip map levels for position texture
354                glBindTexture(GL_TEXTURE_2D, positionsTex);
355                glGenerateMipmapEXT(GL_TEXTURE_2D);
356        }
357
358
359        // read the second buffer, write to the first buffer
360        mNewFbo->Bind();
361        glDrawBuffers(2, mymrt);
362
363        GLuint oldTex = mOldFbo->GetColorBuffer(0)->GetTexture();
364
365        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
366
367        cgGLEnableProfile(RenderState::sCgFragmentProfile);
368        cgGLBindProgram(sCgSsaoProgram);
369
370        cgGLSetTextureParameter(sPositionsTexParam, positionsTex);
371        cgGLEnableTextureParameter(sPositionsTexParam);
372
373        cgGLSetTextureParameter(sColorsTexParam, colorsTex);
374        cgGLEnableTextureParameter(sColorsTexParam);
375
376        cgGLSetTextureParameter(sNormalsTexParam, normalsTex);
377        cgGLEnableTextureParameter(sNormalsTexParam);
378
379        cgGLSetTextureParameter(sNoiseTexParam, noiseTex);
380        cgGLEnableTextureParameter(sNoiseTexParam);
381
382        cgGLSetTextureParameter(sOldTexParam, oldTex);
383        cgGLEnableTextureParameter(sOldTexParam);
384       
385        cgGLSetParameter1f(sMaxDepthParam, mScaleFactor);
386       
387        if (mUseTemporalCoherence)
388        {
389                cgGLSetParameter1f(sNoiseMultiplierParam, RandomValue(3.0f, 17.0f));
390                cgGLSetParameter1f(sExpFactorParam, expFactor);
391
392
393                // q: should we generate new samples or only rotate the old ones?
394                // in the first case, the sample patterns look nicer, but the kernel
395                // needs longer to converge
396                GenerateSamples();
397                cgGLSetParameterArray2f(sSamplesParam, 0, NUM_SAMPLES, (const float *)samples);
398        }
399        else
400        {
401                        cgGLSetParameter1f(sExpFactorParam, 1.0f);
402        }
403
404        Vector3 tl, tr, bl, br;
405        ComputeViewVectors(tl, tr, bl, br);
406
407        glColor3f(1.0f, 1.0f, 1.0f);
408
409        glBegin(GL_QUADS);
410
411        // note: slightly larger texture hides ambient occlusion error on border but costs resolution
412        //const float new_offs = 0.55f;
413        const float new_offs = 0.5f;
414       
415        glColor3f(bl.x, bl.y, bl.z); glTexCoord2f(0, 0); glVertex3f(-new_offs, -new_offs, -0.5f);
416        glColor3f(br.x, br.y, br.z); glTexCoord2f(1, 0); glVertex3f( new_offs, -new_offs, -0.5f);
417        glColor3f(tr.x, tr.y, tr.z); glTexCoord2f(1, 1); glVertex3f( new_offs,  new_offs, -0.5f);
418        glColor3f(tl.x, tl.y, tl.z); glTexCoord2f(0, 1); glVertex3f(-new_offs,  new_offs, -0.5f);
419
420        glEnd();
421
422        cgGLDisableTextureParameter(sColorsTexParam);
423        cgGLDisableTextureParameter(sPositionsTexParam);
424        cgGLDisableTextureParameter(sNormalsTexParam);
425        cgGLDisableTextureParameter(sNoiseTexParam);
426        cgGLDisableTextureParameter(sOldTexParam);
427
428        FrameBufferObject::Release();
429
430        PrintGLerror("ssao first pass");
431}
432
433
434void SsaoShader::ComputeViewVectors(Vector3 &tl, Vector3 &tr, Vector3 &bl, Vector3 &br)
435{
436        Vector3 ftl, ftr, fbl, fbr, ntl, ntr, nbl, nbr;
437
438        mCamera->ComputePoints(ftl, ftr, fbl, fbr, ntl, ntr, nbl, nbr);
439
440#if 1 // matT: debug this!!
441       
442        bl = -Normalize(nbl - fbl);
443        br = -Normalize(nbr - fbr);
444        tl = -Normalize(ntl - ftl);
445        tr = -Normalize(ntr - ftr);
446
447#else // just take camera direction
448       
449        bl = -Normalize(mCamera->GetDirection());
450        br = -Normalize(mCamera->GetDirection());
451        tl = -Normalize(mCamera->GetDirection());
452        tr = -Normalize(mCamera->GetDirection());
453
454#endif
455
456        // normalize to 0 .. 1
457        bl = bl * 0.5f + 0.5f;
458        br = br * 0.5f + 0.5f;
459        tl = tl * 0.5f + 0.5f;
460        tr = tr * 0.5f + 0.5f;
461}
462
463
464void SsaoShader::CreateNoiseTex2D()
465{
466        //GLubyte *randomNormals = new GLubyte[mWidth * mHeight * 3];
467        float *randomNormals = new float[mWidth * mHeight * 3];
468
469        for (int i = 0; i < mWidth * mHeight * 3; i += 3)
470        {
471                // create random samples on a circle
472                const float rx = RandomValue(0, 1);
473                const float theta = 2.0f * acos(sqrt(1.0f - rx));
474
475                //randomNormals[i + 0] = (GLubyte)((cos(theta) * 0.5f + 0.5f) * 255.0f);
476                //randomNormals[i + 1] = (GLubyte)((sin(theta) * 0.5f + 0.5f) * 255.0f);
477                randomNormals[i + 0] = cos(theta);
478                randomNormals[i + 1] = sin(theta);
479                randomNormals[i + 2] = 0;
480        }
481
482        glEnable(GL_TEXTURE_2D);
483        glGenTextures(1, &noiseTex);
484        glBindTexture(GL_TEXTURE_2D, noiseTex);
485               
486        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
487        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
488        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
489        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
490
491        //glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB8, mWidth, mHeight, 0, GL_RGB, GL_UNSIGNED_BYTE, randomNormals);
492        glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA16F_ARB, mWidth, mHeight, 0, GL_RGB, GL_FLOAT, randomNormals);
493
494        glBindTexture(GL_TEXTURE_2D, 0);
495        glDisable(GL_TEXTURE_2D);
496
497        delete [] randomNormals;
498
499        cout << "created noise texture" << endl;
500
501        PrintGLerror("noisetexture");
502}
503
504
505
506static void SetVertex(float x, float y, float x_offs, float y_offs)
507{
508        glMultiTexCoord2fARB(GL_TEXTURE0_ARB, x, y); // center
509        glMultiTexCoord2fARB(GL_TEXTURE1_ARB, x - x_offs, y + y_offs); // left top
510        glMultiTexCoord2fARB(GL_TEXTURE2_ARB, x + x_offs, y - y_offs); // right bottom
511        glMultiTexCoord2fARB(GL_TEXTURE3_ARB, x + x_offs, y + y_offs); // right top
512        glMultiTexCoord2fARB(GL_TEXTURE4_ARB, x - x_offs, y - y_offs); // left bottom
513
514        glMultiTexCoord4fARB(GL_TEXTURE5_ARB, x - x_offs, y, x + x_offs, y); // left right
515        glMultiTexCoord4fARB(GL_TEXTURE6_ARB, x, y + y_offs, x, y - y_offs); // top bottom
516
517        glVertex3f(x - 0.5f, y - 0.5f, -0.5f);
518}
519
520
521void SsaoShader::AntiAliasing(FrameBufferObject *fbo)
522{
523        //GLuint colorsTex = mFbo4->GetColorBuffer(0)->GetTexture();
524        GLuint colorsTex = mNewFbo->GetColorBuffer(1)->GetTexture();
525        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
526       
527        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
528
529        cgGLEnableProfile(RenderState::sCgFragmentProfile);
530        cgGLBindProgram(sCgAntiAliasingProgram);
531       
532        cgGLSetTextureParameter(sColorsTexAntiAliasingParam, colorsTex);
533        cgGLEnableTextureParameter(sColorsTexAntiAliasingParam);
534
535        cgGLSetTextureParameter(sNormalsTexAntiAliasingParam, normalsTex);
536        cgGLEnableTextureParameter(sNormalsTexAntiAliasingParam);
537
538        glColor3f(1.0f, 1.0f, 1.0f);
539
540        float offs2 = 0.5f;
541
542        glBegin(GL_QUADS);
543
544        // the neighbouring texels
545        float x_offs = 1.0f / mWidth;
546        float y_offs = 1.0f / mHeight;
547
548        SetVertex(0, 0, x_offs, y_offs);
549        SetVertex(1, 0, x_offs, y_offs);
550        SetVertex(1, 1, x_offs, y_offs);
551        SetVertex(0, 1, x_offs, y_offs);
552
553        glEnd();
554
555        cgGLDisableTextureParameter(sColorsTexAntiAliasingParam);
556        cgGLDisableTextureParameter(sNormalsTexAntiAliasingParam);
557
558        PrintGLerror("antialiasing");
559}
560
561
562void SsaoShader::FirstPass(FrameBufferObject *fbo)
563{
564        GLuint colorsTex = fbo->GetColorBuffer(0)->GetTexture();
565        GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
566        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
567
568        mFbo3->Bind();
569        //mNewFbo->Bind();
570
571        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
572       
573        glDrawBuffers(1, mymrt);
574
575        cgGLEnableProfile(RenderState::sCgFragmentProfile);
576
577        cgGLBindProgram(sCgDeferredProgram);
578
579        cgGLSetTextureParameter(sColorsTexDeferredParam, colorsTex);
580        cgGLEnableTextureParameter(sColorsTexDeferredParam);
581
582        cgGLSetTextureParameter(sPositionsTexDeferredParam, positionsTex);
583        cgGLEnableTextureParameter(sPositionsTexDeferredParam);
584
585        cgGLSetTextureParameter(sNormalsTexDeferredParam, normalsTex);
586        cgGLEnableTextureParameter(sNormalsTexDeferredParam);
587       
588        glColor3f(1.0f, 1.0f, 1.0f);
589
590        const float offs = 0.5f;
591
592        glBegin(GL_QUADS);
593
594        glTexCoord2f(0, 0); glVertex3f(-offs, -offs, -0.5f);
595        glTexCoord2f(1, 0); glVertex3f( offs, -offs, -0.5f);
596        glTexCoord2f(1, 1); glVertex3f( offs,  offs, -0.5f);
597        glTexCoord2f(0, 1); glVertex3f(-offs,  offs, -0.5f);
598
599        glEnd();
600
601        cgGLDisableTextureParameter(sColorsTexDeferredParam);
602        cgGLDisableTextureParameter(sPositionsTexDeferredParam);
603        cgGLDisableTextureParameter(sNormalsTexDeferredParam);
604
605        cgGLDisableProfile(RenderState::sCgFragmentProfile);
606
607        FrameBufferObject::Release();
608
609        PrintGLerror("deferred shading");
610}
611
612
613void SsaoShader::ComputeGlobIllum(FrameBufferObject *fbo,
614                                                                  float expFactor,
615                                                                  const Matrix4x4 &oldProjViewMatrix
616                                                                  )
617{
618        cgGLSetMatrixParameterfc(sOldModelViewProjMatrixGiParam, (const float *)oldProjViewMatrix.x);
619
620        GLuint colorsTex = mFbo3->GetColorBuffer(0)->GetTexture();
621        GLuint positionsTex = fbo->GetColorBuffer(1)->GetTexture();
622        GLuint normalsTex = fbo->GetColorBuffer(2)->GetTexture();
623
624        if (1)
625        {
626                // generate mip map levels for position texture
627                glBindTexture(GL_TEXTURE_2D, positionsTex);
628                glGenerateMipmapEXT(GL_TEXTURE_2D);
629
630                // generate mip map levels for position texture
631                glBindTexture(GL_TEXTURE_2D, colorsTex);
632                glGenerateMipmapEXT(GL_TEXTURE_2D);
633        }
634
635
636        // read the second buffer, write to the first buffer
637        mNewFbo->Bind();
638        glDrawBuffers(3, mymrt);
639
640        GLuint oldSsaoTex = mOldFbo->GetColorBuffer(0)->GetTexture();
641        GLuint oldIllumTex = mOldFbo->GetColorBuffer(2)->GetTexture();
642
643        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
644
645        cgGLEnableProfile(RenderState::sCgFragmentProfile);
646        cgGLBindProgram(sCgGiProgram);
647
648        cgGLSetTextureParameter(sPositionsTexGiParam, positionsTex);
649        cgGLEnableTextureParameter(sPositionsTexGiParam);
650
651        cgGLSetTextureParameter(sColorsTexGiParam, colorsTex);
652        cgGLEnableTextureParameter(sColorsTexGiParam);
653
654        cgGLSetTextureParameter(sNormalsTexGiParam, normalsTex);
655        cgGLEnableTextureParameter(sNormalsTexGiParam);
656
657        cgGLSetTextureParameter(sNoiseTexGiParam, noiseTex);
658        cgGLEnableTextureParameter(sNoiseTexGiParam);
659
660        cgGLSetTextureParameter(sOldSsaoTexGiParam, oldSsaoTex);
661        cgGLEnableTextureParameter(sOldSsaoTexGiParam);
662
663        cgGLSetTextureParameter(sOldIllumTexGiParam, oldIllumTex);
664        cgGLEnableTextureParameter(sOldIllumTexGiParam);
665
666        cgGLSetParameter1f(sMaxDepthGiParam, mScaleFactor);
667
668
669        if (mUseTemporalCoherence)
670        {
671                cgGLSetParameter1f(sNoiseMultiplierGiParam, RandomValue(3.0f, 17.0f));
672                cgGLSetParameter1f(sExpFactorGiParam, expFactor);
673
674
675                // q: should we generate new samples or only rotate the old ones?
676                // in the first case, the sample patterns look nicer, but the kernel
677                // needs longer to converge
678                GenerateSamples();
679                cgGLSetParameterArray2f(sSamplesGiParam, 0, NUM_SAMPLES, (const float *)samples);
680        }
681        else
682        {
683                        cgGLSetParameter1f(sExpFactorGiParam, 1.0f);
684        }
685
686        Vector3 tl, tr, bl, br;
687        ComputeViewVectors(tl, tr, bl, br);
688
689        glColor3f(1.0f, 1.0f, 1.0f);
690
691        glBegin(GL_QUADS);
692
693        // note: slightly larger texture hides ambient occlusion error on border but costs resolution
694        //const float new_offs = 0.55f;
695        const float new_offs = 0.5f;
696       
697        glColor3f(bl.x, bl.y, bl.z); glTexCoord2f(0, 0); glVertex3f(-new_offs, -new_offs, -0.5f);
698        glColor3f(br.x, br.y, br.z); glTexCoord2f(1, 0); glVertex3f( new_offs, -new_offs, -0.5f);
699        glColor3f(tr.x, tr.y, tr.z); glTexCoord2f(1, 1); glVertex3f( new_offs,  new_offs, -0.5f);
700        glColor3f(tl.x, tl.y, tl.z); glTexCoord2f(0, 1); glVertex3f(-new_offs,  new_offs, -0.5f);
701
702        glEnd();
703
704        cgGLDisableTextureParameter(sColorsTexGiParam);
705        cgGLDisableTextureParameter(sPositionsTexGiParam);
706        cgGLDisableTextureParameter(sNormalsTexGiParam);
707        cgGLDisableTextureParameter(sNoiseTexGiParam);
708        cgGLDisableTextureParameter(sOldSsaoTexGiParam);
709        cgGLDisableTextureParameter(sOldIllumTexGiParam);
710
711        FrameBufferObject::Release();
712
713        PrintGLerror("globillum first pass");
714}
715
716
717} // namespace
Note: See TracBrowser for help on using the repository browser.