I've been trying to do this for some time. I can do it with a vector but with a const void*, it crashes badly!
My bad code:
Bitmaps::Bitmaps(const void* Pointer, int Width, int Height, uint32_t BitsPerPixel)
{
Pixels.clear();
memset(&Info, 0, sizeof(BITMAPINFO));
width = Width; height = Height;
size = ((width * BitsPerPixel + 31) / 32) * 4 * height;
Info.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
Info.bmiHeader.biWidth = width;
Info.bmiHeader.biHeight = height;
Info.bmiHeader.biPlanes = 1;
Info.bmiHeader.biBitCount = BitsPerPixel;
Info.bmiHeader.biCompression = BI_RGB;
Info.bmiHeader.biSizeImage = size;
bFileHeader.bfType = 0x4D42;
bFileHeader.bfOffBits = sizeof(BITMAPFILEHEADER) + sizeof(Info.bmiHeader);
bFileHeader.bfSize = bFileHeader.bfOffBits + size;
const unsigned char* BuffPos = reinterpret_cast<const unsigned char*>(&Pointer);
height = (height < 0 ? -height : height);
Pixels.resize(width * height);
for (int I = 0; I < height; I++)
{
for (int J = 0; J < width; J++)
{
Pixels[(height - 1 - I) * width + J].RGBA.B = *(BuffPos++);
Pixels[(height - 1 - I) * width + J].RGBA.G = *(BuffPos++);
Pixels[(height - 1 - I) * width + J].RGBA.R = *(BuffPos++);
Pixels[(height - 1 - I) * width + J].RGBA.A = (Info.bmiHeader.biBitCount > 24 ? *(BuffPos++) : 0);
}
if(Info.bmiHeader.biBitCount == 24)
BuffPos += width % 4;
}
}
My good code:
Bitmaps::Bitmaps(std::vector<unsigned char> &Pointer, int Width, int Height, uint32_t BitsPerPixel)
{
Pixels.clear();
memset(&Info, 0, sizeof(BITMAPINFO));
width = Width; height = Height;
size = ((width * BitsPerPixel + 31) / 32) * 4 * height;
Info.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
Info.bmiHeader.biWidth = width;
Info.bmiHeader.biHeight = height;
Info.bmiHeader.biPlanes = 1;
Info.bmiHeader.biBitCount = BitsPerPixel;
Info.bmiHeader.biCompression = BI_RGB;
Info.bmiHeader.biSizeImage = size;
bFileHeader.bfType = 0x4D42;
bFileHeader.bfOffBits = sizeof(BITMAPFILEHEADER) + sizeof(Info.bmiHeader);
bFileHeader.bfSize = bFileHeader.bfOffBits + size;
unsigned char* BuffPos = &Pointer[0];
height = (height < 0 ? -height : height);
Pixels.resize(width * height);
for (int I = 0; I < height; I++)
{
for (int J = 0; J < width; J++)
{
Pixels[(height - 1 - I) * width + J].RGBA.B = *(BuffPos++);
Pixels[(height - 1 - I) * width + J].RGBA.G = *(BuffPos++);
Pixels[(height - 1 - I) * width + J].RGBA.R = *(BuffPos++);
Pixels[(height - 1 - I) * width + J].RGBA.A = (Info.bmiHeader.biBitCount > 24 ? *(BuffPos++) : 0);
}
if(Info.bmiHeader.biBitCount == 24)
BuffPos += width % 4;
}
}
Why does the first one crash? :S I've tried everything.
I use it like:
void __stdcall MyHook_glTexImage2D(GLenum target, GLint level, GLint internalformat, GLsizei width, GLsizei height, GLint border, GLint format, GLenum type, const GLvoid *pixels)
{
if (target == GL_TEXTURE_RECTANGLE || target == GL_TEXTURE_2D)
{
Bitmaps BMP(pixels, width, height, 32);
std::string SavePath = "C:/Users/Foo/Desktop/Images/Foo.bmp"/* + ToString(PI.ID) + ".bmp"*/;
BMP.Save(SavePath.c_str());
}
(*sys_glTexImage2D) (target, level, internalformat, width, height, border, format, type, pixels);
}