#include "main/enums.h"
#include "main/macros.h"
#include "main/texenv.h"
-#include "math/m_xform.h"
+#include "main/texstate.h"
#define TE_ERROR(errCode, msg, value) \
case GL_MODULATE_ADD_ATI:
case GL_MODULATE_SIGNED_ADD_ATI:
case GL_MODULATE_SUBTRACT_ATI:
- legal =ctx->Extensions.ATI_texture_env_combine3;
+ legal = ctx->Extensions.ATI_texture_env_combine3;
+ break;
+ case GL_BUMP_ENVMAP_ATI:
+ legal = (ctx->Extensions.ATI_envmap_bumpmap &&
+ pname == GL_COMBINE_RGB);
break;
default:
legal = GL_FALSE;
struct gl_texture_unit *texUnit,
GLenum pname, GLenum param)
{
- GLuint src;
+ GLuint term;
GLboolean alpha, legal;
if (!ctx->Extensions.EXT_texture_env_combine &&
}
/*
- * Translate pname to (src, alpha).
+ * Translate pname to (term, alpha).
*/
switch (pname) {
case GL_SOURCE0_RGB:
- src = 0;
+ term = 0;
alpha = GL_FALSE;
break;
case GL_SOURCE1_RGB:
- src = 1;
+ term = 1;
alpha = GL_FALSE;
break;
case GL_SOURCE2_RGB:
- src = 2;
+ term = 2;
alpha = GL_FALSE;
break;
case GL_SOURCE3_RGB_NV:
if (ctx->Extensions.NV_texture_env_combine4) {
- src = 3;
+ term = 3;
alpha = GL_FALSE;
}
else {
}
break;
case GL_SOURCE0_ALPHA:
- src = 0;
+ term = 0;
alpha = GL_TRUE;
break;
case GL_SOURCE1_ALPHA:
- src = 1;
+ term = 1;
alpha = GL_TRUE;
break;
case GL_SOURCE2_ALPHA:
- src = 2;
+ term = 2;
alpha = GL_TRUE;
break;
case GL_SOURCE3_ALPHA_NV:
if (ctx->Extensions.NV_texture_env_combine4) {
- src = 3;
+ term = 3;
alpha = GL_TRUE;
}
else {
return;
}
- assert(src < 4);
+ assert(term < MAX_COMBINER_TERMS);
/*
* Error-check param (the source term)
FLUSH_VERTICES(ctx, _NEW_TEXTURE);
if (alpha)
- texUnit->Combine.SourceA[src] = param;
+ texUnit->Combine.SourceA[term] = param;
else
- texUnit->Combine.SourceRGB[src] = param;
+ texUnit->Combine.SourceRGB[term] = param;
}
struct gl_texture_unit *texUnit,
GLenum pname, GLenum param)
{
- GLuint op;
+ GLuint term;
GLboolean alpha, legal;
if (!ctx->Extensions.EXT_texture_env_combine &&
switch (pname) {
case GL_OPERAND0_RGB:
- op = 0;
+ term = 0;
alpha = GL_FALSE;
break;
case GL_OPERAND1_RGB:
- op = 1;
+ term = 1;
alpha = GL_FALSE;
break;
case GL_OPERAND2_RGB:
if (ctx->Extensions.ARB_texture_env_combine) {
- op = 2;
+ term = 2;
alpha = GL_FALSE;
}
else {
break;
case GL_OPERAND3_RGB_NV:
if (ctx->Extensions.NV_texture_env_combine4) {
- op = 3;
+ term = 3;
alpha = GL_FALSE;
}
else {
}
break;
case GL_OPERAND0_ALPHA:
- op = 0;
+ term = 0;
alpha = GL_TRUE;
break;
case GL_OPERAND1_ALPHA:
- op = 1;
+ term = 1;
alpha = GL_TRUE;
break;
case GL_OPERAND2_ALPHA:
if (ctx->Extensions.ARB_texture_env_combine) {
- op = 2;
+ term = 2;
alpha = GL_TRUE;
}
else {
break;
case GL_OPERAND3_ALPHA_NV:
if (ctx->Extensions.NV_texture_env_combine4) {
- op = 3;
+ term = 3;
alpha = GL_TRUE;
}
else {
return;
}
- assert(op < 4);
+ assert(term < MAX_COMBINER_TERMS);
/*
* Error-check param (the source operand)
FLUSH_VERTICES(ctx, _NEW_TEXTURE);
if (alpha)
- texUnit->Combine.OperandA[op] = param;
+ texUnit->Combine.OperandA[term] = param;
else
- texUnit->Combine.OperandRGB[op] = param;
+ texUnit->Combine.OperandRGB[term] = param;
}
return;
}
- texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
+ texUnit = _mesa_get_current_tex_unit(ctx);
if (target == GL_TEXTURE_ENV) {
switch (pname) {
case GL_ALPHA_SCALE:
set_combiner_scale(ctx, texUnit, pname, param[0]);
break;
+ case GL_BUMP_TARGET_ATI:
+ if (!ctx->Extensions.ATI_envmap_bumpmap) {
+ _mesa_error( ctx, GL_INVALID_ENUM, "glTexEnv(pname=0x%x)", pname );
+ return;
+ }
+ if (((GLenum) (GLint) param[0] < GL_TEXTURE0) ||
+ ((GLenum) (GLint) param[0] > GL_TEXTURE31)) {
+ /* spec doesn't say this but it seems logical */
+ _mesa_error( ctx, GL_INVALID_ENUM, "glTexEnv(param=0x%x)", (GLenum) (GLint) param[0]);
+ return;
+ }
+ if (!((1 << ((GLenum) (GLint) param[0] - GL_TEXTURE0)) & ctx->Const.SupportedBumpUnits)) {
+ _mesa_error( ctx, GL_INVALID_VALUE, "glTexEnv(param=0x%x)", (GLenum) (GLint) param[0]);
+ return;
+ }
+ else {
+ FLUSH_VERTICES(ctx, _NEW_TEXTURE);
+ texUnit->BumpTarget = (GLenum) (GLint) param[0];
+ }
+ break;
default:
_mesa_error( ctx, GL_INVALID_ENUM, "glTexEnv(pname)" );
return;
void GLAPIENTRY
_mesa_TexEnvf( GLenum target, GLenum pname, GLfloat param )
{
- _mesa_TexEnvfv( target, pname, ¶m );
+ GLfloat p[4];
+ p[0] = param;
+ p[1] = p[2] = p[3] = 0.0;
+ _mesa_TexEnvfv( target, pname, p );
}
_mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
}
break;
+ case GL_BUMP_TARGET_ATI:
+ /* spec doesn't say so, but I think this should be queryable */
+ if (ctx->Extensions.ATI_envmap_bumpmap) {
+ return texUnit->BumpTarget;
+ }
+ else {
+ _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
+ }
+ break;
+
default:
;
}
return;
}
- texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
+ texUnit = _mesa_get_current_tex_unit(ctx);
if (target == GL_TEXTURE_ENV) {
if (pname == GL_TEXTURE_ENV_COLOR) {
return;
}
- texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
+ texUnit = _mesa_get_current_tex_unit(ctx);
if (target == GL_TEXTURE_ENV) {
if (pname == GL_TEXTURE_ENV_COLOR) {
}
+/**
+ * Why does ATI_envmap_bumpmap require new entrypoints? Should just
+ * reuse TexEnv ones...
+ */
+void GLAPIENTRY
+_mesa_TexBumpParameterivATI( GLenum pname, const GLint *param )
+{
+ GLfloat p[4];
+ GET_CURRENT_CONTEXT(ctx);
+ ASSERT_OUTSIDE_BEGIN_END(ctx);
+
+ if (!ctx->Extensions.ATI_envmap_bumpmap) {
+ /* This isn't an "official" error case, but let's tell the user
+ * that something's wrong.
+ */
+ _mesa_error(ctx, GL_INVALID_OPERATION, "glTexBumpParameterivATI");
+ return;
+ }
+
+ if (pname == GL_BUMP_ROT_MATRIX_ATI) {
+ /* hope that conversion is correct here */
+ p[0] = INT_TO_FLOAT( param[0] );
+ p[1] = INT_TO_FLOAT( param[1] );
+ p[2] = INT_TO_FLOAT( param[2] );
+ p[3] = INT_TO_FLOAT( param[3] );
+ }
+ else {
+ p[0] = (GLfloat) param[0];
+ p[1] = p[2] = p[3] = 0.0F; /* init to zero, just to be safe */
+ }
+ _mesa_TexBumpParameterfvATI( pname, p );
+}
+
+
+void GLAPIENTRY
+_mesa_TexBumpParameterfvATI( GLenum pname, const GLfloat *param )
+{
+ struct gl_texture_unit *texUnit;
+ GET_CURRENT_CONTEXT(ctx);
+ ASSERT_OUTSIDE_BEGIN_END(ctx);
+
+ if (!ctx->Extensions.ATI_envmap_bumpmap) {
+ _mesa_error(ctx, GL_INVALID_OPERATION, "glTexBumpParameterfvATI");
+ return;
+ }
+
+ texUnit = _mesa_get_current_tex_unit(ctx);
+
+ if (pname == GL_BUMP_ROT_MATRIX_ATI) {
+ if (TEST_EQ_4V(param, texUnit->RotMatrix))
+ return;
+ FLUSH_VERTICES(ctx, _NEW_TEXTURE);
+ COPY_4FV(texUnit->RotMatrix, param);
+ }
+ else {
+ _mesa_error( ctx, GL_INVALID_ENUM, "glTexBumpParameter(pname)" );
+ return;
+ }
+ /* Drivers might want to know about this, instead of dedicated function
+ just shove it into TexEnv where it really belongs anyway */
+ if (ctx->Driver.TexEnv) {
+ (*ctx->Driver.TexEnv)( ctx, 0, pname, param );
+ }
+}
+
+
+void GLAPIENTRY
+_mesa_GetTexBumpParameterivATI( GLenum pname, GLint *param )
+{
+ const struct gl_texture_unit *texUnit;
+ GLuint i;
+ GET_CURRENT_CONTEXT(ctx);
+ ASSERT_OUTSIDE_BEGIN_END(ctx);
+
+ if (!ctx->Extensions.ATI_envmap_bumpmap) {
+ _mesa_error(ctx, GL_INVALID_OPERATION, "glGetTexBumpParameterivATI");
+ return;
+ }
+
+ texUnit = _mesa_get_current_tex_unit(ctx);
+
+ if (pname == GL_BUMP_ROT_MATRIX_SIZE_ATI) {
+ /* spec leaves open to support larger matrices.
+ Don't think anyone would ever want to use it
+ (and apps almost certainly would not understand it and
+ thus fail to submit matrices correctly) so hardcode this. */
+ *param = 4;
+ }
+ else if (pname == GL_BUMP_ROT_MATRIX_ATI) {
+ /* hope that conversion is correct here */
+ param[0] = FLOAT_TO_INT(texUnit->RotMatrix[0]);
+ param[1] = FLOAT_TO_INT(texUnit->RotMatrix[1]);
+ param[2] = FLOAT_TO_INT(texUnit->RotMatrix[2]);
+ param[3] = FLOAT_TO_INT(texUnit->RotMatrix[3]);
+ }
+ else if (pname == GL_BUMP_NUM_TEX_UNITS_ATI) {
+ GLint count = 0;
+ for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
+ if (ctx->Const.SupportedBumpUnits & (1 << i)) {
+ count++;
+ }
+ }
+ *param = count;
+ }
+ else if (pname == GL_BUMP_TEX_UNITS_ATI) {
+ for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
+ if (ctx->Const.SupportedBumpUnits & (1 << i)) {
+ *param++ = i + GL_TEXTURE0;
+ }
+ }
+ }
+ else {
+ _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexBumpParameter(pname)" );
+ return;
+ }
+}
+
+
+void GLAPIENTRY
+_mesa_GetTexBumpParameterfvATI( GLenum pname, GLfloat *param )
+{
+ const struct gl_texture_unit *texUnit;
+ GLuint i;
+ GET_CURRENT_CONTEXT(ctx);
+ ASSERT_OUTSIDE_BEGIN_END(ctx);
+
+ if (!ctx->Extensions.ATI_envmap_bumpmap) {
+ _mesa_error(ctx, GL_INVALID_OPERATION, "glGetTexBumpParameterfvATI");
+ return;
+ }
+
+ texUnit = _mesa_get_current_tex_unit(ctx);
+
+ if (pname == GL_BUMP_ROT_MATRIX_SIZE_ATI) {
+ /* spec leaves open to support larger matrices.
+ Don't think anyone would ever want to use it
+ (and apps might not understand it) so hardcode this. */
+ *param = 4.0F;
+ }
+ else if (pname == GL_BUMP_ROT_MATRIX_ATI) {
+ param[0] = texUnit->RotMatrix[0];
+ param[1] = texUnit->RotMatrix[1];
+ param[2] = texUnit->RotMatrix[2];
+ param[3] = texUnit->RotMatrix[3];
+ }
+ else if (pname == GL_BUMP_NUM_TEX_UNITS_ATI) {
+ GLint count = 0;
+ for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
+ if (ctx->Const.SupportedBumpUnits & (1 << i)) {
+ count++;
+ }
+ }
+ *param = (GLfloat) count;
+ }
+ else if (pname == GL_BUMP_TEX_UNITS_ATI) {
+ for (i = 0; i < ctx->Const.MaxTextureImageUnits; i++) {
+ if (ctx->Const.SupportedBumpUnits & (1 << i)) {
+ *param++ = (GLfloat) (i + GL_TEXTURE0);
+ }
+ }
+ }
+ else {
+ _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexBumpParameter(pname)" );
+ return;
+ }
+}