Welcome! Log In Create A New Profile

Advanced

GX texture problem

Posted by scanff 
GX texture problem
March 20, 2009 05:49PM
Hi all,

I've been converting over a class I had for MD2 models. I'm trying to load the skin texture from a file but when I view the model it looks like black tiger stripes are running through the texture. I don't think it's a stride/pitch issue as the texture does not look shifted.

I have also tested the texture from a memory tpl and it works fine to skin the model. Here's the code below, any help is appreciated. Here's what it does.

1. Load a RGB BMP and Convert to RGBA (what GX_InitTexObj wants)
2. Order the pixels into tiles of 4x4. (using wiiQuake code)
3. Create the texture.

void CMD2Model::cv_bmp_24_to_32bit(unsigned char* b,int scaled_width, int scaled_height )
{
	//expected 32 bit data 
	u8* s = b;
	u8* tmp_32 = new u8[scaled_width * scaled_height * 4];
	u8* n = tmp_32;
	
	for(int ty=0;ty<scaled_height;ty++) {
		for(int tx=0;tx<scaled_width;tx++) {
			*n++ = 255; // a
			*n++ = s[0]; //r
			*n++ = s[1]; // g
			*n++ = s[2]; // b
			s+=3;
		}
	}

	texture_buffer = new u8[scaled_width * scaled_height * 4];//(u8*)memalign(32, scaled_width * scaled_height );
	if (!texture_buffer) return;

	u8* scaled = tmp_32;
	u8* pos = (u8 *)texture_buffer;

	for (int y = 0; y < scaled_height; y +=4)
	{
			u8* row1 = (u8 *)&(scaled[scaled_width * (y + 0)]);
			u8* row2 = (u8 *)&(scaled[scaled_width * (y + 1)]);
			u8* row3 = (u8 *)&(scaled[scaled_width * (y + 2)]);
			u8* row4 = (u8 *)&(scaled[scaled_width * (y + 3)]);

			for (int x = 0; x < scaled_width; x += 4)
			{
					u8 AR[32];
					u8 GB[32];

					for (int i = 0; i < 4; i++)
					{
							u8* ptr1 = &(row1[(x + i) * 4]);
							u8* ptr2 = &(row2[(x + i) * 4]);
							u8* ptr3 = &(row3[(x + i) * 4]);
							u8* ptr4 = &(row4[(x + i) * 4]);

							AR[(i * 2) +  0] = ptr1[0];
							AR[(i * 2) +  1] = ptr1[3];
							AR[(i * 2) +  8] = ptr2[0];
							AR[(i * 2) +  9] = ptr2[3];
							AR[(i * 2) + 16] = ptr3[0];
							AR[(i * 2) + 17] = ptr3[3];
							AR[(i * 2) + 24] = ptr4[0];
							AR[(i * 2) + 25] = ptr4[3];

							GB[(i * 2) +  0] = ptr1[2];
							GB[(i * 2) +  1] = ptr1[1];
							GB[(i * 2) +  8] = ptr2[2];
							GB[(i * 2) +  9] = ptr2[1];
							GB[(i * 2) + 16] = ptr3[2];
							GB[(i * 2) + 17] = ptr3[1];
							GB[(i * 2) + 24] = ptr4[2];
							GB[(i * 2) + 25] = ptr4[1];
					}

					memcpy(pos, AR, sizeof(AR));
					pos += sizeof(AR);
					memcpy(pos, GB, sizeof(GB));
					pos += sizeof(GB);
			}
	}
	


	GX_InitTexObj(&tex_skin, texture_buffer, scaled_width, scaled_height, GX_TF_RGBA8, GX_REPEAT, GX_REPEAT, GX_FALSE);
	DCFlushRange(texture_buffer,scaled_width*scaled_height*4);
	

	//temp 32bit buffer
	delete [] tmp_32;
	tmp_32 = 0;
}

bool CMD2Model::LoadSkin( const char *filename )
{
	FILE* f = 0;
	f = fopen(filename,"rb");
	if (!f) return false;

	BITMAPINFOHEADER bih;
	BITMAPFILEHEADER bfh;

	fread(&bfh,14,1,f);
	fread(&bih,40,1,f);

	bih.biWidth = int4_swap(bih.biWidth);
	bih.biHeight = int4_swap(bih.biHeight);
	bih.biSizeImage = int4_swap(bih.biSizeImage);
	bih.biBitCount = 24;

	unsigned char* buf = 0;
	buf = new unsigned char[bih.biSizeImage];
	if (!buf) return false;

	fread(buf,bih.biSizeImage,1,f);
	fclose(f);

		
	cv_bmp_24_to_32bit(buf,bih.biWidth,bih.biHeight); //convert 24bit to 32bit

	delete [] buf;
	buf = 0;
	
	return true;

	
}
Re: GX texture problem
March 21, 2009 10:34AM
Are you sure that new aligns your texture to 32 bits? I think it doesn´t, you'd better look for some equivalent.
Re: GX texture problem
March 21, 2009 12:21PM
therefor is memalign, which he commented out.
And no, new doesn't align on a 32B boundery.
Re: GX texture problem
March 21, 2009 06:41PM
In case you want to use memalign and a nontrivial constructor (but you don't need that here), use placement new.
Re: GX texture problem
March 21, 2009 07:45PM
I was not familiar with memalign(being more a windows programmer). I have tried that too (that's why I commented it out) but it produces the same result.

e.g. - texture_buffer = (u8*)memalign(32, scaled_width * scaled_height * 4);

From what I looked up memalign is a wrapper for malloc() as my code is c++ would there be any problems using the c style memory allocations. I was always told never to use the old c functions when allocating memory in a c++ program and always use ... new .. delete.

Thanks for the help guys!
Re: GX texture problem
March 21, 2009 11:34PM
One more thing I'm noticing.

I don't think the stripes are random. It looks like every other row is taken from the bottom of the image.

For example ... The first row is correct, the second is taken from the bottom of the image, the third is correct, the fourth is the bottom of the image minus one row.
Re: GX texture problem
March 22, 2009 02:00AM
Ok fixed it. It was the Quake 4x4 tile code. I found this on plaatsoft (http://www.plaatsoft.nl/wiibrew/2009/03/) that works great. Thanks for the help
static void BitmapTo4×4RGBA(const unsigned char *src, void *dst, const unsigned int width, const unsigned int height)
Sorry, only registered users may post in this forum.

Click here to login