📄 tsmesh.cc
字号:
S32 & emapMethod = TSShapeInstance::smRenderData.environmentMapMethod;
S32 & dmapMethod = TSShapeInstance::smRenderData.detailMapMethod;
S32 & fogMethod = TSShapeInstance::smRenderData.fogMethod;
S32 & dmapTE = TSShapeInstance::smRenderData.detailMapTE;
S32 & emapTE = TSShapeInstance::smRenderData.environmentMapTE;
S32 & baseTE = TSShapeInstance::smRenderData.baseTE;
S32 & fogTE = TSShapeInstance::smRenderData.fogTE;
TSShapeInstance::smRenderData.detailTextureScale = 1.0f;
TSShapeInstance::smRenderData.fadeSet = false;
TSShapeInstance::smRenderData.textureMatrixPushed = false;
// initialize various sources of vertex alpha
TSShapeInstance::smRenderData.vertexAlpha.init();
TSShapeInstance::smRenderData.vertexAlpha.always = TSShapeInstance::smRenderData.alwaysAlphaValue;
// -------------------------------------------------
if (dmapMethod == TSShapeInstance::DETAIL_MAP_MULTI_1)
{
glClientActiveTextureARB(GL_TEXTURE0_ARB + dmapTE);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glClientActiveTextureARB(GL_TEXTURE0_ARB + baseTE);
// switch to detail map texture unit
glActiveTextureARB(GL_TEXTURE0_ARB + dmapTE);
glEnable(GL_TEXTURE_2D);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_MODULATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB,GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
glTexEnvf(GL_TEXTURE_ENV,GL_RGB_SCALE,2.0f);
// switch to base texture unit
glActiveTextureARB(GL_TEXTURE0_ARB + baseTE);
}
else if (dmapMethod == TSShapeInstance::DETAIL_MAP_MULTI_2)
{
glClientActiveTextureARB(GL_TEXTURE0_ARB + dmapTE);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glClientActiveTextureARB(GL_TEXTURE0_ARB + baseTE);
// switch to detail map texture unit
glActiveTextureARB(GL_TEXTURE0_ARB + dmapTE);
glEnable(GL_TEXTURE_2D);
// following used to "alpha" out detail texture
F32 f = (1.0f-TSShapeInstance::smRenderData.detailMapAlpha)*0.5f;
glTexEnvfv(GL_TEXTURE_ENV,GL_TEXTURE_ENV_COLOR,Point4F(f,f,f,1.0f-f));
// first unit computes "alpha-ed" detail texture
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_INTERPOLATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_CONSTANT);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_ALPHA);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB,GL_CONSTANT);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE2_RGB,GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND2_RGB,GL_SRC_COLOR);
// alpha: don't need it...
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_CONSTANT); // don't need alpha, maybe this'll be cheaper than alternatives
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
// second unit applies detail texture to base texture
AssertFatal(dmapTE+1==baseTE,"TSShapeInstance::setupTexturing: assertion failed (1)");
glActiveTextureARB(GL_TEXTURE0_ARB+dmapTE+1);
glEnable(GL_TEXTURE_2D);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_MODULATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB,GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
glTexEnvf(GL_TEXTURE_ENV,GL_RGB_SCALE,2.0f);
// third unit will apply lighting...
// we need to use the combine extension...we modulate by primary color rather than fragment color
glActiveTextureARB(GL_TEXTURE0_ARB+dmapTE+2);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_MODULATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB,GL_PRIMARY_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_MODULATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_ALPHA,GL_PRIMARY_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_ALPHA,GL_SRC_ALPHA);
// switch to base texture unit
glActiveTextureARB(GL_TEXTURE0_ARB + baseTE);
}
if (emapMethod == TSShapeInstance::ENVIRONMENT_MAP_MULTI_1)
{
// reflectance map == alpha of texture map (always preferred if no translucency)
// ---------------------------------
// set up second texure unit (TE #1)
glActiveTextureARB(GL_TEXTURE0_ARB + emapTE);
glEnable(GL_TEXTURE_2D);
glTexGeni(GL_S,GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
glTexGeni(GL_T,GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
glEnable(GL_TEXTURE_GEN_S);
glEnable(GL_TEXTURE_GEN_T);
// use combine extension -- RGB: interpolate between previous and current texture on previous alpha
// Alpha: previous alpha
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_INTERPOLATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE2_RGB,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND2_RGB,GL_SRC_ALPHA);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
// set the environment map
glBindTexture(GL_TEXTURE_2D, TSShapeInstance::smRenderData.environmentMapGLName);
TSShapeInstance::smRenderData.vertexAlpha.emap = TSShapeInstance::smRenderData.environmentMapAlpha;
// switch to base texture unit
glActiveTextureARB(GL_TEXTURE0_ARB + baseTE);
}
else if (emapMethod == TSShapeInstance::ENVIRONMENT_MAP_MULTI_3)
{
// ---------------------------------
// set up first texure unit (TE #1)
// Note: TE #1 bound to refelectance
// map in tsmesh
glActiveTextureARB(GL_TEXTURE0_ARB + emapTE);
glEnable(GL_TEXTURE_2D);
// use combine extension -- RGB: previous
// Alpha: modulate previous with primary color
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_MODULATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_ALPHA,GL_PRIMARY_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_ALPHA,GL_SRC_ALPHA);
// ---------------------------------
// set up second texure unit (TE #2)
glActiveTextureARB(GL_TEXTURE0_ARB + emapTE + 1);
glEnable(GL_TEXTURE_2D);
glTexGeni(GL_S,GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
glTexGeni(GL_T,GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
glEnable(GL_TEXTURE_GEN_S);
glEnable(GL_TEXTURE_GEN_T);
// use combine extension -- RGB: interpolate between previous and current texture on previous alpha
// Alpha: previous alpha
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_INTERPOLATE); // Interpolate
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_TEXTURE); // texture.color
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB,GL_PREVIOUS); // previous.color
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE2_RGB,GL_PREVIOUS); // by previous.srcalpha
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND2_RGB,GL_SRC_ALPHA);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_REPLACE); // alpha replace
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_PREVIOUS); // previous.srcalpha
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
// set the environment map
glBindTexture(GL_TEXTURE_2D, TSShapeInstance::smRenderData.environmentMapGLName);
// ---------------------------------
// set up third texure unit (TE #3)
// Note: TE #3 bound to shape texture
// in tsmesh (only uses alpha)
glActiveTextureARB(GL_TEXTURE0_ARB + emapTE);
glEnable(GL_TEXTURE_2D);
// use combine extension -- RGB: previous RGB
// Alpha: interpolate between 1 and current texture using previous alpha
// = previous.alpha + (1-previous.alpha) * current.alpha
// = 1 - (1-previous.alpha) * (1-current.alpha)
// = correct alpha value of texture w/ emap pre-blended
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_INTERPOLATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_CONSTANT);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
glTexEnvfv(GL_TEXTURE_ENV,GL_TEXTURE_ENV_COLOR,Point4F(1.0f,1.0f,1.0f,1.0f));
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_ALPHA,GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_ALPHA,GL_SRC_ALPHA);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE2_ALPHA,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND2_ALPHA,GL_SRC_ALPHA);
// set vertex color alpha
TSShapeInstance::smRenderData.vertexAlpha.emap = TSShapeInstance::smRenderData.environmentMapAlpha;
// switch to base texture unit
glActiveTextureARB(GL_TEXTURE0_ARB + baseTE);
}
if (fogMethod == TSShapeInstance::FOG_MULTI_1)
{
// ---------------------------------
// set up fog texure unit
glActiveTextureARB(GL_TEXTURE0_ARB + fogTE);
glEnable(GL_TEXTURE_2D);
glTexEnvfv(GL_TEXTURE_ENV,GL_TEXTURE_ENV_COLOR,TSShapeInstance::smRenderData.fogColor);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_RGB,GL_INTERPOLATE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_RGB,GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE1_RGB,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND1_RGB,GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND2_RGB,GL_SRC_ALPHA);
glTexEnvi(GL_TEXTURE_ENV,GL_COMBINE_ALPHA,GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE0_ALPHA,GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV,GL_OPERAND0_ALPHA,GL_SRC_ALPHA);
// the ATI Rage 128 needs a forthcoming driver to do do constant alpha blend
if (TSShapeInstance::smRenderData.fogTexture)
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE2_RGB,GL_TEXTURE);
else
glTexEnvi(GL_TEXTURE_ENV,GL_SOURCE2_RGB,GL_CONSTANT);
// bind constant fog bitmap
glBindTexture(GL_TEXTURE_2D, TSShapeInstance::smRenderData.fogHandle->getGLName());
glActiveTextureARB(GL_TEXTURE0_ARB + baseTE);
}
else if (fogMethod == TSShapeInstance::FOG_MULTI_1_TEXGEN)
{
// set up fog texure unit
glActiveTextureARB(GL_TEXTURE0_ARB + fogTE);
glEnable(GL_TEXTURE_2D);
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_DECAL);
// set up fog map
glBindTexture(GL_TEXTURE_2D, TSShapeInstance::smRenderData.fogMapHandle->getGLName());
// set up texgen equations
glTexGeni(GL_S,GL_TEXTURE_GEN_MODE, GL_OBJECT_LINEAR);
glTexGeni(GL_T,GL_TEXTURE_GEN_MODE, GL_OBJECT_LINEAR);
glEnable(GL_TEXTURE_GEN_S);
glEnable(GL_TEXTURE_GEN_T);
glTexGenfv(GL_S,GL_OBJECT_PLANE,&TSShapeInstance::smRenderData.fogTexGenS.x);
glTexGenfv(GL_T,GL_OBJECT_PLANE,&TSShapeInstance::smRenderData.fogTexGenT.x);
// return to base TE
glActiveTextureARB(GL_TEXTURE0_ARB + baseTE);
}
//----------------------------------
// set up texture enviroment for base texture
TSShapeInstance::smRenderData.materialFlags = TSMaterialList::S_Wrap | TSMaterialList::T_Wrap;
TSShapeInstance::smRenderData.materialIndex = TSDrawPrimitive::NoMaterial;
// draw one-sided...
glEnable(GL_CULL_FACE);
glFrontFace(GL_CW);
// enable vertex arrays...
glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_NORMAL_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
// when blending we modulate and draw using src_alpha, 1-src_alpha...
glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA);
// we modulate in order to apply lighting...
glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_MODULATE);
// but we don't blend by default...
glDisable(GL_BLEND);
glDepthMask(GL_TRUE);
// lighting?
TSShapeInstance::smRenderData.lightingOn = glIsEnabled(GL_LIGHTING)!=0;
// set vertex color (if emapping, vertexColor.w holds emapAlpha)
TSShapeInstance::smRenderData.vertexAlpha.set();
Point4F vertexColor(1,1,1,TSShapeInstance::smRenderData.vertexAlpha.current);
glColor4fv(vertexColor);
glMaterialfv(GL_FRONT_AND_BACK,GL_AMBIENT_AND_DIFFUSE,vertexColor);
// this should be off by default, but we'll end up turning it on asap...
glDisable(GL_TEXTURE_2D);
}
void TSMesh::resetMaterials()
{
// restore gl state changes made for dmap
if (TSShapeInstance::smRenderData.detailMapMethod==TSShapeInstance::DETAIL_MAP_MULTI_1 ||
TSShapeInstance::smRenderData.detailMapMethod==TSShapeInstance::DETAIL_MAP_MULTI_2)
{
// set detail maps texture unit
glActiveTextureARB(GL_TEXTURE0_ARB + TSShapeInstance::smRenderData.detailMapTE);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glDisable(GL_TEXTURE_2D);
// may have changed texture matrix of one of detail-texture texture-environment
if (mFabs(TSShapeInstance::smRenderData.detailTextureScale-1.0f) > 0.001f)
{
glMatrixMode(GL_TEXTURE);
glLoadIdentity();
glMatrixMode(GL_MODELVIEW);
}
if (TSShapeInstance::smRenderData.detailMapMethod==TSShapeInstance::DETAIL_MAP_MULTI_2)
{
glTexEnvfv(GL_TEXTURE_ENV,GL_TEXTURE_ENV_COLOR,Point4F(0,0,0,0));
glActiveTextureARB(GL_TEXTURE0_ARB + TSShapeInstance::smRenderData.detailMapTE+1);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glDisable(GL_TEXTURE_2D);
glTexEnvf(GL_TEXTURE_ENV,GL_RGB_SCALE,1.0f);
}
else
glTexEnvf(GL_TEXTURE_ENV,GL_RGB_SCALE,1.0f);
// disable tcoord's on detail map's TE
glClientActiveTextureARB(GL_TEXTURE0_ARB + TSShapeInstance::smRenderData.detailMapTE);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -