Sign in to follow this  
phalaris

SDL tiling is way too slow..

Recommended Posts

I've laid down a very nice framework for my game. Sprites + animated explosions, and everything works really well .. now I'm trying to create a moving background made of tiles.. they're two sea tiles from the 1945 game (you all know that sprite sheet right?). Anyway, any attempts to do this have made the game unplayably slow.. So are there any well-known/documented techniques for this? I basically want a grid made up of random tiles.. either tile 1 or tile 2. So right now I'm doing something like: virtual void Draw(SDL_Surface* pDest, int windowWidth, int windowHeight) { for (int i=0; i<windowWidth; i+=tileWidth) { for (int j=0; j<windowHeight; j+=tileHeight) { // Generate random int between 1 and 2 // If 1, then apply tile 1 at (i,j) to pDest // If 2, then apply tile 2 at (i,j) to pDest } } } Just to make it clear, I'm using a pointer to an SDL_Surface* and constantly clipping from it, so in-fact there's only just that one sprite sheet loaded into memory for the whole game.. everything else is just different SDL_Rects and clipping from one place to another, etc..

Share this post


Link to post
Share on other sites
How many blits does that code end up doing (ie, how many tiles fit on screen at one time)?

I don't know the performance characteristics of SDL on its own, but I'm surprised that it's so slow.

Are you sure the destination surface is the same format as the source surface? If it's having to do a conversion every time you blit I imagine that could slow it down a lot.

John B

Share this post


Link to post
Share on other sites
Well the tiles are 37x37 each and I'm using 800x600 resolution..

I am not sure how to use dirty pixels in SDL. Is there a standard function for this? Or do I have to write my own functions using rects, etc?

My game has a lot of small moving parts (airplanes, boats, missiles, etc..). I fear that iterating over many rectangles per second and updating probably more than half of them anyway, will cause the same overhead.. So now I really don't what I should do.

Share this post


Link to post
Share on other sites
You didn't answer the question of whether the formats are the same. This is vital. If you're not using SDL_DisplayFormat on the images as the last step prior to blitting them, then you are likely to see slowdowns.

It's also important to show us the code for 'applying' the surfaces, which is far more critical to the process than the loops you use. (Although those loops imply the background will change randomly every frame; that can't be what you want, surely?)

Share this post


Link to post
Share on other sites
Quote:
Original post by Hombert
Drawing routines are faster when the image size is a power of 2, so that might be one reason.


SDL handles non-POT images just fine (it's a software renderer).

Share this post


Link to post
Share on other sites
Haven't done SDL, but here's a possible optimization:

Instead of drawing the background tile by tile each frame, how about you pre-compute the whole background with maybe +1 tile on each edge? then, when you draw it, you blit only one image, not however many tiles you have. And when your background scrolls down and reaches an end of your pre-rendered background, simply add another row/column of tiles, while removing the same from the other end. Should cut down on blit calls subsitentially.

Share this post


Link to post
Share on other sites
Hey guys, thanks a lot for the enthusiastic responses. I am not sure what you mean by the surface having the same format. My main surface (pScreen) is created using ::SDL_SetVideoMode(), and the only other surfaces I have are images loaded into memory using ::SDL_DisplayFormat(::IMG_Load(szFilename));
any other surface interaction is by means of pointers to/from these surfaces.

But anyway, Koobazaur's solution seems to have solved my problem.

I created a buffer surface, as Koobazaur suggested, but just once, in the constructor of the bg class and basically made a little moving camera.. so it's not so much a tiled background as a scrolling background made out of tiles.. it seemed to have done the job, and looks realistic enough for my purposes so I'm not going to complain..

Thanks a lot everyone for the feedback

Share this post


Link to post
Share on other sites
I think what is meant by the same format is that they should have the same color depth. For example if you are trying to blit a 24 bit per pixel image to a 32 bit per pixel then it will have to convert that image every time you blit it, which can cause a lot of slowdown. You should convert images to be the same depth when you load them (there's an SDL function but I'm at work right now so I probably shouldn't go on a hunt right now :P).

Share this post


Link to post
Share on other sites
Quote:
Original post by Mr_Threepwood
I think what is meant by the same format is that they should have the same color depth. For example if you are trying to blit a 24 bit per pixel image to a 32 bit per pixel then it will have to convert that image every time you blit it, which can cause a lot of slowdown. You should convert images to be the same depth when you load them (there's an SDL function but I'm at work right now so I probably shouldn't go on a hunt right now :P).


Yes, they're all 32 bpp, since I always pass in a SYSTEM_BPP macro anytime something is created..

So assuming they are the same format, is it weird that tiling should be so slow, given that I'm not using any intermediate surfaces?

Share this post


Link to post
Share on other sites
There's more to formatting than simple 32 bits vs. 24 bits. BGA vs. RGB, hardware vs. software, and other things like that all play a role. But you're calling SDL_DisplayFormat() on it so that's OK.

As an aside, you have a memory leak. SDL_DisplayFormat() *copies* the contents of the surface to a new surface, which it then returns. This means that the original surface (the one crated by IMG_Load()) is never freed, and therefore leaking. Simply store it and SDL_FreeSurface() it after you've stored the SDL_DisplayFormat-ed version.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this