How to determine texture format?

I have a texture of alpha channel only using GL_ALPHA8 as internal format. The fixed pipeline shader works fine to fill rgb as 1.0f. But in GLSL, the texture() sampler function returns rgb as 0. Is there any option to set or a way to determine the texture format?

The fixed pipeline shader works fine to fill rgb as 1.0f. But in GLSL, the texture() sampler function returns rgb as 0.

I have no idea why the fixed function pipeline returns 1.0. It should return 0, the way GLSL does.

I am also wondering this. I tested one with shader and another without shader under same enables/settings. The fragment shader code has to be written as follows. BTW, I also tested the fixed function pipeline of Direct3D 9, it does fill rgb with 0.


struct VS_OUTPUT {
    vec4 color, texcoord;
};

uniform sampler2D ss1;

in VS_OUTPUT vso;
out vec4 color;

void main() {
    color = vso.color * vec4(1.0f, 1.0f, 1.0f, texture(ss1, vso.texcoord.st).a);
}

color = vso.color * vec4(1.0f, 1.0f, 1.0f, texture(ss1, vso.texcoord.st).a);

That’s overcomplicating things. You could just do this:


color.rgb = vec3(1.0);
color.a = texture(...).a;

It’s more clear as to what’s going on.

Well, it’s something like the following. But can it be faster? I suppose GPU take vec4 as primary operand just like the SSE2 instructions.


color.rgb = vso.color.rgb;
color.a = vso.color.a * texture(ss1, vso.texcoord.st).a;

It does. But then the sample is immediately fed into the TexEnv equation. The default MODULATE/REPLACE/BLEND/ADD TexEnv equations don’t use the RGB components of alpha format textures. They use the previous RGB, which could very well be 1.0 (or whatever the current color is.)

If you use TexEnv COMBINE, then you can see that the RGB components of an alpha texture are 0.0.

cool… yes, it is the current color.

… The default MODULATE/REPLACE/BLEND/ADD TexEnv equations don’t use the RGB components of alpha format textures. …

The question is yet the original one. How to do check the texture format in GLSL just as the fixed function pipeline does? It knows it is alpha format texture so that it can use rgb from TexEnv.

How to do check the texture format in GLSL just as the fixed function pipeline does? It knows it is alpha format texture so that it can use rgb from TexEnv.

It knows that because it checked the texture format when you made a glDraw* call and swapped out whatever internal shader it used with a different one. You cannot detect this from within a shader. Not with GLSL.

You should already know the texture format because you bound the texture for each unit (or if you didn’t because you are middleware, then you can query it with glGetTexLevelParameter.)

If you want to write GLSL shaders that simulate what fixed function TexEnv does, then you will need to write a bunch of different shaders, one for each combination of TexEnv equation and texture format.

Basically, implement the tables in the “Texture Environments and Texture Functions” section of the specification.

If you want to completely emulate fixed function, then you will end up with thousands/millions/billions of shader permutations (ARB_texture_env_crossbar and the other fixed function extensions lead to a combinatorial explosion of possible configurations when you have multiple units.)

For solving the original issue, I would recommend you to take a look at the texture swizzling extensions:

http://www.opengl.org/registry/specs/ARB/texture_swizzle.txt
http://www.opengl.org/registry/specs/EXT/texture_swizzle.txt

I think the extension has widespread support and can solve some of your issues (at least the one you mentioned in your original post).

Swizzling the sample doesn’t solve the original issue, since you need to combine two sources (the previous color and the texture sample) in different ways depending on the base format.

This was the original question:

I have a texture of alpha channel only using GL_ALPHA8 as internal format. The fixed pipeline shader works fine to fill rgb as 1.0f. But in GLSL, the texture() sampler function returns rgb as 0. Is there any option to set or a way to determine the texture format?

If you specify swizzling for the texture as (GL_ONE, GL_ONE, GL_ONE, GL_ALPHA) then you could expect the same functionality from both GLSL and fixed function thus you don’t have to detect the texture format.

This topic was automatically closed 183 days after the last reply. New replies are no longer allowed.