Tilemap: Optimize atlas assembly from mega surface tileset

Use 'glPixelStorei()' parameters to upload sub images
directly from the same surface instead of creating
helper surfaces to upload from.
This commit is contained in:
Jonas Kulla 2013-10-16 19:20:36 +02:00
parent 94911b61a6
commit 397856089d
2 changed files with 22 additions and 21 deletions

View File

@ -313,6 +313,24 @@ typedef struct GenericBO<GL_ELEMENT_ARRAY_BUFFER> IBO;
#undef DEF_GL_ID #undef DEF_GL_ID
namespace PixelStore
{
/* Setup a 'glSubTexImage2D()' call where the uploaded image
* itself is part of a bigger image in client memory */
inline void setupSubImage(GLint imgWidth, GLint subX, GLint subY)
{
glPixelStorei(GL_UNPACK_ROW_LENGTH, imgWidth);
glPixelStorei(GL_UNPACK_SKIP_PIXELS, subX);
glPixelStorei(GL_UNPACK_SKIP_ROWS, subY);
}
/* Reset all states set with 'setupSubImage()' */
inline void reset()
{
setupSubImage(0, 0, 0);
}
}
/* Convenience struct wrapping a framebuffer /* Convenience struct wrapping a framebuffer
* and a 2D texture as its target */ * and a 2D texture as its target */
struct TEXFBO struct TEXFBO

View File

@ -654,33 +654,16 @@ struct TilemapPrivate
SDL_Surface *tsSurf = tileset->megaSurface(); SDL_Surface *tsSurf = tileset->megaSurface();
int bpp;
Uint32 rMask, gMask, bMask, aMask;
SDL_PixelFormatEnumToMasks(SDL_PIXELFORMAT_ABGR8888,
&bpp, &rMask, &gMask, &bMask, &aMask);
for (int i = 0; i < blits.count(); ++i) for (int i = 0; i < blits.count(); ++i)
{ {
TileAtlas::Blit &blitOp = blits[i]; TileAtlas::Blit &blitOp = blits[i];
SDL_Surface *blitTemp = PixelStore::setupSubImage(tsSurf->w, blitOp.src.x, blitOp.src.y);
SDL_CreateRGBSurface(0, tsLaneW, blitOp.h, bpp, rMask, gMask, bMask, aMask);
SDL_Rect tsRect; TEX::uploadSubImage(blitOp.dst.x, blitOp.dst.y, tsLaneW, blitOp.h, tsSurf->pixels, GL_RGBA);
tsRect.x = blitOp.src.x;
tsRect.y = blitOp.src.y;
tsRect.w = tsLaneW;
tsRect.h = blitOp.h;
SDL_Rect tmpRect = tsRect;
tmpRect.x = tmpRect.y = 0;
SDL_BlitSurface(tsSurf, &tsRect, blitTemp, &tmpRect);
TEX::uploadSubImage(blitOp.dst.x, blitOp.dst.y, tsLaneW, blitOp.h, blitTemp->pixels, GL_RGBA);
SDL_FreeSurface(blitTemp);
} }
PixelStore::reset();
} }
else else
{ {