Hi all,
I’ve been playing around with the nVidia texture shader extension now for about a month. I’m running into a problem when
using the GL_DOT_PRODUCT_DIFFUSE_CUBE_MAP_NV (aka. the diffuse shader) with the GL_DOT_PRODUCT_REFLECT_CUBE_MAP_NV (aka. the
reflect) shader. According to the info that I’ve read at nVidia’s public developer’s website, the diffuse shader is supposed
to act the same as the GL_DOT_PRODUCT_TEXTURE_CUBE_MAP_NV (aka. the cube) shader. What happens is that I can get the plain
reflect shader to work and produce the same reflection with a flat colored bump map as if I were running the cubemap texgen
routines. So I know that I’ve got that one running right. If I use the cube shader itself, it accurately maps my objects just
the way I want it. Yet when I run the reflection-diffuse shaders together, I get strange results. I’m currently running a
GF2MX/400 w/ NV20Emulate, not doing anything with the register combiners, and have no idea why this isn’t working. If you
think you may know what is wrong and want to see a screenshot of what is happening, email me and I will send you one. My
basic setup code is below.
//rm := RenderMode
somegeometryclass: rawGL(GLuint rm) {
if(rm>=RM_BUMP_ENVIRONMENT) {
if((nrmtex->GetTexNumber()==0)| |(envtex->GetTexNumber()==0)) {
return;
}
glActiveTextureARB(GL_TEXTURE0_ARB);
glBindTexture(GL_TEXTURE_2D,nrmtex->GetTexNumber());
glActiveTextureARB(GL_TEXTURE3_ARB);
glBindTexture(GL_TEXTURE_CUBE_MAP_ARB,envtex->GetTexNumber());
glVertexAttribPointerNV(0,3,GL_DOUBLE,0,vtxpts);
glVertexAttribPointerNV(8,2,GL_DOUBLE,0,texpts);
glVertexAttribPointerNV(9,3,GL_DOUBLE,0,tanpts);
glVertexAttribPointerNV(10,3,GL_DOUBLE,0,binpts);
glVertexAttribPointerNV(11,3,GL_DOUBLE,0,nrmpts);
}
if(rm&RM_DIFFUSE_BUMP_ENVIRONMENT) {
if(lighttex->GetTexNumber()==0) {
return;
}
glActiveTextureARB(GL_TEXTURE2_ARB);
glBindTexture(GL_TEXTURE_CUBE_MAP_ARB,lighttex->GetTexNumber());
}
//loops to draw geometry here!
}
…
//rm := RenderMode
void ConfigRender(GLuint rm) {
for(unsigned int i=0;i<4;i=i+1) {
glActiveTextureARB(GL_TEXTURE3_ARB-j);
glClientActiveTextureARB(GL_TEXTURE3_ARB-j);
glDisable(GL_TEXTURE_2D);
glDisable(GL_TEXTURE_CUBE_MAP_ARB);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
glDisable(GL_TEXTURE_GEN_S);
glDisable(GL_TEXTURE_GEN_T);
//BUG!!! weird problems happen when disabling tex_gen_r
//glDisable(GL_TEXTURE_GEN_R);
glDisable(GL_TEXTURE_GEN_Q);
}
glDisableClientState(GL_NORMAL_ARRAY);
glDisableClientState(GL_COLOR_ARRAY);
glDisableClientState(GL_VERTEX_ARRAY);
for(j=0;j<16;j=j+1) {
glDisableClientState(GL_VERTEX_ATTRIB_ARRAY15_NV-j);
}
glDisable(GL_VERTEX_PROGRAM_NV);
glDisable(GL_TEXTURE_SHADER_NV);
if(rm==RM_NONE) {
return;
}
if(rm&RM_WIREFRAME) {
glPolygonMode(GL_FRONT_AND_BACK,GL_LINE);
glDisable(GL_CULL_FACE);
}
if(rm>=RM_BUMP_ENVIRONMENT) {
glEnable(GL_VERTEX_PROGRAM_NV);
glEnable(GL_TEXTURE_SHADER_NV);
glBindProgramNV(GL_VERTEX_PROGRAM_NV,vp_num);
glEnable(GL_TEXTURE_2D);
//turn on vertex program attrib arrays for…
// attrib_array0 ~ vertex array
// attrib_array8 ~ tex0 tex coord array ~ normal map coord
// attrib_array9 ~ tex1 tex coord array ~ surface tangent
// attrib_array10 ~ tex2 tex coord array ~ surface binormal
// attrib_array11 ~ tex3 tex coord array ~ surface normal
glEnableClientState(GL_VERTEX_ATTRIB_ARRAY0_NV);
glEnableClientState(GL_VERTEX_ATTRIB_ARRAY8_NV);
glEnableClientState(GL_VERTEX_ATTRIB_ARRAY9_NV);
glEnableClientState(GL_VERTEX_ATTRIB_ARRAY10_NV);
glEnableClientState(GL_VERTEX_ATTRIB_ARRAY11_NV);
//c[0-3] ~ projection * modelview, row major
//c[4-7] ~ modelview, row major
//c[8-11] ~ modelview, column major
//c[12-15] ~ modelview-inverse, row major
glTrackMatrixNV(GL_VERTEX_PROGRAM_NV,0,GL_MODELVIEW_PROJECTION_NV,
GL_IDENTITY_NV);
glTrackMatrixNV(GL_VERTEX_PROGRAM_NV,4,GL_MODELVIEW,
GL_IDENTITY_NV);
glTrackMatrixNV(GL_VERTEX_PROGRAM_NV,8,GL_MODELVIEW,
GL_TRANSPOSE_NV);
glTrackMatrixNV(GL_VERTEX_PROGRAM_NV,12,GL_MODELVIEW,
GL_INVERSE_NV);
//c[16-19] ~ cubemap rotation matrix
glProgramParameters4dvNV(GL_VERTEX_PROGRAM_NV,16,4,cuberot.dData);
//constants {-1,0,1,2}
glProgramParameter4dNV(GL_VERTEX_PROGRAM_NV,32,-1.0,0.0,1.0,2.0);
glActiveTextureARB(GL_TEXTURE0_ARB);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_NONE);
glTexEnvi(GL_TEXTURE_SHADER_NV,GL_SHADER_OPERATION_NV,
GL_TEXTURE_2D);
glActiveTextureARB(GL_TEXTURE1_ARB);
glTexEnvi(GL_TEXTURE_SHADER_NV,
GL_RGBA_UNSIGNED_DOT_PRODUCT_MAPPING_NV,GL_EXPAND_NORMAL_NV);
glTexEnvi(GL_TEXTURE_SHADER_NV,GL_PREVIOUS_TEXTURE_INPUT_NV,
GL_TEXTURE0_ARB);
glTexEnvi(GL_TEXTURE_SHADER_NV,GL_SHADER_OPERATION_NV,
GL_DOT_PRODUCT_NV);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_NONE);
glActiveTextureARB(GL_TEXTURE2_ARB);
if(rm&RM_DIFFUSE_BUMP_ENVIRONMENT) {
glEnable(GL_TEXTURE_CUBE_MAP_ARB);
glTexEnvi(GL_TEXTURE_SHADER_NV,GL_SHADER_OPERATION_NV,
GL_DOT_PRODUCT_DIFFUSE_CUBE_MAP_NV);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_REPLACE);
} else {
glTexEnvi(GL_TEXTURE_SHADER_NV,GL_SHADER_OPERATION_NV,
GL_DOT_PRODUCT_NV);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_NONE);
}
glTexEnvi(GL_TEXTURE_SHADER_NV,
GL_RGBA_UNSIGNED_DOT_PRODUCT_MAPPING_NV,GL_EXPAND_NORMAL_NV);
glTexEnvi(GL_TEXTURE_SHADER_NV,GL_PREVIOUS_TEXTURE_INPUT_NV,
GL_TEXTURE0_ARB);
glActiveTextureARB(GL_TEXTURE3_ARB);
glEnable(GL_TEXTURE_CUBE_MAP_ARB);
glTexEnvi(GL_TEXTURE_SHADER_NV,
GL_RGBA_UNSIGNED_DOT_PRODUCT_MAPPING_NV,GL_EXPAND_NORMAL_NV);
glTexEnvi(GL_TEXTURE_SHADER_NV,GL_PREVIOUS_TEXTURE_INPUT_NV,
GL_TEXTURE0_ARB);
glTexEnvi(GL_TEXTURE_SHADER_NV,GL_SHADER_OPERATION_NV,
GL_DOT_PRODUCT_REFLECT_CUBE_MAP_NV);
if(rm&RM_DIFFUSE_BUMP_ENVIRONMENT) {
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_MODULATE);
} else {
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_REPLACE);
}
}
}
…
//rm := RenderMode
someobjectclass: rawGL(GLuint rm) {
glMatrixMode(GL_MODELVIEW);
glPushMatrix();
//object translation & rotation here
//vertex program update values code here
glExecuteProgramNV(GL_VERTEX_STATE_PROGRAM_NV,vsp_num,junkfloatptr);
for(unsigned int i=0;i<itemcount;i=i+1) {
somegeometryclassarray[i].DrawGL(rm);
}
glPopMatrix();
}
…
//main draw loop
void DrawGL(void) {
//typical stuff like clear and perspective setup here!
glPushAttrib(GL_ALL_ATTRIB_BITS);
glPushClientAttrib(GL_CLIENT_ALL_ATTRIB_BITS);
ConfigRender(RenderMode);
for(unsigned int i=0;i<objcount;i=i+1) {
someobjectclassarray[i].DrawGL(RenderMode);
}
glPopClientAttrib();
glPopAttrib();
}
It’s 4am, I better take a quick nap before I go to work.