It seems like the oldest game technology in the world – drawing tile maps is really slow. Am I doing something wrong?
Written by MM. Posted at 10:19 am on May 7th, 2009
11 comments.
Post a comment.
One of the things is that you should never render all tiles at once, just the visible ones. That’s the most common problem of all tile-rendering systems I’ve seen.
Yes. Still the minimum tiles size is 8×8 (Sigvatr wants it really detailed and varied). Thats 128×96 visible tiles. There is a noticably performance drop. Also add to that the background and foreground layer.
Optimize and use display lists or vertex buffer objects?
Take care that all objects have the same color depth. Cache every object and only draw when its (partially) visible.
Maybe you could prerender all static layers into huge memory buffers, that would be the fastest way, but maybe too much amount of ram would be needed (for standard PC’s). You could make an intelligent prerendering function that would first analyze each map before starting the match, for instance if 4 similar tiles fit in an rectangle you could merge this section into one big tile in memory… happy coding
Of course you’re doing something wrong!
First of all, don’t redraw unless you have to. Second, you don’t need to buffer the whole map.
Instead, let’s suppose your viewport is X*Y pixels. Your buffer only needs to be as big as X+width of longest tile, same for Y. Now whenever the player moves you translate, AKA move the entire viewport. The player moves left, you move the pixels in the buffer right. The pixels on the right get cropped, and on the left we have blank space.
You render the tiles in that missing space. Just make the buffer large enough to be able to render any tile before it appears in the viewport.
Also, blitting is slow like bloody hell. It’s about five times faster than trying to hand-knit an image using coloured thread.
archont has the right idea; first frame you fill the buffer with the tiles around the player, then most frames you either render the entire buffer to the screen, you move the buffer around a bit then render it, or you render a few rows/columns of tiles to the buffer first then render the buffer to the screen. Much faster to do one draw operation as opposed to 12,288.
lol – this blog went to twitter-style! :O
Also, show us some code, you noob!
Thanks guys. I think I’m gonna go with prerendering into a memory buffers. That way I can also easily make effects and have faster pixel shader effects.
at my after-school study they worked with areas, when ur in a area and u can see it, you draw the tiles, the poly’s and the graphics. if u cant see it. simply dont.
its easier to show in a jpeg. but im not bothering to do so, since archonts idea seems to work fine in my opinion.
I doubt this is the real problem you’re having with performance, but this will help speed things up…
If possible, render tiles grouped by their texture, to minimize changing which texture is being rendered. This operation can be pretty costly for the GPU. In other words, sort the render order of the tiles based on their texture.