Managed the freeing of entityplacers. Also cleaned up EntityManager

pull/52/head
Katharina Ziolkowski 2 months ago
parent bcbc074c86
commit b65a3bbd6d

@ -0,0 +1,13 @@
using System.Collections.Generic;
namespace Babushka.scripts.CSharp.GameEntity.Entities;
public class LoadedScenesEntity : Entity
{
private HashSet<string> _loadedScenes = new();
public override string EntityType => "LoadedScenesEntity";
public void AddScene(string sceneName) => _loadedScenes.Add(sceneName);
public bool WasSceneLoaded(string sceneName) => _loadedScenes.Contains(sceneName);
}

@ -28,6 +28,6 @@ public abstract class PositionalEntity : Entity
} }
// Deals with Instantiation of the node // Deals with Instantiation of the node
public abstract void AddEntity(Node2D parent); public abstract void InstantiateEntityNode(Node2D parent);
} }

@ -13,10 +13,10 @@ public class TrashEntity : PositionalEntity
{ {
} }
public override void AddEntity(Node2D parent) public override void InstantiateEntityNode(Node2D parent)
{ {
if(_creator == null) _creator = EntityManager.Instance.NodeCreator; if(_creator == null) _creator = EntityManager.Instance.NodeCreator;
var entityNode = _creator.CreateNode2D(EntityType); var entityNode = _creator.InstantiateNode(EntityType);
parent.AddChild(entityNode); parent.AddChild(entityNode);
entityNode.GlobalPosition = position; entityNode.GlobalPosition = position;
} }

@ -10,9 +10,17 @@ public partial class TrashEntityPlacer : Node2D
public override void _Ready() public override void _Ready()
{ {
TrashEntity entity = new TrashEntity(); string sceneName = EntityManager.Instance.CurrentEntitySceneContainer!.sceneName;
entity.sceneName = EntityManager.Instance.CurrentEntitySceneContainer!.sceneName; var loadedScenesEntity = EntityManager.Instance.GetUniqueEntity<LoadedScenesEntity>();
entity.position = GlobalPosition;
EntityManager.Instance.AddEntity(entity); if (!loadedScenesEntity.WasSceneLoaded(sceneName))
{
TrashEntity entity = new TrashEntity();
entity.sceneName = sceneName;
entity.position = GlobalPosition;
EntityManager.Instance.AddEntity(entity);
}
QueueFree();
} }
} }

