Ejemplo n.º 1
0
// using EtcPack to decode ETC1
void CodecETC1_Decode(TexDecodeTask *task)
{
	byte *data, *stream;
	int x, y, w, h;
	size_t size;

	w = task->image->width;
	h = task->image->height;
	size = w * h * task->image->bpp;
	data = (byte *)mem_alloc(size);
	stream = task->pixeldata;
	for (y = 0; y < h / 4; y++)
	{
		for (x = 0; x < w / 4; x++)
		{
			// etcpack path
			unsigned int block1, block2;
			block1 = 0;           block1 |= stream[0];
			block1 = block1 << 8; block1 |= stream[1];
			block1 = block1 << 8; block1 |= stream[2];
			block1 = block1 << 8; block1 |= stream[3];
			block2 = 0;           block2 |= stream[4];
			block2 = block2 << 8; block2 |= stream[5];
			block2 = block2 << 8; block2 |= stream[6];
			block2 = block2 << 8; block2 |= stream[7];
			stream += 8;
			// ETC2 is backwards compatible, which means that an ETC2-capable decompressor
			// can also handle old ETC1 textures without any problems.
			etcpack_decompressBlockETC2c(block1, block2, data, w, h, x*4, y*4, task->image->bpp);
		}
	}
	Image_StoreUnalignedData(task->image, data, size);
	free(data);
	task->image->colorSwap = false;
}
Ejemplo n.º 2
0
// using EtcPack to decode ETC2
void CodecETC2_Decode(TexDecodeTask *task)
{
	byte *data, *stream, rgba[4*4*4], *lb;
	unsigned int block1, block2;
	int x, y, w, h, bpp;
	int lx, ly, lw, lh;

	// init
	w = task->image->width;
	h = task->image->height;
	bpp = task->image->bpp;
	data = (byte *)mem_alloc(w * h * bpp);
	stream = task->pixeldata;

	// decode
	if (task->format->block == &B_ETC2)
	{
		for (y = 0; y < h; y+=4)
		{
			for (x = 0; x < w; x+=4)
			{
				readColorBlockETC(&stream, block1, block2);
				etcpack_decompressBlockETC2c(block1, block2, rgba, 4, 4, 0, 0, 4);
				lb = rgba;
				lh = min(y + 4, h) - y;
				lw = min(x + 4, w) - x;
				for (ly = 0; ly < lh; ly++,lb+=4*4)
					for(lx = 0; lx < lw; lx++)
						memcpy(data + (w*(y + ly) + x + lx)*bpp, lb + lx*4, 3);
			}
		}
	}
	else if (task->format->block == &B_ETC2A)
	{
		for (y = 0; y < h; y+=4)
		{
			for (x = 0; x < w; x+=4)
			{
				// EAC block + ETC2 RGB block
				etcpack_decompressBlockAlphaC(stream, rgba+3, 4, 4, 0, 0, 4);
				stream += 8;
				readColorBlockETC(&stream, block1, block2);
				etcpack_decompressBlockETC2c(block1, block2, rgba, 4, 4, 0, 0, 4);
				lb = rgba;
				lh = min(y + 4, h) - y;
				lw = min(x + 4, w) - x;
				for (ly = 0; ly < lh; ly++,lb+=4*4)
					for(lx = 0; lx < lw; lx++)
						memcpy(data + (w*(y + ly) + x + lx)*bpp, lb + lx*4, 4);
			}
		}
	}
	else if (task->format->block == &B_ETC2A1)
	{
		for (y = 0; y < h; y+=4)
		{
			for (x = 0; x < w; x+=4)
			{
				// ETC2 RGB/punchthrough alpha block 
				readColorBlockETC(&stream, block1, block2);
				etcpack_decompressBlockETC21BitAlphaC(block1, block2, rgba, NULL, 4, 4, 0, 0, 4);
				lb = rgba;
				lh = min(y + 4, h) - y;
				lw = min(x + 4, w) - x;
				for (ly = 0; ly < lh; ly++,lb+=4*4)
					for(lx = 0; lx < lw; lx++)
						memcpy(data + (w*(y + ly) + x + lx)*bpp, lb + lx*4, 4);
			}
		}
	}
	else
		Error("CodecETC2_Decode: block %s not supported\n", task->format->block->name);

	// store decoded image
	Image_StoreUnalignedData(task->image, data, w*h*bpp);
	free(data);
	task->image->colorSwap = false;
}