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

Revision 2886, 25.6 KB checked in by mattausch, 16 years ago (diff)

using gaussian distribution for sampling

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