So, I’m tiling the world for my game, and it got out of hand. I figured out how to use infinite worlds, but I want to be able to crop my map into chunks so that the game can load in only a small section of the world to prevent lag. Is there any way to do this?
Infinite maps are already chunked, and you can control the size of the chunks in Map Properties.
When you load the map, don’t load the entire thing, load just the chunks you need, and stream in the rest as the player moves across the world. This way, only a few chunks of the world are loaded at any given time. The infinite map format was created specifically with data streaming in mind, I believe.
If you’re looking for a creation-time solution to split up the map into several separate maps with transitions between them: You can create a copy of the map, select the area you want to crop out, and Map > Crop to Selection
. Rinse and repeat. If you’ve already made a lot, you can potentially automate this with scripting.
However, this is not an ideal solution for the future. For your future mapping, I recommend creating your smaller maps right away instead of working in one giant map. You can still view them all together if you create a World and add them all to that world.
Ok, thanks for your help!
-Sincerely
FiveBrosStopMosYT
I have to disappoint a little here, since all supported formats (JSON, TMX and Lua) that store chunks would anyway have to be fully parsed to get at any desired chunk (except TMX, would could be read up to that point, but that doesn’t help much).
Basically, the chunked format only avoids storing large empty areas, which makes a big difference especially when a lot of sparsely filled layers are used. It does also help with avoiding conflicts when multiple people edit the same world. But the file generally still needs to be entirely loaded.
So yeah, the two solutions here would be:
- Script a custom action to automate the cropping + saving sequence.
- Use the worlds feature instead, so you can edit multiple separate maps but still see them in a single view (though, if you’ve already got a very large map, you may want to look into scripting the above anyway, even if you only plan to do it once).
If you consider scripting this, here’s some lines to help you on your way:
// Resize + offset the map to capture a chunk (passing `true` to also delete objects outside of the map)
tiled.activeAsset.resize(Qt.size(16, 16), Qt.point(-16, 0), true)
// Save the chunk in TMX format
tiled.mapFormat("tmx").write(tiled.activeAsset, "/tmp/test.tmx")
// Undo the resize (to perform a resize to the next chunk)
tiled.activeAsset.undo()
You’d need to perform the above in a loop. Note that since it relies on undo being available it would need to operate on a currently open map.
Also, for an infinite map there’s currently no way to directly get the bounds of the entire map. You can get the bounds of an individual tile layer by doing tiled.activeAsset.layerAt(0).region().boundingRect
. In case of multiple tile layers you’d want to combine the regions (using totalRegion.add(region)
before calling boundingRect
.
Ok, thanks.