@ -1,5 +1,4 @@
using System; using System.Collections.Generic;
using System.Collections.Generic;
using System.Linq; using System.Linq;
using Godot; using Godot;
using Entity = Babushka.scripts.CSharp.GameEntity.Entities.Entity; using Entity = Babushka.scripts.CSharp.GameEntity.Entities.Entity;
@ -7,21 +6,23 @@ using PositionalEntity = Babushka.scripts.CSharp.GameEntity.Entities.PositionalE
namespace Babushka.scripts.CSharp.GameEntity.Management; namespace Babushka.scripts.CSharp.GameEntity.Management;
/// <summary>
/// Manages the lifecycle and interactions of all entities within the game, including their creation, retrieval,
/// and organization. The EntityManager serves as a centralized hub for managing both standard and positional entities.
/// </summary>
public partial class EntityManager : Node public partial class EntityManager : Node
{ {
public static EntityManager Instance;
[Export] private EntityNodeCreator _nodeCreator = null!; [Export] private EntityNodeCreator _nodeCreator = null!;
public EntityNodeCreator NodeCreator => _nodeCreator;
private EntitySceneContainer? _currentEntitySceneContainer; private EntitySceneContainer? _currentEntitySceneContainer;
public static EntityManager Instance;
private readonly List<Entity> _allEntities = new(); private readonly List<Entity> _allEntities = new();
public IEnumerable<Entity> AllEntities => _allEntities; public IEnumerable<Entity> AllEntities => _allEntities;
public IEnumerable<PositionalEntity> AllPositionalEntities => _allEntities.OfType<PositionalEntity>(); public IEnumerable<PositionalEntity> AllPositionalEntities => _allEntities.OfType<PositionalEntity>();
public EntitySceneContainer? CurrentEntitySceneContainer => _currentEntitySceneContainer;
public EntityNodeCreator NodeCreator => _nodeCreator;
public override void _EnterTree() public override void _EnterTree()
{ {
@ -30,6 +31,7 @@ public partial class EntityManager : Node
public override void _Input(InputEvent @event) public override void _Input(InputEvent @event)
{ {
// for debugging purposes
if (@event.IsActionPressed("DebugEntities")) if (@event.IsActionPressed("DebugEntities"))
{ {
GD.Print("Entities:"); GD.Print("Entities:");
@ -39,37 +41,49 @@ public partial class EntityManager : Node
} }
} }
} }
#region ENTITY MANAGEMENT
public void UnloadScene() /// <summary>
{ /// Adds an entity to the list of managed entities. If the entity is a positional entity
if (_currentEntitySceneContainer == null) return; /// and its scene matches the current scene container, it is also instantiated in the scene.
_currentEntitySceneContainer = null; /// </summary>
} /// <param name="entity">The entity to be added to the manager.</param>
public void LoadScene(EntitySceneContainer sceneContainer)
{
_currentEntitySceneContainer = sceneContainer;
foreach (var entity in AllPositionalEntities)
{
_currentEntitySceneContainer.AddIfNeeded(entity);
}
}
public void AddEntity(Entity entity) public void AddEntity(Entity entity)
{ {
if(!_allEntities.Contains(entity)) if (!_allEntities.Contains(entity))
_allEntities.Add(entity); _allEntities.Add(entity);
if(entity is PositionalEntity positionalEntity && positionalEntity.sceneName == _currentEntitySceneContainer?.sceneName) if(entity is PositionalEntity positionalEntity && positionalEntity.sceneName == _currentEntitySceneContainer?.sceneName)
CreateEntityNode(positionalEntity); InstantiatePositionalEntityNode(positionalEntity);
} }
public void CreateEntityNode(PositionalEntity entity) private void InstantiatePositionalEntityNode(PositionalEntity entity)
{ {
if(_currentEntitySceneContainer == null) return; if(_currentEntitySceneContainer == null) return;
entity.AddEntity(_currentEntitySceneContainer); entity.InstantiateEntityNode(_currentEntitySceneContainer);
}
/// <summary>
/// Retrieves the first entity of the specified type from the list of managed entities.
/// If no such entity exists, creates a new instance of the specified type, adds it to the manager, and returns it.
/// </summary>
/// <typeparam name="T">The type of entity to retrieve or create. Must inherit from the Entity class and have a parameterless constructor.</typeparam>
/// <returns>The first entity of the specified type or a newly created entity of that type if none were found.</returns>
public T GetUniqueEntity<T>() where T : Entity, new()
{
var result = AllEntities.OfType<T>().FirstOrDefault();
if (result == null)
{
var newEntity = new T();
AddEntity(newEntity);
result = newEntity;
}
return result;
} }
public EntitySceneContainer? CurrentEntitySceneContainer => _currentEntitySceneContainer; #endregion
#region SCENE CONTAINER ACCESS
public void SetSceneContainer(EntitySceneContainer sceneContainer) public void SetSceneContainer(EntitySceneContainer sceneContainer)
{ {
@ -80,4 +94,7 @@ public partial class EntityManager : Node
{ {
_currentEntitySceneContainer = null; _currentEntitySceneContainer = null;
} }
#endregion
} }

@ -1,4 +1,5 @@
using Godot; using System;
using Godot;
using Godot.Collections; using Godot.Collections;
namespace Babushka.scripts.CSharp.GameEntity.Management; namespace Babushka.scripts.CSharp.GameEntity.Management;
@ -7,8 +8,18 @@ public partial class EntityNodeCreator : Node
{ {
[Export] private Dictionary<string, PackedScene> _entityPrefabs; [Export] private Dictionary<string, PackedScene> _entityPrefabs;
public Node2D CreateNode2D(string type) public Node2D InstantiateNode(string type)
{ {
if (string.IsNullOrEmpty(type))
{
throw new NullReferenceException("The type provided for Node instantiation cannot be null or empty.");
}
if (!_entityPrefabs.ContainsKey(type))
{
throw new Exception($"The type provided for Node instantiation ({type}) is not specified in the EntityNodeCreator dictionary.");
}
return _entityPrefabs[type].Instantiate<Node2D>(); return _entityPrefabs[type].Instantiate<Node2D>();
} }
} }

@ -1,4 +1,5 @@
using System.Linq; using System.Linq;
using Babushka.scripts.CSharp.GameEntity.Entities;
using Godot; using Godot;
using PositionalEntity = Babushka.scripts.CSharp.GameEntity.Entities.PositionalEntity; using PositionalEntity = Babushka.scripts.CSharp.GameEntity.Entities.PositionalEntity;
@ -16,6 +17,8 @@ public partial class EntitySceneContainer : Node2D
public override void _ExitTree() public override void _ExitTree()
{ {
EntityManager.Instance.UnsetSceneContainer(); EntityManager.Instance.UnsetSceneContainer();
var loadedScenesEntity = EntityManager.Instance.GetUniqueEntity<LoadedScenesEntity>();
loadedScenesEntity.AddScene(sceneName);
} }
public override void _Ready() public override void _Ready()
@ -33,7 +36,7 @@ public partial class EntitySceneContainer : Node2D
public void AddEntity(PositionalEntity entity) public void AddEntity(PositionalEntity entity)
{ {
entity.AddEntity(this); entity.InstantiateEntityNode(this);
} }
} }
Loading…
Cancel
Save