EXT_texture_env_combine

I’ve read the spec for EXT_texture_env_combine several times and I still have no idea how to use it.

What’s the diff between an operand and a source? What if one of my textures has just a alpha and no rgb?

Can anyone suggest a web page that has an englishy guide to this extension?

The spec is here if anyone is curious: http://oss.sgi.com/projects/ogl-sample/registry/EXT/texture_env_combine.txt http://oss.sgi.com/projects/ogl-sample/registry/ARB/texture_env_combine.txt

An operand works on a source. For an alpha texture, its RGB is clamped to black. It’s not a problem. I’ll dig up a small combine demo I did and modify it to do what you want, but it might take me a few hours to get it to you since I’m working on other code at the moment too.

[This message has been edited by DFrey (edited 04-28-2001).]

After alot of hacking around the multiply finally worked:

glActiveTextureARB( GL_TEXTURE0_ARB );
glEnable( GL_TEXTURE_2D );
glBindTexture( GL_TEXTURE_2D, diffuse );
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_REPLACE );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, GL_REPLACE );

glActiveTextureARB( GL_TEXTURE1_ARB );
glEnable( GL_TEXTURE_2D );
glBindTexture( GL_TEXTURE_2D, bump );
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PREVIOUS_EXT );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_ALPHA );

Although I’m not certain if it was a fluke. Anyways the new problem is how to add my specular map to the frame buffer. The specular must be done in a second pass because my Geforce MX only has 2 texture units. I suppose I could just use old fashion glBlendFunc(1,1) and no multitexture but what fun would that be.

glActiveTextureARB( GL_TEXTURE0_ARB );
glEnable( GL_TEXTURE_2D );
glBindTexture( GL_TEXTURE_2D, specular );
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_ADD );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, ???
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, ???
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_ALPHA );

glActiveTextureARB( GL_TEXTURE1_ARB );
glDisable( GL_TEXTURE_2D );

What should I use for source0 and operand0 to indicate frame buffer? My specular map is currently GL_LUMINANCE8 format. Should I change it to GL_ALPHA8 format?

[This message has been edited by Frumpy (edited 04-28-2001).]

You have to use blend to mix a texture with the framebuffer. Combine only works with textures and constants. Blending works with the final texture output, and framebuffer.

[This message has been edited by DFrey (edited 04-29-2001).]

Originally posted by DFrey:
instead of using GL_COMBINE_EXT on the first unit, just use GL_MODULATE since that is what you are configuring combine to do anyway

When I changed texUnit0 from GL_COMBINE_EXT to GL_MODULATE and changed the quad color from white to blue the final image was blueish. For texUnit0 I’ve settled on using

glActiveTextureARB( GL_TEXTURE0_ARB );
glEnable( GL_TEXTURE_2D );
glBindTexture( GL_TEXTURE_2D, diffuse );
glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE );

“An operand works on a source.”

I´m still trying to figure out how the combine extensions really works.

Works operand0 only on source0 or is it sequential like you code it?

Would the follwowing work?

  1. s0 op0 s1?
  2. s0 op0 s0?
  3. s0 op0 s1 op1 s3?

Could somone give me a shot but clear explanation, please !

Diapolo

For example lets say you have set GL_COMBINE_RGB_EXT to GL_INTERPOLATE_EXT.
Then the RGB function would be:

(op0 source0) * (op2 source2) + (op1 source1) * (1 - (op2 source2))

[This message has been edited by DFrey (edited 05-01-2001).]

OK, let´s see, if I got that !

Modulate:
(Op0 Src0) * (Op1 Src1)

Is Op the “thing” that changes the source values before the multiply in this example?

If I got it wrong, perhaps you could give a very short piece of code??

Regards,
Diapolo

I´ll try to translate some of the above code:

glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE_EXT );
glTexEnvi( GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, GL_MODULATE );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, GL_PREVIOUS_EXT );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, GL_SRC_COLOR );
glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_ALPHA );

  • Operation is Modulate

  • from the previous texenv on texture unit 0 take the source color (the texture like it was on texture unit 1)

multiply this result with

  • the alpha value of the current texture

DFrey, please?

Regards,
Diapolo

Essentially that is correct, however exactly what it does depends upon which texture unit you configure that way. If you configure unit 0 with that code, then GL_SRC_COLOR GL_PREVIOUS_EXT is the primary color. If you configure unit 1 with that code, then GL_SRC_COLOR GL_PREVIOUS_EXT is the color output of unit 0.

Other small question, how is the primary color defined?
Is it the vertex color?

And another thing, for helping me understand:
An arg for the alpha or RGB formula consists of:

  1. an op multiplied with a src?
  2. only a src?

In my example earlier where I wrote:
(op0 source0) * (op2 source2) + (op1 source1) * (1 - (op2 source2))

(op0 source0) means op0 OF source0.
so GL_SRC_COLOR GL_PREVIOUS_EXT means GL_SRC_COLOR OF GL_PREVIOUS_EXT. It was as if I was seeing the operands as unitary discrete functions that act on a source.

Each term of the function is an operand that is derived from the associated source.

Oh and regarding primary color, that is the unlit vertex color, or is determined from the colors and intensities of lights that illuminate the vertex which has a given material color. In another lighting mode, you can make the material colors simply track the vertex color.

[This message has been edited by DFrey (edited 05-02-2001).]

Sorry, if I´m asking that much, but great to get some answers from you !

An operand works on a source, right?

glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_ALPHA );

In the above example the current Texture is the source and from this source take the alpha value to work on (operand), or?
It could be said, that source is the “where to take information” from and the operand is the “what information from”.

Currently my base color should always be white with no alpha (1.0f, 1.0f, 1.0f, 1.0f), because I don´t set vertex colors (only white on init).

And the other unanswered question: an arg in the RGB / Alpha function is allways op + src (every src needs an op), or?

Oh and thanks for your patience !

Regards,
Diapolo

glTexEnvi( GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, GL_TEXTURE );
glTexEnvi( GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, GL_SRC_ALPHA );

could be translated as meaning: “let arg1 be the alpha component of this texture environment’s current texture.”

“every src needs an op”, should really be every source has an op, it is the operand that determines what part of the source is to be used as the argument.

[This message has been edited by DFrey (edited 05-02-2001).]

Thanks, now it is much clearer to me !

But what, if no operand is specified for a source?
Is there a default value for this or will it cause an error?

Regards,
Diapolo

Btw: Where could I find some samples (code + exe) for the use of these combiner functions?

[This message has been edited by Diapolo (edited 05-02-2001).]

Originally posted by Diapolo:
what, if no operand is specified for a source?

The official spec lists the starting default values for operands: http://oss.sgi.com/projects/ogl-sample/registry/EXT/texture_env_combine.txt

However if you have changed the values during runtime then the extension will used whatever it was set to last for the respective texture unit.

I have to say I’m pretty disappointed in nVidia & ATI (2 official supporting companies for EXT_texture_env_combine) for posting so little information about an important extension. I realize the official spec exists but it hardly makes any sense at all if there is no one to interpret it.

You are right, I think it´s a powerful extension and I now know how to setup and to configure it, but not what cool effects / helpful things CAN be done with it, because there is not much information / documentation !

One thing that can be done (and I have got sample code for) with it is Emboss Bump Mapping in 1 Pass, but I dislike the whole TexCoord shifting stuff (I´m not very good in the graphics math … hope this will get better)

Regards,
Diapolo