[STI/Tiled] Less Layers For Efficency or More Layers For Readability?

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.
Post Reply
Saphiresurf
Prole
Posts: 14
Joined: Thu Mar 16, 2017 1:53 am

[STI/Tiled] Less Layers For Efficency or More Layers For Readability?

Post by Saphiresurf »

When designing your levels in Tiled (implemented through STI) is it better to try to go with less layers for the sake of performance efficiency (as in one layer for tiles, one layer for tile collisions) or is it better to try to use more layers for the sake of separation, organization, and human readability (such as a tile layer for platforms, collision layer for platforms, tile layer for obstructions, separate collision layer for obstructions)?

Essentially saying would it be better to use less layers to describe your levels tiles and collisions and would it be harmful to performance if you decided to use more layers to separate different groups/components of your levels? Is the difference negligible on performance for the most part when it comes to layers added even as your game starts to grow? Is this something I should even be worrying about? :halloween:
User avatar
Imaculata
Party member
Posts: 102
Joined: Mon Aug 10, 2015 2:51 pm

Re: [STI/Tiled] Less Layers For Efficency or More Layers For Readability?

Post by Imaculata »

I think that depends entirely on how you use the information contained in the file. Here's what I'm currently doing for my 2d platformer:

I first create two layers in Tiled:

+Backgrounds
+Entities


I then export these as an csv file, not a lua file. This creates a separate CSV file for each layer. This is because I just want to know the numbers of the tiles, but none of the code that Tiled adds. I want a clean file.

I then run a bat-file that I wrote myself, that looks in the directory, and merges the contents of all the CSV files into one lua file, with all the desired code and formatting that I want, but with the two layers as separate variables that the game can load.

Then I create a reference file, which is basically a lua file with a lookup table, that tells my game exactly what each tile is. So any wall tiles that I place in Tiled, are automatically added as collision, thanks to the reference file. The game basically checks every tile that it loads, against the reference file, and processes the tile in accordance with my rules.

Here's what that may look like:

Code: Select all

	-- Collision reference sheet for the tilesheet
	--"X"=wall--"."=floor--"W"=water--"SW"=shallowwater--"L"=lava--"F"=firepit--"E"=emptyfirepit
	--"P"=pit--"T"=spiketrap--"S"=stairs--"U"=hammerblockup--"D"=hammerblockdown
	--"C"=chest--"I"=blockup--"O"=blockdown--"B"=blockswitch--"Q"=pressurepad
	--"V"=vase--"R"=button--"M"=MoveableObject--
	
	local collisionsheet={
	{ "X","X","X","X","X","X","X","X","X","X","P","P","P","X","X","X","X"}, 
	{ "X","X","X","X","X","X",".",".","X","X","P","P","P","X","X","X","X"}, 
	{ "X","X","X","X","X","X",".",".","X","X","P","P","P","X","X","X","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","P","P","X","X","X","."}, 
	{ "X","X","X",".",".",".",".",".",".",".","X","P","P","X","X","X","."}, 
	{ "X","X","X",".",".",".",".",".",".",".","X","X","X","X","X","X","Q"}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","X",".",".",".","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","W",".",".","X","P"}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","S","S","S","S","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","S","S","S","S","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","X","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","S","S","S","S","."}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X","S","S","S","S","."}, 
	{ ".",".",".",".",".",".","X","X","X","X",".",".",".",".",".",".","X"}, 
	{ ".",".",".",".",".",".","X","X","X","X",".",".",".",".",".",".","."}, 
	{ ".","X","X","X","X","X","X","E","F","F","F","X","X","X","T","T","T"}, 
	{ ".","X","X","X","X","X","X","O","I","I","O","I","I",".",".","X","S"}, 
	{ "L","SW","SW","SW","X",".",".",".","X",".",".",".",".","B","B","X","S"}, 
	{ "L","X","X","X","X",".","X","X","X",".","X","X","X",".",".",".","S"}, 
	{ "L","X","X","X",".",".",".","X","X","X","X","X","X",".",".",".","W"}, 
	{ "X","X","X","X","X","X","X","X","X","X","X","X",".",".",".",".","."}, 
	{ "X","X","X","X","X",".",".","X","X","X",".",".",".","D","U","U","U"}, 
	{ ".",".",".",".","X",".",".",".",".",".",".",".","S","S","S","S","C"}, 
	{ ".",".",".",".",".",".",".",".",".",".",".",".","S","S","S","S","X"},
	{ ".",".",".",".","S","S","X","X",".",".",".",".","X","X","X","X","C"},
	{ "C","C","X","X","S","S","X","X",".",".",".",".","X","X","X","X","X"},
	{ ".",".",".",".",".",".",".",".",".",".",".",".",".",".",".",".","V"},
	{ ".",".",".",".",".",".",".",".",".",".",".",".",".",".",".",".","."},
	{ ".",".",".",".",".","P","P","P","P",".",".",".",".",".",".",".","."},
	{ ".",".",".",".",".","P","P","P","P",".",".",".",".",".",".",".","."},
	{ "S","S","S","X","X","X","X","X",".",".",".","S","S","S",".","X","X"},
	{ "X","X","S","S","X","X","X","X",".",".",".",".",".",".",".","X","X"},
	{ "X","X","S","S","X","X","X","X",".",".",".",".",".",".",".","X","X"},
	{ "X","X","S","S","X","X","X","X",".",".",".",".",".",".",".","X","X"},
	{ "S","S","S","S","S","S","S","S","X","X","X","X","X",".",".",".","."},
	{ "S","S","S","S","S","S","S","S","X","X","X","X","X",".",".",".","."}
	}

 return collisionsheet
