using System;
using System.Collections.Generic;
using System.Diagnostics.CodeAnalysis;
using Robust.Shared.Players;
namespace Robust.Shared.GameObjects
{
public partial interface IEntityManager
{
///
/// A component was added to the manager.
///
event EventHandler? ComponentAdded;
///
/// A component was removed from the manager.
///
event EventHandler? ComponentRemoved;
///
/// A component was deleted. This is usually deferred until some time after it was removed.
/// Usually you will want to subscribe to .
///
event EventHandler? ComponentDeleted;
///
/// Calls Initialize() on all registered components of the entity.
///
void InitializeComponents(EntityUid uid);
///
/// Calls Startup() on all registered components of the entity.
///
void StartComponents(EntityUid uid);
///
/// Adds a Component type to an entity. If the entity is already Initialized, the component will
/// automatically be Initialized and Started.
///
/// Concrete component type to add.
/// The newly added component.
T AddComponent(EntityUid uid) where T : Component, new();
///
/// Adds an uninitialized Component type to an entity.
///
///
/// This function returns a disposable initialize handle that you can use in a statement, to set up a component
/// before initialization is ran on it.
///
/// Concrete component type to add.
/// Entity being modified.
/// Component initialization handle. When you are done setting up the component, make sure to dispose this.
EntityManager.CompInitializeHandle AddComponentUninitialized(EntityUid uid) where T : Component, new();
///
/// Adds a Component to an entity. If the entity is already Initialized, the component will
/// automatically be Initialized and Started.
///
/// Entity being modified.
/// Component to add.
/// Should it overwrite existing components?
void AddComponent(EntityUid uid, T component, bool overwrite = false) where T : Component;
///
/// Removes the component with the specified reference type,
/// Without needing to have the component itself.
///
/// The component reference type to remove.
/// Entity UID to modify.
void RemoveComponent(EntityUid uid);
///
/// Removes the component with a specified type.
///
/// Entity UID to modify.
/// A trait or component type to check for.
void RemoveComponent(EntityUid uid, Type type);
///
/// Removes the component with a specified network ID.
///
/// Entity UID to modify.
/// Network ID of the component to remove.
void RemoveComponent(EntityUid uid, ushort netID);
///
/// Removes the specified component.
///
/// Entity UID to modify.
/// Component to remove.
void RemoveComponent(EntityUid uid, IComponent component);
///
/// Removes all components from an entity, except the required components.
///
/// Entity UID to modify.
void RemoveComponents(EntityUid uid);
///
/// Removes ALL components from an entity. This includes the required components,
/// and . This should ONLY be
/// used when deleting an entity.
///
/// Entity UID to modify.
void DisposeComponents(EntityUid uid);
///
/// Checks if the entity has a component type.
///
/// Component reference type to check for.
/// Entity UID to check.
/// True if the entity has the component type, otherwise false.
bool HasComponent(EntityUid uid);
///
/// Checks if the entity has a component type.
///
/// Component reference type to check for.
/// Entity UID to check.
/// True if the entity has the component type, otherwise false.
bool HasComponent(EntityUid? uid);
///
/// Checks if the entity has a component type.
///
/// Entity UID to check.
/// A trait or component type to check for.
/// True if the entity has the component type, otherwise false.
bool HasComponent(EntityUid uid, Type type);
///
/// Checks if the entity has a component type.
///
/// Entity UID to check.
/// A trait or component type to check for.
/// True if the entity has the component type, otherwise false.
bool HasComponent(EntityUid ?uid, Type type);
///
/// Checks if the entity has a component with a given network ID. This does not check
/// if the component is deleted.
///
/// Entity UID to check.
/// Network ID to check for.
/// True if the entity has a component with the given network ID, otherwise false.
bool HasComponent(EntityUid uid, ushort netId);
///
/// Checks if the entity has a component with a given network ID. This does not check
/// if the component is deleted.
///
/// Entity UID to check.
/// Network ID to check for.
/// True if the entity has a component with the given network ID, otherwise false.
bool HasComponent(EntityUid? uid, ushort netId);
///
/// This method will always return a component for a certain entity, adding it if it's not there already.
///
/// Entity to modify.
/// Component to add.
/// The component in question
T EnsureComponent(EntityUid uid) where T : Component, new();
///
/// This method will always return a component for a certain entity, adding it if it's not there already.
///
/// Entity to modify.
/// The output component after being ensured.
/// Component to add.
/// The component in question
bool EnsureComponent(EntityUid uid, out T component) where T : Component, new();
///
/// Returns the component of a specific type.
///
/// A trait or type of a component to retrieve.
/// Entity UID to look on.
/// The component of Type from the Entity.
T GetComponent(EntityUid uid);
///
/// Returns the component of a specific type.
///
/// Entity UID to look on.
/// A trait or component type to check for.
/// The component of Type from the Entity.
IComponent GetComponent(EntityUid uid, Type type);
///
/// Returns the component with a specific network ID. This does not check
/// if the component is deleted.
///
/// Entity UID to look on.
/// Network ID of the component to retrieve.
/// The component with the specified network id.
IComponent GetComponent(EntityUid uid, ushort netId);
///
/// Returns the component of a specific type.
///
/// A trait or type of a component to retrieve.
/// Entity UID to check.
/// Component of the specified type (if exists).
/// If the component existed in the entity.
bool TryGetComponent(EntityUid uid, [NotNullWhen(true)] out T component);
///
/// Returns the component of a specific type.
///
/// A trait or type of a component to retrieve.
/// Entity UID to check.
/// Component of the specified type (if exists).
/// If the component existed in the entity.
bool TryGetComponent([NotNullWhen(true)] EntityUid? uid, [NotNullWhen(true)] out T component);
///
/// Returns the component of a specific type.
///
/// Entity UID to check.
/// A trait or component type to check for.
/// Component of the specified type (if exists).
/// If the component existed in the entity.
bool TryGetComponent(EntityUid uid, Type type, [NotNullWhen(true)] out IComponent? component);
///
/// Returns the component of a specific type.
///
/// Entity UID to check.
/// A trait or component type to check for.
/// Component of the specified type (if exists).
/// If the component existed in the entity.
bool TryGetComponent([NotNullWhen(true)] EntityUid? uid, Type type, [NotNullWhen(true)] out IComponent? component);
///
/// Returns the component with a specified network ID. This does not check
/// if the component is deleted.
///
/// Entity UID to check.
/// Component Network ID to check for.
/// Component with the specified network id.
/// If the component existed in the entity.
bool TryGetComponent(EntityUid uid, ushort netId, [NotNullWhen(true)] out IComponent? component);
///
/// Returns the component with a specified network ID. This does not check
/// if the component is deleted.
///
/// Entity UID to check.
/// Component Network ID to check for.
/// Component with the specified network id.
/// If the component existed in the entity.
bool TryGetComponent([NotNullWhen(true)] EntityUid? uid, ushort netId, [NotNullWhen(true)] out IComponent? component);
///
/// Returns a cached struct enumerator with the specified component.
///
EntityQuery GetEntityQuery() where TComp1 : Component;
///
/// Returns ALL component type instances on an entity. A single component instance
/// can have multiple component types.
///
/// Entity UID to look on.
/// All component types on the Entity.
IEnumerable GetComponents(EntityUid uid);
///
/// Returns ALL component type instances that are assignable to the specified type.
/// A single component instance can have multiple component type instances.
///
/// A trait or type of a component to retrieve.
/// Entity UID to look on.
/// All components that are assignable to the specified type.
IEnumerable GetComponents(EntityUid uid);
///
/// Returns ALL networked components on an entity, including deleted ones.
///
/// Entity UID to look on.
/// All components that have a network ID.
NetComponentEnumerable GetNetComponents(EntityUid uid);
///
/// Gets a component state.
///
/// A reference to the event bus instance.
/// Component to generate the state for.
/// The component state of the component.
///
ComponentState GetComponentState(IEventBus eventBus, IComponent component);
///
/// Checks if a certain player should get a component state.
///
/// A reference to the event bus instance.
/// Component to generate the state for.
/// The player to generate the state for.
/// True if the player should get the component state.
bool CanGetComponentState(IEventBus eventBus, IComponent component, ICommonSession player);
///
/// Returns ALL component instances of a specified type.
///
/// A trait or type of a component to retrieve.
/// All components that have the specified type.
IEnumerable EntityQuery(bool includePaused = false) where T: IComponent;
///
/// Returns the relevant components from all entities that contain the two required components.
///
/// First required component.
/// Second required component.
/// The pairs of components from each entity that has the two required components.
IEnumerable<(TComp1, TComp2)> EntityQuery(bool includePaused = false)
where TComp1 : IComponent
where TComp2 : IComponent;
///
/// Returns the relevant components from all entities that contain the three required components.
///
/// First required component.
/// Second required component.
/// Third required component.
/// The pairs of components from each entity that has the three required components.
IEnumerable<(TComp1, TComp2, TComp3)> EntityQuery(bool includePaused = false)
where TComp1 : IComponent
where TComp2 : IComponent
where TComp3 : IComponent;
///
/// Returns the relevant components from all entities that contain the four required components.
///
/// First required component.
/// Second required component.
/// Third required component.
/// Fourth required component.
/// The pairs of components from each entity that has the four required components.
IEnumerable<(TComp1, TComp2, TComp3, TComp4)> EntityQuery(bool includePaused = false)
where TComp1 : IComponent
where TComp2 : IComponent
where TComp3 : IComponent
where TComp4 : IComponent;
///
/// Returns ALL component instances of a specified type.
///
/// A trait or component type to check for.
///
/// All components that are the specified type.
IEnumerable GetAllComponents(Type type, bool includePaused = false);
///
/// Culls all components from the collection that are marked as deleted. This needs to be called often.
///
void CullRemovedComponents();
}
}