Efficiently drawing a grid map

Questions about the LÖVE API, installing LÖVE and other support related questions go here.
Forum rules
Before you make a thread asking for help, read this.
User avatar
Gunroar:Cannon()
Party member
Posts: 263
Joined: Thu Dec 10, 2020 1:57 am

Efficiently drawing a grid map

Post by Gunroar:Cannon() »

Hello all, I've made a grid map that draws images next to each other and I was wondering whether there's any way to make it faster, like using imagedata to store how each tile looks and then drawing it as 1 image then changing the graphics of the image when needed.
Will this work, any details. Thnx.
Check out Treaty
me: I don't always code but when I do it's done flawlessly.
also me:

Code: Select all

 function Gunroar:Cannon()
    for x, enemy in ipairs(self.allEnemies) do
        self:Cannon(enemy)
    end
end

Code: Select all

Lua Error: [file Gunroar.lua]:18: C stack overflow
User avatar
pgimeno
Party member
Posts: 2610
Joined: Sun Oct 18, 2015 2:58 pm

Re: Efficiently drawing a grid map

Post by pgimeno »

A texture atlas is the way to speed it up. SpriteBatch is made mostly for this kind of usage, and requires a texture atlas.
User avatar
Gunroar:Cannon()
Party member
Posts: 263
Joined: Thu Dec 10, 2020 1:57 am

Re: Efficiently drawing a grid map

Post by Gunroar:Cannon() »

pgimeno wrote: Sat Apr 17, 2021 10:56 am A texture atlas is the way to speed it up. SpriteBatch is made mostly for this kind of usage, and requires a texture atlas.
Thnx, now I know it's possible, but how?
1)Any pointers/references on the use for this type of thing?
2)Will it make the game faster?
Check out Treaty
me: I don't always code but when I do it's done flawlessly.
also me:

Code: Select all

 function Gunroar:Cannon()
    for x, enemy in ipairs(self.allEnemies) do
        self:Cannon(enemy)
    end
end

Code: Select all

Lua Error: [file Gunroar.lua]:18: C stack overflow
User avatar
pgimeno
Party member
Posts: 2610
Joined: Sun Oct 18, 2015 2:58 pm

Re: Efficiently drawing a grid map

Post by pgimeno »

Gunroar:Cannon() wrote: Sat Apr 17, 2021 11:34 am
pgimeno wrote: Sat Apr 17, 2021 10:56 am A texture atlas is the way to speed it up. SpriteBatch is made mostly for this kind of usage, and requires a texture atlas.
Thnx, now I know it's possible, but how?
1)Any pointers/references on the use for this type of thing?
2)Will it make the game faster?
1) https://love2d.org/wiki/Tutorial:Effici ... _Scrolling
2) It depends on how you're doing it currently, and whether you're hitting a bottleneck.
User avatar
Gunroar:Cannon()
Party member
Posts: 263
Joined: Thu Dec 10, 2020 1:57 am

Re: Efficiently drawing a grid map

Post by Gunroar:Cannon() »

I just draw the pictures with a for loop

Code: Select all

for x=... do
    for y=... do
        draw(map[x][y])
    end
end
Something like that. I kind of use bump to get all the tiles in a certain view then loop through the result and draw them.
I'm not hitting a bottleneck, just done with the map, so now I'm thinking on optimization...
1)So will it be faster?

2)Oh, and the reference you gave me was nice, but wondering if I could do it with images that aren't in tilesets, but in different image files.
Check out Treaty
me: I don't always code but when I do it's done flawlessly.
also me:

Code: Select all

 function Gunroar:Cannon()
    for x, enemy in ipairs(self.allEnemies) do
        self:Cannon(enemy)
    end
end

Code: Select all

Lua Error: [file Gunroar.lua]:18: C stack overflow
User avatar
pgimeno
Party member
Posts: 2610
Joined: Sun Oct 18, 2015 2:58 pm

Re: Efficiently drawing a grid map

Post by pgimeno »

Gunroar:Cannon() wrote: Sat Apr 17, 2021 1:28 pm I'm not hitting a bottleneck, just done with the map, so now I'm thinking on optimization...
Planning on using a texture atlas in advance would have saved you some work. Don't believe the tale about "premature optimization blah blah". Misuse of that adage is the root of all evil.

Gunroar:Cannon() wrote: Sat Apr 17, 2021 1:28 pm 1)So will it be faster?
Most probably.

Gunroar:Cannon() wrote: Sat Apr 17, 2021 1:28 pm 2)Oh, and the reference you gave me was nice, but wondering if I could do it with images that aren't in tilesets, but in different image files.
No, batches require a single image. In Löve, using different images implies using different GL draw calls. In GL, draw calls have a cost in performance. Starting with version 11, Löve has the capability of auto-batching, that is, it automatically generates the equivalent of a SpriteBatch in order to save draw calls, but that's only possible while drawing from the same image. When you draw a different image, the current batch is flushed and drawn, and a new batch is started.

Bottom line is, if you use different images, there's nothing that can be done to save draw calls, making the performance suffer.

By the way, I think that creating the sprite batches yourself still results in a performance improvement over letting Löve auto-batch, but I'm not 100% sure of that, and I don't know how much of an improvement it may bring.
togFox
Party member
Posts: 159
Joined: Sat Jan 30, 2021 9:46 am

Re: Efficiently drawing a grid map

Post by togFox »

When you draw a different image, the current batch is flushed and drawn, and a new batch is started.
If you had a dungeon crawler that doesn't scroll very fast, would it help to draw all the floor tiles first then all the walls then all the doors etc? In other words, don't blindly draw left to right and causing a lot of swapping?

Sprite sheets and batches will always be faster but if one must use images then would that technique reduce the 'swapping' of images?
User avatar
pgimeno
Party member
Posts: 2610
Joined: Sun Oct 18, 2015 2:58 pm

Re: Efficiently drawing a grid map

Post by pgimeno »

togFox wrote: Sat Apr 17, 2021 11:57 pm If you had a dungeon crawler that doesn't scroll very fast, would it help to draw all the floor tiles first then all the walls then all the doors etc? In other words, don't blindly draw left to right and causing a lot of swapping?
If you have all floor tiles in a single texture atlas, all the walls in another, and all the doors in another, then yes, drawing all stuff that is in a single image together would save draw calls, potentially improving performance (if you don't do anything in between that forces a flush, that is).

The scroll speed is irrelevant, by the way.
User avatar
Gunroar:Cannon()
Party member
Posts: 263
Joined: Thu Dec 10, 2020 1:57 am

Re: Efficiently drawing a grid map

Post by Gunroar:Cannon() »

How about if I have on big ImageData then when a tile is made add the image's data, relative to the pos of the tile, to the image data. Then I just draw the one image...?
Check out Treaty
me: I don't always code but when I do it's done flawlessly.
also me:

Code: Select all

 function Gunroar:Cannon()
    for x, enemy in ipairs(self.allEnemies) do
        self:Cannon(enemy)
    end
end

Code: Select all

Lua Error: [file Gunroar.lua]:18: C stack overflow
User avatar
pgimeno
Party member
Posts: 2610
Joined: Sun Oct 18, 2015 2:58 pm

Re: Efficiently drawing a grid map

Post by pgimeno »

You can certainly generate the atlas at load time, if that's what you're asking. Even a canvas would work.
Post Reply

Who is online

Users browsing this forum: No registered users and 8 guests