PDA

View Full Version : glsl dynamic reflection using FBO



glsl09
09-25-2010, 01:05 PM
hi.
Application has skybox using cube mapping, floor and 2 simple cube. i want to apply dynamic reflection mapping on one of the cube. but reflected cube looks weirdly.how can i fix problem. where i made wrong. code is below. thanks in advence

//////in init()


glGenTextures(1, &box2CubeMap);
glBindTexture(GL_TEXTURE_CUBE_MAP, box2CubeMap);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
for(int i=0; i<6; ++i)
{
glTexImage2D(cube[i], 0, GL_RGB, 512, 512, 0, GL_RGB, GL_UNSIGNED_BYTE, 0);
}


// FBO and RenderObject
glGenRenderbuffers(1, &amp;box2depthRender);
glBindRenderbuffer(GL_RENDERBUFFER, box2depthRender);
glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH_COMPONENT, 512, 512);
glBindRenderbuffer(GL_RENDERBUFFER, 0);
glGenFramebuffers(1, &amp;fbo);
glBindFramebuffer(GL_FRAMEBUFFER, fbo);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, depthTexture, 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_POSITIVE_X, box2CubeMap, 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_NEGATIVE_X, box2CubeMap, 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_POSITIVE_Y, box2CubeMap, 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, box2CubeMap, 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_POSITIVE_Z, box2CubeMap, 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, box2CubeMap, 0);

GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
if(status != GL_FRAMEBUFFER_COMPLETE)
{
exit(0);
}
glBindFramebuffer(GL_FRAMEBUFFER, 0);


/////in draw function


glBindFramebuffer(GL_FRAMEBUFFER, fbo);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, 0, 0);
glBindRenderbuffer(GL_RENDERBUFFER, box2depthRender);
glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_RENDERBUFFER, box2depthRender);
// generete cube mapping
generateENV(Vector3D(5, 3, 0));
glBindRenderbuffer(GL_RENDERBUFFER, 0);
glBindFramebuffer(GL_FRAMEBUFFER, 0);
box2prg->use();
glUniformMatrix4fv(invViewMat, 1, GL_FALSE, invView.m);
glPushMatrix();
glTranslatef(5,3,0);
glActiveTexture(GL_TEXTURE6);
glBindTexture(GL_TEXTURE_CUBE_MAP, box2CubeMap);
glEnable(GL_MULTISAMPLE);
box2();
glPopMatrix();
box2prg->disable();


///// generateENV function


void generateENV(const Vector3D&amp; v)
{
glMatrixMode(GL_PROJECTION);
glPushMatrix();
glLoadIdentity();
gluPerspective(90, 1, 0.5, 500);
glMatrixMode(GL_MODELVIEW);
glPushMatrix();

for(GLenum i= GL_TEXTURE_CUBE_MAP_POSITIVE_X ;
i < GL_TEXTURE_CUBE_MAP_POSITIVE_X +6; ++i)
{
glLoadIdentity();
switch(i)
{
case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
{
gluLookAt(v.v[0], v.v[1], v.v[2], 1, 0, 0, 0, -1, 0);
break;
}
case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
{
gluLookAt(v.v[0], v.v[1], v.v[2], -1, 0, 0, 0, -1, 0);
break;
}
case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
{
gluLookAt(v.v[0], v.v[1], v.v[2], 0, 1, 0, 0, 0, 1);
break;
}
case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
{
gluLookAt(v.v[0], v.v[1], v.v[2], 0, -1, 0, 0, 0, -1);
break;
}
case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
{
gluLookAt(v.v[0], v.v[1], v.v[2], 0, 0, 1, 0, -1, 0);
break;
}
case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
{
gluLookAt(v.v[0], v.v[1], v.v[2], 0, 0, -1, 0, -1, 0);
break;
}

glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, i, box2CubeMap, 0);

glPushMatrix();
glActiveTexture(GL_TEXTURE0);
glEnable(GL_TEXTURE_CUBE_MAP);
glBindTexture(GL_TEXTURE_CUBE_MAP, skyTexture);
glLoadIdentity();
GLfloat m[16];
glGetFloatv(GL_MODELVIEW_MATRIX, m);
m[12] = 0; m[13] = 0; m[14] = 0;
glMultMatrixf(m);
sky();
glDisable(GL_TEXTURE_CUBE_MAP);
glPopMatrix();


glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, diffuseMapTexture);
glEnable(GL_TEXTURE_2D);
//prg->use();
glPushMatrix();
floor();
glPopMatrix();
//prg->disable();
glDisable(GL_TEXTURE_2D);

//box1prg->use();
glPushMatrix();
glTranslatef(-3,2,0);
box1();
glPopMatrix();
//box1prg->disable();

glGenerateMipmap(GL_TEXTURE_CUBE_MAP);
}
}

