Improving constness and encapsulation of surface:
Provide a read-only access to pixels data and use it when appropriate. Remove last use of SDL_Surface reference outside of surface.
This commit is contained in:
parent
28bf4f69c7
commit
33d1de9cf0
4 changed files with 73 additions and 43 deletions
|
@ -56,8 +56,8 @@ static SDL_Cursor* create_cursor(surface surf)
|
|||
|
||||
// See http://sdldoc.csn.ul.ie/sdlcreatecursor.php for documentation
|
||||
// on the format that data has to be in to pass to SDL_CreateCursor
|
||||
surface_lock lock(nsurf);
|
||||
const Uint32* const pixels = reinterpret_cast<Uint32*>(lock.pixels());
|
||||
const_surface_lock lock(nsurf);
|
||||
const Uint32* const pixels = lock.pixels();
|
||||
for(int y = 0; y != nsurf->h; ++y) {
|
||||
for(int x = 0; x != nsurf->w; ++x) {
|
||||
|
||||
|
|
|
@ -881,7 +881,7 @@ const SDL_Rect& game_display::calculate_energy_bar(surface surf)
|
|||
|
||||
surface image(make_neutral_surface(surf));
|
||||
|
||||
surface_lock image_lock(image);
|
||||
const_surface_lock image_lock(image);
|
||||
const Uint32* const begin = image_lock.pixels();
|
||||
|
||||
for(int y = 0; y != image->h; ++y) {
|
||||
|
|
|
@ -28,14 +28,20 @@
|
|||
#include <cstring>
|
||||
#include <iostream>
|
||||
|
||||
surface_lock::surface_lock(const surface &surf) : surface_(surf), locked_(false)
|
||||
|
||||
/// Check that the surface is neutral bpp 32, possibly with an empty alpha channel.
|
||||
inline bool is_neutral(const surface& surf)
|
||||
{
|
||||
return (surf->format->BytesPerPixel == 4 &&
|
||||
surf->format->Rmask == 0xFF0000u &&
|
||||
(surf->format->Amask | 0xFF000000u) == 0xFF000000u);
|
||||
}
|
||||
|
||||
surface_lock::surface_lock(surface &surf) : surface_(surf), locked_(false)
|
||||
{
|
||||
assert(is_neutral(surface_));
|
||||
if (SDL_MUSTLOCK(surface_))
|
||||
locked_ = SDL_LockSurface(surface_) == 0;
|
||||
// Check that the surface is neutral bpp 32, possibly with an empty alpha channel.
|
||||
assert(surface_->format->BytesPerPixel == 4 &&
|
||||
surface_->format->Rmask == 0xFF0000u &&
|
||||
(surface_->format->Amask | 0xFF000000u) == 0xFF000000u);
|
||||
}
|
||||
|
||||
surface_lock::~surface_lock()
|
||||
|
@ -44,6 +50,19 @@ surface_lock::~surface_lock()
|
|||
SDL_UnlockSurface(surface_);
|
||||
}
|
||||
|
||||
const_surface_lock::const_surface_lock(const surface &surf) : surface_(surf), locked_(false)
|
||||
{
|
||||
assert(is_neutral(surface_));
|
||||
if (SDL_MUSTLOCK(surface_))
|
||||
locked_ = SDL_LockSurface(surface_) == 0;
|
||||
}
|
||||
|
||||
const_surface_lock::~const_surface_lock()
|
||||
{
|
||||
if (locked_)
|
||||
SDL_UnlockSurface(surface_);
|
||||
}
|
||||
|
||||
SDL_Color int_to_color(const Uint32 rgb)
|
||||
{
|
||||
SDL_Color result;
|
||||
|
@ -232,11 +251,11 @@ surface stretch_surface_horizontal(
|
|||
|
||||
{
|
||||
// Extra scoping used for the surface_lock.
|
||||
surface_lock src_lock(src);
|
||||
const_surface_lock src_lock(src);
|
||||
surface_lock dst_lock(dst);
|
||||
|
||||
Uint32* const src_pixels = reinterpret_cast<Uint32*>(src_lock.pixels());
|
||||
Uint32* dst_pixels = reinterpret_cast<Uint32*>(dst_lock.pixels());
|
||||
const Uint32* const src_pixels = src_lock.pixels();
|
||||
Uint32* dst_pixels = dst_lock.pixels();
|
||||
|
||||
for(unsigned y = 0; y < static_cast<unsigned>(src->h); ++y) {
|
||||
const Uint32 pixel = src_pixels [y * src->w];
|
||||
|
@ -277,11 +296,11 @@ surface stretch_surface_vertical(
|
|||
|
||||
{
|
||||
// Extra scoping used for the surface_lock.
|
||||
surface_lock src_lock(src);
|
||||
const_surface_lock src_lock(src);
|
||||
surface_lock dst_lock(dst);
|
||||
|
||||
Uint32* const src_pixels = reinterpret_cast<Uint32*>(src_lock.pixels());
|
||||
Uint32* dst_pixels = reinterpret_cast<Uint32*>(dst_lock.pixels());
|
||||
const Uint32* const src_pixels = src_lock.pixels();
|
||||
Uint32* dst_pixels = dst_lock.pixels();
|
||||
|
||||
for(unsigned y = 0; y < static_cast<unsigned>(h); ++y) {
|
||||
for(unsigned x = 0; x < static_cast<unsigned>(src->w); ++x) {
|
||||
|
@ -328,11 +347,11 @@ surface scale_surface(const surface &surf, int w, int h, bool optimize)
|
|||
const fixed_t yratio = fxpdiv(surf->h,h);
|
||||
|
||||
{
|
||||
surface_lock src_lock(src);
|
||||
const_surface_lock src_lock(src);
|
||||
surface_lock dst_lock(dst);
|
||||
|
||||
Uint32* const src_pixels = reinterpret_cast<Uint32*>(src_lock.pixels());
|
||||
Uint32* const dst_pixels = reinterpret_cast<Uint32*>(dst_lock.pixels());
|
||||
const Uint32* const src_pixels = src_lock.pixels();
|
||||
Uint32* const dst_pixels = dst_lock.pixels();
|
||||
|
||||
fixed_t ysrc = ftofxp(0.0);
|
||||
for(int ydst = 0; ydst != h; ++ydst, ysrc += yratio) {
|
||||
|
@ -341,7 +360,7 @@ surface scale_surface(const surface &surf, int w, int h, bool optimize)
|
|||
const int xsrcint = fxptoi(xsrc);
|
||||
const int ysrcint = fxptoi(ysrc);
|
||||
|
||||
Uint32* const src_word = src_pixels + ysrcint*src->w + xsrcint;
|
||||
const Uint32* const src_word = src_pixels + ysrcint*src->w + xsrcint;
|
||||
Uint32* const dst_word = dst_pixels + ydst*dst->w + xdst;
|
||||
const int dx = (xsrcint + 1 < src->w) ? 1 : 0;
|
||||
const int dy = (ysrcint + 1 < src->h) ? src->w : 0;
|
||||
|
@ -489,11 +508,11 @@ surface scale_opaque_surface(const surface &surf, int w, int h, bool optimize_fo
|
|||
const fixed_t yratio = fxpdiv(surf->h,h);
|
||||
|
||||
{
|
||||
surface_lock src_lock(src);
|
||||
const_surface_lock src_lock(src);
|
||||
surface_lock dst_lock(dst);
|
||||
|
||||
Uint32* const src_pixels = reinterpret_cast<Uint32*>(src_lock.pixels());
|
||||
Uint32* const dst_pixels = reinterpret_cast<Uint32*>(dst_lock.pixels());
|
||||
const Uint32* const src_pixels = src_lock.pixels();
|
||||
Uint32* const dst_pixels = dst_lock.pixels();
|
||||
|
||||
fixed_t ysrc = ftofxp(0.0);
|
||||
for(int ydst = 0; ydst != h; ++ydst, ysrc += yratio) {
|
||||
|
@ -502,7 +521,7 @@ surface scale_opaque_surface(const surface &surf, int w, int h, bool optimize_fo
|
|||
const int xsrcint = fxptoi(xsrc);
|
||||
const int ysrcint = fxptoi(ysrc);
|
||||
|
||||
Uint32* const src_word = src_pixels + ysrcint*src->w + xsrcint;
|
||||
const Uint32* const src_word = src_pixels + ysrcint*src->w + xsrcint;
|
||||
Uint32* const dst_word = dst_pixels + ydst*dst->w + xdst;
|
||||
const int dx = (xsrcint + 1 < src->w) ? 1 : 0;
|
||||
const int dy = (ysrcint + 1 < src->h) ? src->w : 0;
|
||||
|
@ -579,11 +598,11 @@ surface scale_surface_blended(const surface &surf, int w, int h, bool optimize)
|
|||
static_cast<double>(h);
|
||||
|
||||
{
|
||||
surface_lock src_lock(src);
|
||||
const_surface_lock src_lock(src);
|
||||
surface_lock dst_lock(dst);
|
||||
|
||||
Uint32* const src_pixels = reinterpret_cast<Uint32*>(src_lock.pixels());
|
||||
Uint32* const dst_pixels = reinterpret_cast<Uint32*>(dst_lock.pixels());
|
||||
const Uint32* const src_pixels = src_lock.pixels();
|
||||
Uint32* const dst_pixels = dst_lock.pixels();
|
||||
|
||||
double ysrc = 0.0;
|
||||
for(int ydst = 0; ydst != h; ++ydst, ysrc += yratio) {
|
||||
|
@ -941,12 +960,12 @@ surface mask_surface(const surface &surf, const surface &mask)
|
|||
|
||||
{
|
||||
surface_lock lock(nsurf);
|
||||
surface_lock mlock(nmask);
|
||||
const_surface_lock mlock(nmask);
|
||||
|
||||
Uint32* beg = lock.pixels();
|
||||
Uint32* end = beg + nsurf->w*surf->h;
|
||||
Uint32* mbeg = mlock.pixels();
|
||||
Uint32* mend = mbeg + nmask->w*nmask->h;
|
||||
const Uint32* mbeg = mlock.pixels();
|
||||
const Uint32* mend = mbeg + nmask->w*nmask->h;
|
||||
|
||||
while(beg != end && mbeg != mend) {
|
||||
Uint8 alpha = (*beg) >> 24;
|
||||
|
@ -996,10 +1015,10 @@ bool in_mask_surface(const surface &surf, const surface &mask)
|
|||
|
||||
{
|
||||
surface_lock lock(nsurf);
|
||||
surface_lock mlock(nmask);
|
||||
const_surface_lock mlock(nmask);
|
||||
|
||||
Uint32* mbeg = mlock.pixels();
|
||||
Uint32* mend = mbeg + nmask->w*nmask->h;
|
||||
const Uint32* mbeg = mlock.pixels();
|
||||
const Uint32* mend = mbeg + nmask->w*nmask->h;
|
||||
Uint32* beg = lock.pixels();
|
||||
// no need for 'end', because both surfaces have same size
|
||||
|
||||
|
@ -1108,12 +1127,12 @@ surface light_surface(const surface &surf, const surface &lightmap, bool optimiz
|
|||
}
|
||||
{
|
||||
surface_lock lock(nsurf);
|
||||
surface_lock llock(nlightmap);
|
||||
const_surface_lock llock(nlightmap);
|
||||
|
||||
Uint32* beg = lock.pixels();
|
||||
Uint32* end = beg + nsurf->w * nsurf->h;
|
||||
Uint32* lbeg = llock.pixels();
|
||||
Uint32* lend = lbeg + nlightmap->w * nlightmap->h;
|
||||
const Uint32* lbeg = llock.pixels();
|
||||
const Uint32* lend = lbeg + nlightmap->w * nlightmap->h;
|
||||
|
||||
while(beg != end && lbeg != lend) {
|
||||
Uint8 alpha = (*beg) >> 24;
|
||||
|
@ -1437,14 +1456,14 @@ surface cut_surface(const surface &surf, SDL_Rect const &r)
|
|||
if(src_rect.x >= surf->w || src_rect.y >= surf->h)
|
||||
return res;
|
||||
|
||||
surface_lock slock(surf);
|
||||
const_surface_lock slock(surf);
|
||||
surface_lock rlock(res);
|
||||
|
||||
Uint8* src = reinterpret_cast<Uint8 *>(slock.pixels());
|
||||
const Uint8* src = reinterpret_cast<const Uint8 *>(slock.pixels());
|
||||
Uint8* dest = reinterpret_cast<Uint8 *>(rlock.pixels());
|
||||
|
||||
for(int y = 0; y < src_rect.h && (src_rect.y + y) < surf->h; ++y) {
|
||||
Uint8* line_src = src + (src_rect.y + y) * spitch + src_rect.x * sbpp;
|
||||
const Uint8* line_src = src + (src_rect.y + y) * spitch + src_rect.x * sbpp;
|
||||
Uint8* line_dest = dest + (dst_rect.y + y) * rpitch + dst_rect.x * rbpp;
|
||||
size_t size = src_rect.w + src_rect.x <= surf->w ? src_rect.w : surf->w - src_rect.x;
|
||||
|
||||
|
@ -1649,11 +1668,11 @@ void blit_surface(const surface& src,
|
|||
|
||||
{
|
||||
// Extra scoping used for the surface_lock.
|
||||
surface_lock src_lock(src);
|
||||
const_surface_lock src_lock(src);
|
||||
surface_lock dst_lock(dst);
|
||||
|
||||
Uint32* const src_pixels = reinterpret_cast<Uint32*>(src_lock.pixels());
|
||||
Uint32* dst_pixels = reinterpret_cast<Uint32*>(dst_lock.pixels());
|
||||
const Uint32* const src_pixels = src_lock.pixels();
|
||||
Uint32* dst_pixels = dst_lock.pixels();
|
||||
|
||||
for(unsigned y = 0; y < height; ++y) {
|
||||
for(unsigned x = 0; x < width; ++x) {
|
||||
|
@ -1802,7 +1821,7 @@ struct not_alpha
|
|||
SDL_Rect get_non_transparent_portion(const surface &surf)
|
||||
{
|
||||
SDL_Rect res = {0,0,0,0};
|
||||
const surface nsurf(make_neutral_surface(surf));
|
||||
surface nsurf(make_neutral_surface(surf));
|
||||
if(nsurf == NULL) {
|
||||
std::cerr << "failed to make neutral surface\n";
|
||||
return res;
|
||||
|
|
|
@ -328,12 +328,23 @@ SDL_Color create_color(const unsigned char red
|
|||
*/
|
||||
struct surface_lock
|
||||
{
|
||||
surface_lock(const surface &surf);
|
||||
surface_lock(surface &surf);
|
||||
~surface_lock();
|
||||
|
||||
Uint32* pixels() { return reinterpret_cast<Uint32*>(surface_->pixels); }
|
||||
private:
|
||||
SDL_Surface *surface_;
|
||||
surface& surface_;
|
||||
bool locked_;
|
||||
};
|
||||
|
||||
struct const_surface_lock
|
||||
{
|
||||
const_surface_lock(const surface &surf);
|
||||
~const_surface_lock();
|
||||
|
||||
const Uint32* pixels() const { return reinterpret_cast<const Uint32*>(surface_->pixels); }
|
||||
private:
|
||||
const surface& surface_;
|
||||
bool locked_;
|
||||
};
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue