From fc33b6f591fda70fd64ea34806e5516c695cd89b Mon Sep 17 00:00:00 2001 From: Kurtis Melby Date: Mon, 4 Dec 2023 23:55:10 -0500 Subject: [PATCH 1/2] feat: Adding a method to get any object in a map by its unique ID --- packages/tiled/lib/src/tiled_map.dart | 21 +++++++++++ packages/tiled/test/map_test.dart | 51 +++++++++++++++++++++++++++ 2 files changed, 72 insertions(+) diff --git a/packages/tiled/lib/src/tiled_map.dart b/packages/tiled/lib/src/tiled_map.dart index 8b7bb5b..ef6133a 100644 --- a/packages/tiled/lib/src/tiled_map.dart +++ b/packages/tiled/lib/src/tiled_map.dart @@ -91,6 +91,9 @@ class TiledMap { List editorSettings; CustomProperties properties; + // Cache the object by ID when accessed. + Map? _cachedObjects; + // only for hexagonal maps: int? hexSideLength; StaggerAxis? staggerAxis; @@ -279,6 +282,24 @@ class TiledMap { throw ArgumentError('Layer $name not found'); } + /// Finds the [TiledObject] in this map with the unique [id]. + /// Objects have map wide unique IDs which are never reused. + /// https://doc.mapeditor.org/en/stable/reference/tmx-map-format/#object + /// + /// Returns null if not found. + TiledObject? objectById(int id) { + if (_cachedObjects == null) { + _cachedObjects = {}; + layers.whereType().forEach((objectGroup) { + for (final object in objectGroup.objects) { + _cachedObjects![object.id] = object; + } + }); + } + + return _cachedObjects?[id]; + } + Tileset tilesetByName(String name) { return tilesets.firstWhere( (element) => element.name == name, diff --git a/packages/tiled/test/map_test.dart b/packages/tiled/test/map_test.dart index 9b1acd3..7f91085 100644 --- a/packages/tiled/test/map_test.dart +++ b/packages/tiled/test/map_test.dart @@ -380,4 +380,55 @@ void main() { expect(map.tilesetByName('Humans'), equals(tileset)); }); }); + + group('Map.objectById', () { + late TiledMap map; + setUp(() { + map = TiledMap( + width: 2, + height: 2, + tileWidth: 8, + tileHeight: 8, + layers: [ + TileLayer( + name: 'tile layer 1', + width: 2, + height: 2, + data: [1, 0, 2, 0], + ), + ObjectGroup( + name: 'object layer 1', + objects: [ + TiledObject(id: 1, name: 'object one'), + TiledObject(id: 5, name: 'object five'), + ], + ), + ], + tilesets: [ + Tileset( + name: 'TileSet_1', + image: const TiledImage(source: 'tileset_1.png'), + firstGid: 1, + columns: 1, + tileCount: 2, + tiles: [ + Tile(localId: 0), + Tile(localId: 1), + ], + ), + ], + ); + }); + + test('gets images only in use on each TileLayer', () { + final object1 = map.objectById(1); + expect(object1?.name, equals('object one')); + + final object5 = map.objectById(5); + expect(object5?.name, equals('object five')); + + final object3 = map.objectById(3); + expect(object3, equals(null)); + }); + }); } From 203482beaa5d616caa5de3f078bd42c52c1ed0a1 Mon Sep 17 00:00:00 2001 From: Kurtis Melby Date: Tue, 5 Dec 2023 22:45:31 -0500 Subject: [PATCH 2/2] adding comment about caching --- packages/tiled/lib/src/tiled_map.dart | 3 +++ 1 file changed, 3 insertions(+) diff --git a/packages/tiled/lib/src/tiled_map.dart b/packages/tiled/lib/src/tiled_map.dart index ef6133a..270f425 100644 --- a/packages/tiled/lib/src/tiled_map.dart +++ b/packages/tiled/lib/src/tiled_map.dart @@ -286,6 +286,9 @@ class TiledMap { /// Objects have map wide unique IDs which are never reused. /// https://doc.mapeditor.org/en/stable/reference/tmx-map-format/#object /// + /// This reads through a cached map of all the objects so it does not + /// need to loop through all the object layers each time. + /// /// Returns null if not found. TiledObject? objectById(int id) { if (_cachedObjects == null) {