add Bitmap.to_file

This commit is contained in:
Inori 2019-09-06 18:30:37 -04:00 committed by Inori
parent 6ffb073178
commit dd9c0c50f8
5 changed files with 49 additions and 7 deletions

View file

@ -150,6 +150,7 @@ To smooth over cross-platform compatibility, functionality that you won't find i
### Bitmap
* The `Bitmap` class has one additional property: `raw_data` gets and sets the raw pixel data of a Bitmap in the form of a string. The string must be the size of the bitmap's `width*height*4`. If it is not, no error is raised, but the Bitmap will not be updated.
* The `Bitmap` class has one additional function: `to_file(path)` will save the bitmap to `path` in BMP format. This won't take opacity into account.
### Audio

View file

@ -445,6 +445,25 @@ RB_METHOD(bitmapSetRawData)
return self;
}
RB_METHOD(bitmapSaveToFile)
{
RB_UNUSED_PARAM;
VALUE str;
rb_scan_args(argc, argv, "1", &str);
SafeStringValue(str);
Bitmap *b = getPrivateData<Bitmap>(self);
try {
b->saveToFile(RSTRING_PTR(str));
} catch (const Exception &e) {
raiseRbExc(e);
}
return RUBY_Qnil;
}
RB_METHOD(bitmapInitializeCopy)
{
rb_check_argc(argc, 1);
@ -496,6 +515,7 @@ bitmapBindingInit()
_rb_define_method(klass, "raw_data", bitmapGetRawData);
_rb_define_method(klass, "raw_data=", bitmapSetRawData);
_rb_define_method(klass, "to_file", bitmapSaveToFile);
_rb_define_method(klass, "gradient_fill_rect", bitmapGradientFillRect);
_rb_define_method(klass, "clear_rect", bitmapClearRect);

View file

@ -883,9 +883,9 @@ void Bitmap::setPixel(int x, int y, const Color &color)
p->onModified(false);
}
void Bitmap::getRaw(void *output, int output_size)
bool Bitmap::getRaw(void *output, int output_size)
{
if (output_size != width()*height()*4) return;
if (output_size != width()*height()*4) return false;
guardDisposed();
@ -893,6 +893,7 @@ void Bitmap::getRaw(void *output, int output_size)
FBO::bind(p->gl.fbo);
glReadPixels(0,0,width(),height(),GL_BGRA,GL_UNSIGNED_BYTE,output);
return true;
}
void Bitmap::replaceRaw(void *pixel_data, int size)
@ -919,6 +920,27 @@ void Bitmap::replaceRaw(void *pixel_data, int size)
p->onModified();
}
void Bitmap::saveToFile(const char *filename)
{
guardDisposed();
GUARD_MEGA;
SDL_Surface *surf = SDL_CreateRGBSurface(0, width(), height(),p->format->BitsPerPixel, 0,0,0,0);
if (!surf)
throw new Exception(Exception::SDLError, "Failed to save bitmap: %s", SDL_GetError());
getRaw(surf->pixels, surf->w * surf->h * 4);
char *fn_normalized = shState->fileSystem().normalize(filename, 1, 1);
int rc = SDL_SaveBMP(surf, fn_normalized);
SDL_FreeSurface(surf);
delete fn_normalized;
if (rc) throw new Exception(Exception::SDLError, "%s", SDL_GetError());
}
void Bitmap::hueChange(int hue)
{
guardDisposed();

View file

@ -82,8 +82,9 @@ public:
Color getPixel(int x, int y) const;
void setPixel(int x, int y, const Color &color);
void getRaw(void *output, int output_size);
bool getRaw(void *output, int output_size);
void replaceRaw(void *pixel_data, int size);
void saveToFile(const char *filename);
void hueChange(int hue);

View file

@ -984,9 +984,8 @@ void Graphics::screenshot(const char *filename)
#ifdef __WIN32__
SDL_Surface *img = SDL_CreateRGBSurface(SDL_SWSURFACE, w, h, 32, 0,0,0,0);
if (!img) throw Exception(Exception::SDLError, "%s", SDL_GetError());
if (!img) throw new Exception(Exception::SDLError, "%s", SDL_GetError());
glReadBuffer(GL_FRONT);
glReadPixels(0,0,w,h,GL_BGRA,GL_UNSIGNED_BYTE, img->pixels);
#else
SDL_Surface *tmp, *img;
@ -999,7 +998,6 @@ void Graphics::screenshot(const char *filename)
throw Exception(Exception::SDLError, "%s", SDL_GetError());
}
glReadBuffer(GL_FRONT);
glReadPixels(0,0,w,h,GL_BGRA,GL_UNSIGNED_BYTE, tmp->pixels);
for (int i = 0; i < h; i++)
@ -1016,7 +1014,7 @@ void Graphics::screenshot(const char *filename)
SDL_FreeSurface(img);
delete fn_normalized;
if (rc) throw Exception(Exception::SDLError, "%s", SDL_GetError());
if (rc) throw new Exception(Exception::SDLError, "%s", SDL_GetError());
}
DEF_ATTR_RD_SIMPLE(Graphics, Brightness, int, p->brightness)