Using 2x2 RGB texture creates red lines?

I’ve been trying to track down a problem in my app and I’ve created a test app with the same problem. If I create and bind an RGB - UNSIGNED_BYTE texture of any size other than 2x2 the texture looks great, however if the texture is 2x2 red lines appear (originally noticed on my mipmaps). I changed my original mipmap to a solid blue 2x2 with the same results. Where is the red coming from?

Test app code:

{
glViewport(0, 0, Width, Height);

glMatrixMode(GL_PROJECTION);
glLoadIdentity();

gluPerspective(60, (((float)Width) / ((float)Height)), 1, 100000);

glMatrixMode(GL_MODELVIEW);
glLoadIdentity();

glBlendFunc(GL_ONE, GL_ZERO);
glEnable(GL_TEXTURE_2D);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);

glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);


unsigned char texture[48] = {0, 0, 255, 0, 0, 255, 0, 0, 255, 0, 0, 255,
							 0, 0, 255, 0, 0, 255, 0, 0, 255, 0, 0, 255,
                             0, 0, 255, 0, 0, 255, 0, 0, 255, 0, 0, 255,
							 0, 0, 255, 0, 0, 255, 0, 0, 255, 0, 0, 255};
						   //r  g  b    r  g  b    r  g  b    r  g  b
glBindTexture(GL_TEXTURE_2D, 1);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB8, 2, 2,
    	0, GL_RGB, GL_UNSIGNED_BYTE, texture);

}

Paint method:

{
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glClear(GL_DEPTH_BUFFER_BIT);
glMatrixMode(GL_MODELVIEW);

glColor3f(0, 0, 0);

glBegin(GL_TRIANGLES);
glTexCoord2f(4, 4);
glVertex3f(10, 10, -20);
glTexCoord2f(0, 4);
glVertex3f(-10, 10, -20);
glTexCoord2f(0, 0);
glVertex3f(-10, -10, -20);
glEnd();

SwapBuffers(DeviceContext);

}

Changing the width and height on the glTexImage2D to 1x1 or 4x4 will work, but 2x2 won’t. I’m my original app the highest texture size I tested was 512x512.

I’m running a GF2Pro with 40.72 drivers…

Thanks…

John.

[This message has been edited by john_at_kbs_is (edited 02-09-2003).]

Put a glPixelStorei(GL_UNPACK_ALIGNMENT, 1) before uploading the texture. Read more about it in the red book , chapter 8.

I had the same problem when I set the r_picmic cvar of quake3 (which controls minimal mipmap level to use) to a high value.Probably beacuse 2x2 textures were used close enough to be seen.
Bob:why exactly does an unpack alignment of 1 help?The red book just explains what GL_UNPACK_ALIGNMENT is.

Otherwise it’ll think that the lines are aligned on 4 bytes bounderies by default. That will work for everything down to 4x4 on normal 3 component (RGB) texture. But for lower res it’ll cause a slight offset and it’ll read outside of your memory.

Originally posted by Bob:
Put a glPixelStorei(GL_UNPACK_ALIGNMENT, 1) before uploading the texture. Read more about it in the red book , chapter 8.

Instead of torturing your hardware and perhaps the rest of the world) like that, why not just supply the alpha component, or padd each line in your image. Most good image formats are stored 4 byte aligned for this reason.

Good call… that was exactly it. I’m still not sure I understand why it worked on larger textures. You would think the load would still read in 4 components for the first pixel and then start the next pixel at the following blue component.

V-Man - I agree with you, however I have a lot of big textures and I’m trying to conserve disk real estate. Does loading this way cause a big performance hit? I would hate for my loading screen to be up annoying the user 2 – 3 times longer than it needed to be.

Thanks a lot guys!

John.

Originally posted by V-man:
[b] Instead of torturing your hardware and perhaps the rest of the world) like that, why not just supply the alpha component, or padd each line in your image. Most good image formats are stored 4 byte aligned for this reason.

[/b]

The hardware? The only thing it could affect is the speed at which the driver can process it, which would be insignificant on a 2x2 size mipmap level anyway. A good image format is IMO a format that does NOT do 4 byte alignment. Not only is it a waste of space, requires longer load time and thus slower, and is harder to deal with. If you plan on doing any kind of post processing of your loaded image you’ll probably put it into a non-padded memory anyway which due to its simper structure will enable tighter and faster code.

Originally posted by john_at_kbs_is:
Good call… that was exactly it. I’m still not sure I understand why it worked on larger textures. You would think the load would still read in 4 components for the first pixel and then start the next pixel at the following blue component.

The alignment is on a row level, not a pixel level. The performance should be fine, you shouldn’t notice any performance difference at all.

Originally posted by john_at_kbs_is:
I would hate for my loading screen to be up annoying the user 2 – 3 times longer than it needed to be.

No probably it won’t be that bad in the average case but it’s better to stick with an alignment of 4.

If this is a concern :
NVidia says that 24 bpp textures are converted to 32bpp (where the alpha is wasted space). In a document I have (OpenGL_Perf_FAQ) they say that uploading 32 bpp images can be as much as twice as fast as 24 bpp.

I have to benchmark since I update my drivers often and things change.

On the other hand, knowing that the texture contains no alpha can be a valueable information and speed things up on runtime (which I would value higher than upload speed).

The alignment is on a row level, not a pixel level.

That makes more sense, now I can see how the line appeared.

No probably it won’t be that bad in the average case but it’s better to stick with an alignment of 4.

If this is a concern :
NVidia says that 24 bpp textures are converted to 32bpp (where the alpha is wasted space). In a document I have (OpenGL_Perf_FAQ) they say that uploading 32 bpp images can be as much as twice as fast as 24 bpp.

I do remember reading that… If my load time gets ridiculous I know how to fix it now.

Thanks for the help guys…

John.