glMatrixMode(GL_PROJECTION);
glPopMatrix();
glMatrixMode(GL_MODELVIEW);
glPopMatrix();
}



vertex shader


varying vec4 shadowCoord;
varying vec3 R;

uniform mat4 invView;

void main()
{
gl_Position = ftransform();
vec4 pos = gl_ModelViewMatrix * gl_Vertex;
vec3 E = pos.xyz;
vec3 N = gl_NormalMatrix * gl_Normal;
E = normalize(E);
N = normalize(N);
R = reflect(E, N);
R = (invView * vec4(R, 0.0)).xyz;
shadowCoord = gl_TextureMatrix[5] * pos;
}


fragment shader


varying vec4 shadowCoord;
varying vec3 R;

uniform sampler2D depthTexture;
uniform samplerCube cubeTexture;

void main()
{
float shadowFactor = texture2DProj(depthTexture, shadowCoord).g;
vec4 color = textureCube(cubeTexture, R.xyz);
gl_FragColor = color ;//* shadowFactor;
}



scene photo
http://img69.imageshack.us/img69/1675/adszdrw.jpg

ravage
09-25-2010, 05:38 PM
Did you set the correct texture unit for the cubemap which is 6? I don't see you setting it for the shader but only the function that seems to be your draw call box2().



box2prg->use();
glUniformMatrix4fv(invViewMat, 1, GL_FALSE, invView.m);
glPushMatrix();
glTranslatef(5,3,0);
glActiveTexture(GL_TEXTURE6);
glBindTexture(GL_TEXTURE_CUBE_MAP, box2CubeMap);
glEnable(GL_MULTISAMPLE);
box2();
glPopMatrix();
box2prg->disable();



I don't see a glUniform1i("cubeTexture", 6);

glsl09
09-25-2010, 06:07 PM
thanks ravage for your reply. yes i set texture unit

/// in init()


box2prg->use();
box2loc5Depth = glGetUniformLocation(box2prg->program, "depthTexture");
box2loc6Cube = glGetUniformLocation(box2prg->program, "cubeTexture");
invViewMat = glGetUniformLocation(box2prg->program, "invView");
glUniform1i(box2loc5Depth, 5);
glUniform1i(box2loc6Cube, 6);

box2prg->disable();


i changed vertex shader code to see wheter cube mapping is rendered correctly. Changed code and screen output is below

http://img689.imageshack.us/img689/4174/adsznce.jpg


// vertex shader


// R = (invView * vec4(R, 0.0)).xyz;
R = normalize(gl_NormalMatrix * gl_Normal);


but i have still problem. i think my problem arise from render to cube texture. but i cant find my mistake.

ravage
09-25-2010, 06:29 PM
Use the normal instead of the reflect(R) vector just to see if you at least get back the environment. If this doesn't give you back the environment then the setup for the fbo is weird.

vec4 color = textureCube(cubeTexture, normal.xyz);


I also had a suggestion if this by itself doesn't show any results.

you have:
gluLookAt(v.v[0], v.v[1], v.v[2], 1, 0, 0, 0, -1, 0);
etc.

Change it to:
gluLookAt(v.v[0], v.v[1], v.v[2], v.v[0]+1, v.v[1], v.v[2], 0, -1, 0);
etc.

Doing it the way you have it would cause problems if you are not at the position (0,0,0).

glsl09
09-26-2010, 12:36 PM
problem was solved. i have forgotten put curly bracket end of switch statement. thanks ravage for your help. good day