Make love.image automatically pad ImageData (and thus all images) to PO2.

Two notes:
- I don't think I ever clear the textures, so are they only transparent by coincidence?
- Maybe it's best if we surround the actually po2-ifying with ifs if we ever find a way to test if it's needed.
This commit is contained in:
Bart van Strien
2011-05-13 15:55:41 +02:00
parent 2acc6279fe
commit cf60754ef0
2 changed files with 86 additions and 85 deletions
+80 -85
View File
@@ -33,97 +33,19 @@ namespace image
{
namespace devil
{
void ImageData::load(Data * data)
void ImageData::createPo2(int width, int height, void * data)
{
// Generate DevIL image.
//create the image
ilGenImages(1, &image);
// Bind the image.
//bind it
ilBindImage(image);
// Try to load the image.
ILboolean success = ilLoadL(IL_TYPE_UNKNOWN, (void*)data->getData(), data->getSize());
//scale to nearest bigger po2
width = pow(2, ceil(log((double) width)/log(2.0)));
height = pow(2, ceil(log((double) height)/log(2.0)));
// Check for errors
if(!success)
{
throw love::Exception("Could not decode image!");
return;
}
width = ilGetInteger(IL_IMAGE_WIDTH);
height = ilGetInteger(IL_IMAGE_HEIGHT);
origin = ilGetInteger(IL_IMAGE_ORIGIN);
// Make sure the image is in RGBA format.
ilConvertImage(IL_RGBA, IL_UNSIGNED_BYTE);
// This should always be four.
bpp = ilGetInteger(IL_IMAGE_BPP);
if(bpp != 4)
{
std::cerr << "Bits per pixel != 4" << std::endl;
return;
}
}
ImageData::ImageData(Data * data)
{
load(data);
}
ImageData::ImageData(filesystem::File * file)
{
Data * data = file->read();
load(data);
data->release();
}
ImageData::ImageData(int width, int height)
: width(width), height(height), origin(IL_ORIGIN_UPPER_LEFT), bpp(4)
{
// Generate DevIL image.
ilGenImages(1, &image);
// Bind the image.
ilBindImage(image);
bool success = (ilTexImage(width, height, 1, bpp, IL_RGBA, IL_UNSIGNED_BYTE, 0) == IL_TRUE);
if(!success) {
int err = ilGetError();
if (err != IL_NO_ERROR){
switch (err) {
case IL_ILLEGAL_OPERATION:
throw love::Exception("Error: Illegal operation");
break;
case IL_INVALID_PARAM:
throw love::Exception("Error: invalid parameters");
break;
case IL_OUT_OF_MEMORY:
throw love::Exception("Error: out of memory");
break;
default:
throw love::Exception("Error: unknown error");
break;
}
}
throw love::Exception("Could not decode image data.");
}
// Set to black.
memset((void*)ilGetData(), 0, width*height*4);
}
ImageData::ImageData(int width, int height, void *data)
: width(width), height(height), origin(IL_ORIGIN_UPPER_LEFT), bpp(4)
{
// Generate DevIL image.
ilGenImages(1, &image);
// Bind the image.
ilBindImage(image);
// Try to load the data.
//create and populate the image
bool success = (ilTexImage(width, height, 1, bpp, IL_RGBA, IL_UNSIGNED_BYTE, data) == IL_TRUE);
if(!success) {
@@ -148,6 +70,79 @@ namespace devil
}
}
void ImageData::load(Data * data)
{
// Create a temporary image to store
// the decoded image in.
ILuint tempimage;
// Generate DevIL image.
ilGenImages(1, &tempimage);
// Bind the image.
ilBindImage(tempimage);
// Try to load the image.
ILboolean success = ilLoadL(IL_TYPE_UNKNOWN, (void*)data->getData(), data->getSize());
// Check for errors
if(!success)
{
ilDeleteImages(1, &tempimage);
throw love::Exception("Could not decode image!");
return;
}
width = ilGetInteger(IL_IMAGE_WIDTH);
height = ilGetInteger(IL_IMAGE_HEIGHT);
origin = ilGetInteger(IL_IMAGE_ORIGIN);
// Make sure the image is in RGBA format.
ilConvertImage(IL_RGBA, IL_UNSIGNED_BYTE);
// This should always be four.
bpp = ilGetInteger(IL_IMAGE_BPP);
if(bpp != 4)
{
ilDeleteImages(1, &tempimage);
std::cerr << "Bits per pixel != 4" << std::endl;
return;
}
// Create a new, PO2, image based on it
createPo2(width, height, ilGetData());
// Delete the temporary image.
ilDeleteImages(1, &tempimage);
}
ImageData::ImageData(Data * data)
{
load(data);
}
ImageData::ImageData(filesystem::File * file)
{
Data * data = file->read();
load(data);
data->release();
}
ImageData::ImageData(int width, int height)
: width(width), height(height), origin(IL_ORIGIN_UPPER_LEFT), bpp(4)
{
createPo2(width, height);
// Set to black.
memset((void*)ilGetData(), 0, width*height*4);
}
ImageData::ImageData(int width, int height, void *data)
: width(width), height(height), origin(IL_ORIGIN_UPPER_LEFT), bpp(4)
{
createPo2(width, height, data);
}
ImageData::~ImageData()
{
ilDeleteImages(1, &image);
+6
View File
@@ -32,6 +32,9 @@
// String
#include <string.h>
// Math
#include <math.h>
namespace love
{
namespace image
@@ -57,6 +60,9 @@ namespace devil
// DevIL image identifier.
ILuint image;
// Create PO2 imagedata.
void createPo2(int width, int height, void * data = 0);
void load(Data * data);
public: