diff --git a/packages/flame/lib/src/components/core/component.dart b/packages/flame/lib/src/components/core/component.dart index 55883caa26a..38f34e441a5 100644 --- a/packages/flame/lib/src/components/core/component.dart +++ b/packages/flame/lib/src/components/core/component.dart @@ -896,17 +896,12 @@ class Component { void _remove() { assert(_parent != null, 'Trying to remove a component with no parent'); - if (_key != null) { - final game = findGame(); - if (game is FlameGame) { - game.unregisterKey(_key!); - } - } _parent!.children.remove(this); propagateToChildren( (Component component) { component ..onRemove() + .._unregisterKey() .._clearMountedBit() .._clearRemovingBit() .._setRemovedBit() @@ -920,6 +915,15 @@ class Component { ); } + void _unregisterKey() { + if (_key != null) { + final game = findGame(); + if (game is FlameGame) { + game.unregisterKey(_key!); + } + } + } + //#endregion //#region Debugging assistance diff --git a/packages/flame/test/components/component_test.dart b/packages/flame/test/components/component_test.dart index ae71ccf5070..3dd96e61cbc 100644 --- a/packages/flame/test/components/component_test.dart +++ b/packages/flame/test/components/component_test.dart @@ -1381,6 +1381,29 @@ void main() { }, ); + testWithFlameGame( + 'Removed keys can be reused by components', + (game) async { + final key = ComponentKey.named('A'); + final parent1 = Component(children: [ComponentA(key: key)]); + + game.world.add(parent1); + await game.ready(); + + parent1.removeFromParent(); + await game.ready(); + + final component = ComponentA(key: key); + final parent2 = Component(children: [component]); + + game.world.add(parent2); + await game.ready(); + + final retrieved1 = game.findByKey(key); + expect(retrieved1, equals(component)); + }, + ); + testWithFlameGame( 'Throws assertion error when registering a component with the same key', (game) async {