MonoGame.Extended icon indicating copy to clipboard operation
MonoGame.Extended copied to clipboard

TiledMapTileReader does not resolve object type TiledMapObjectType.Tile

Open Mephisztoe opened this issue 1 year ago • 2 comments

I used Tiled to create a tiled map.

So that I can add static visual assets offgrid, I added an Object Layer and used the "T"-shortcut with <CTRL> on selected tiles.

You can see the result here: image

For now, it is not possible to make MonoGame.Extended just render an object layer the same way a tile layer is rendered, although loading and manually accessing its content is pretty much identical.

So I wanted to manually spritebatch the objects. When trying to identify the objects' source rectangles within their respective tilesheet, I noticed, that I am not able to access their global identifiers. Also, I noticed that the TilesMapTileReader does not populate the Tile property on the TiledMapTileObject which kind of seems like an issue to me.

Here is a little repro-solution (the assets being used are taken from one of the Kenney Game Asset Packs): ObjectLayerIssueRepro.zip

Mephisztoe avatar Aug 26 '24 20:08 Mephisztoe

So apparently this one is sort of a duplicate of this one.

Here is how I fixed it for the moment:

  1. In Tiled, I edited the TileSheet and added a Class description. image

  2. By doing so, the tiles get added to the TileSheets' .tsx file.

<?xml version="1.0" encoding="UTF-8"?>
<tileset version="1.9" tiledversion="1.10.2" name="Roguelike_RPG" tilewidth="16" tileheight="16" spacing="1" tilecount="1767" columns="57">
 <image source="roguelikeSheet_transparent.png" width="968" height="526"/>
 <tile id="420" class="Decoration"/>
 <tile id="478" class="Decoration"/>
 <tile id="482" class="Decoration"/>
</tileset>
  1. Because the TiledMapTileReader can now populate the Tiled property of the TileMapTileObject objects, I can now retrieve their source rectangles and draw them properly
private void DrawObjectLayer(SpriteBatch spriteBatch, TiledMap tiledMap)
{
    foreach (var obj in decorationLayer.Objects)
    {
        if (obj is TiledMapTileObject tileObject)
        {
            var tileset = tileObject.Tileset;
            var localIdentifier = tileObject.Tile.LocalTileIdentifier;
            var tileHeight = tileset.TileHeight;             

            var sourceRectangle = tileset.GetTileRegion(localIdentifier);

            var position = new Vector2(tileObject.Position.X, tileObject.Position.Y - tileHeight);

            spriteBatch.Draw(tileset.Texture, position, sourceRectangle, Color.White);
        }
    }
}

Result: image

However, I'd vote for ninjeffs suggestion here.

Mephisztoe avatar Aug 26 '24 22:08 Mephisztoe

Tiled implementation is going to be overhauled, currently looking into existing solutions such as DotTiled to see what can be used for improvements.

AristurtleDev avatar Nov 07 '24 17:11 AristurtleDev