using System; using System.Collections.Generic; namespace IgniteEngine { /// /// Class for objects that can be referenced. /// public class Object : IDisposable { /// /// The name of the object. /// public string Name => GetName(); /// /// Keeps track of the number of all object types. /// private static readonly Dictionary TypeCounts = new Dictionary(); /// /// An object to lock for TypeCounts access. /// private static readonly object TypeCountsLock = new object(); /// /// Creates a new instance of the class. /// public Object() { var type = GetType(); EnsureTypeExists(type); lock (TypeCountsLock) { TypeCounts[type]++; } } /// /// This method is called whenever an is deconstructed. /// ~Object() { var type = GetType(); EnsureTypeExists(type); lock (TypeCountsLock) { TypeCounts[type]--; } } /// /// Destroys the object. /// /// The object to destroy. public static void Destroy(Object obj) { obj.Dispose(); } /// /// Determines if the object exists. /// /// The object to check. public static implicit operator bool(Object obj) { return obj != null; } /// /// Ensures that the TypeCounts dictionary contains the type. /// If the type is not found, it is added to the dictionary with a count of 0. /// /// The type to check for. private static void EnsureTypeExists(Type type) { lock (TypeCountsLock) { if (!TypeCounts.ContainsKey(type)) { TypeCounts.Add(type, 0); } } } /// /// Use the static method Object.Destroy() instead. /// public void Dispose() { Destroy(); } /// /// Gets the name of the object instance. The name is based on how /// many instances of the object there are. /// /// The name of the object. public string GetName() { var type = GetType(); EnsureTypeExists(type); lock (TypeCountsLock) { return $"{type.Name} {TypeCounts[type]}"; } } /// /// Returns the name of the object. /// /// The name of the object. public override string ToString() { return Name; } /// /// This method does nothing unless it is overidded by the top-level /// implementation of the class. /// protected virtual void Destroy() { } } }