And here's the tilesheet that this file refers to. In this example I used some classic Zelda tiles for this. As you can see, the reference file tells the game exactly what the tile is supposed to be. "X" for a wall, or "." for a floor tile, or "L" for hot boiling lava.

Image

I do the same with the entities layer, with the difference that entities simply add functionality, and are usually not added to the spritebatch. This allows me to add things on top of the normal tiles, such as enemies, items, invisible zones, water and ladders... etc.

Since all of this information is only processed upon loading the map, none of this really affects performance during the game.
So, you don't need to have a separate layer in Tiled for collisions. That seems like an awful lot of work. If all wall tiles are always considered collision by your game, then that is one layer that you can leave out completely.

And one thing that I did in my current project, was add a "fake-wall" tile to the entity layer. This tells my game that when it looks up a tile, which is considered a wall, but it has a "fake-wall" tile on top of it in the entities layer, that those tiles do not need to be added to the collision. It is basically checking each tile against two reference files, and deciding what to do with it upon loading the map.
Saphiresurf
Prole
Posts: 14
Joined: Thu Mar 16, 2017 1:53 am

Re: [STI/Tiled] Less Layers For Efficency or More Layers For Readability?

Post by Saphiresurf »

This is awesome and makes a ton of sense. That really simplifies the process of how to create different types of collisions, I appreciate it! I'm going to toy around with this a bit and I'll get back to you if I have any questions or anything. I appreciate the help!


EDIT: Also something I do is just check the object name which for me at least bypasses the need to use an external .bat file. This way I just determine collisions by the name attached to the collision box and it looks like this:

Code: Select all

    -- Creating collisions as defined in  (platforms)
    for x, object in pairs(level.layers.Collisions.objects) do
        if object.name == "platform" then
            tiles.collisionShape[x] = collider:rectangle(object.x, object.y, object.width, object.height)
            tiles.collisionShape[x] = tiles.collisionShape[x]:rotate(object.rotation)
            tiles.collisionShape[x].id = "platform"
        end
    end

I in this case do export my level as a .lua file. The id attached to the collisionShape is what my other collisionShape's will be checking for when handling collisions (for example the player object checks it's list of collisions through Hardon Collider and if the collisionShape that's colliding with the players collisionShape has the id of "platform" then it'll handle the collision in this certain way made just for platforms. Is there any reason why I may not want to go this route or does this work pretty well as well?
User avatar
Imaculata
Party member
Posts: 102
Joined: Mon Aug 10, 2015 2:51 pm

Re: [STI/Tiled] Less Layers For Efficency or More Layers For Readability?

Post by Imaculata »

I haven't used Hardon Collider myself, I use Bump, but that looks totally fine. Looks what you have there is a simple and clean collision response.

The reason I use a bat file, is because I want my map files to formatted the way I want them to, and not the way Tiled formats them by default. There's a bit of clutter in lua files saved by Tiled, so I just have a bat file copy the data from a csv file, into a clean lua file of my own.

But there is no reason not to do it the way you are now, apart from personal preference. ;)
Saphiresurf
Prole
Posts: 14
Joined: Thu Mar 16, 2017 1:53 am

Re: [STI/Tiled] Less Layers For Efficency or More Layers For Readability?

Post by Saphiresurf »

Cool sounds good! I know I'm actually starting to think if I just want to do it directly in the format you're working with now because it seems pretty nice. Would be cool to have a sprite layer and a collision layer sort of like how the Pokemon games will do it. Giving me lots of things to think about here fosho ^_^.

EDIT: Ohhhh that's practically what you're doing here, too, huh :o
Post Reply

Who is online

Users browsing this forum: No registered users and 61 guests