Z ordering issues - tiledquickplugin

Currently I’m using Tiled (tiledquickplugin) for the “ground” in my game. I’m using my own editor for everything else (entities like characters, walls, buildings, etc). The problem is that the things that I place in my editor are above the ground layer created by Tiled (i.e. MapItem), and hence they are always rendered above it. This results in a loss of a sense of depth in some tiles. For example, here’s a mulch tile; you can see on the top left edge that it extends outside the isometric tile shape to make it appear “lumpy”:

Here’s a screenshot of the game running with a wall in place:

You can see that it looks clean and flat because the depth is gone.

So what I’m wondering is if there is a way to integrate the two. MapItem is a QQuickItem that has MapLayerItems as children. Each MapLayerItem renders its tiles in one go using draw order as the Z value, whereas in my game, each entity has its own QQuickItem with a Z value assigned to it based on which tile they’re on.

One way I thought of was to do the first level of buildings, walls, etc. as a layer in tiled below the ground layer so that the lumpy ground can be rendered on top of it. This should work, as building and wall tiles are impassable, and since it would only be the bottom section of them, it shouldn’t ever need to render above the player. The downside to this approach is that I need to do half in Tiled and half in my editor (the upper walls)… which I’m kind of already doing anyway.

However, this problem got me thinking about fully integrating a game with tiledquickplugin and replacing my editor with Tiled (Quick). Beyond somehow integrating the features of my editor with (or into a fork of) Tiled (Quick) I would also need to replace my own top-level Scene item (of which all entities in the game are child items) with MapItem so that I can get the Z ordering working. That might be a lot of work, but it should be doable.

However, If I want to use TileLayerItem to add different layers (e.g. buildings or whatever), currently I think that I would need to put each individual tile on its own layer, because Z ordering in Qt Quick is relative, and TileLayerItem has a single item for all of its tiles. I like the put-all-tiles-in-one-item approach because it’s likely very efficient, but it makes this sort of integration very difficult.

Another thing is that I have my own data saved as JSON and don’t really want to use XML. There might already be a solution for this though…

Bjorn (and anyone else in case they have knowledge of Qt Quick): what are your thoughts on this?

Specifically, I’m wondering what you think about the issue where entities have a calculated Z value based on their tiled position, and if it is even possible to integrate this kind of setup into a MapItem-based scene.

One way I thought of was to do the first level of buildings, walls, etc. as a layer in tiled below the ground layer so that the lumpy ground can be rendered on top of it. This should work, as building and wall tiles are impassable, and since it would only be the bottom section of them, it shouldn’t ever need to render above the player. The downside to this approach is that I need to do half in Tiled and half in my editor (the upper walls)… which I’m kind of already doing anyway.

Following on from this, some entities in my game are made up of several different “tiles”; not tiles in the sense of isometric Tiled tilesets, but tiles that are taken out of a larger image at runtime using QQuickImageProvider:

Doing it this way makes creating artwork – specifically making everything tile properly – much easier, so I would like to keep doing it this way. Is there a way to do this with Tiled? If not, what would I need to do to make it possible? Some kind of plugin or something?

Regarding the depth, I think this related to the following recent topic:

Essentially the fix would be to render each tile column, instead of rendering each tile layer and then each tile individually. That way, the walls would be already rendered by the time the tile columns that should be rendered over them are drawn.

This is currently not supported by the tiledquickplugin, and with the way it is set up with an item per layer it is not easily changed. The easiest way would probably be to copy the code and then to modify it so that a TileLayerItem receives a list of layers that it will process one tile stack at a time. This will then also mean either not relying on mRenderer->drawTileLayer to draw each layer, or to also “fork” that code and modify it as well to take a list of layers which can then be processed in its inner loop.

A real fix would probably be similar to the way we added the RenderTileCallback, in that we separate the responsibilities further. What we would need, is a function that iterates tile locations in rendering order (like drawTileLayer does), but rather than directly drawing the tiles, it could call a callback in which you can then render all tiles from a certain location, instead of drawing only the tiles from a single layer.

Potentially, we can just make our existing RenderTileCallback less specific. Instead of taking the cell, position and size as parameters, it could only take the tile coordinates and the pixel coordinates. At the same time, this more generic drawTileLayer function would no longer take a TileLayer*, but just the rectangle of the area that needs to be rendered.

Hmm, I’m not sure what could be done here. I would suggest to generate a regular tileset based on your system, so that you can use them in Tiled.

Thanks for the response. :slight_smile: I’ll need to think about this some more…

By the way, by tile column, I’m assuming you mean a vertical “stack” of tiles at the same tile position? Going from the “floor” upwards?

Yes, that’s what I meant.