using Content.Shared.Abilities.Psionics; using Content.Server.Abilities.Psionics; using Content.Shared.Eye; using Content.Server.NPC.Systems; using Robust.Shared.Containers; using Robust.Shared.Player; using Robust.Server.GameObjects; using Content.Shared.NPC.Systems; namespace Content.Server.Psionics { public sealed class PsionicInvisibilitySystem : EntitySystem { [Dependency] private readonly VisibilitySystem _visibilitySystem = default!; [Dependency] private readonly PsionicInvisibilityPowerSystem _invisSystem = default!; [Dependency] private readonly NpcFactionSystem _npcFactonSystem = default!; [Dependency] private readonly SharedEyeSystem _eye = default!; public override void Initialize() { base.Initialize(); /// Masking SubscribeLocalEvent(OnInit); SubscribeLocalEvent(OnInsulInit); SubscribeLocalEvent(OnInsulShutdown); /// Layer SubscribeLocalEvent(OnInvisInit); SubscribeLocalEvent(OnInvisShutdown); // PVS Stuff SubscribeLocalEvent(OnEntInserted); SubscribeLocalEvent(OnEntRemoved); } private void OnInit(EntityUid uid, ActorComponent component, ComponentInit args) { if (!HasComp(uid)) SetCanSeePsionicInvisiblity(uid, false); } private void OnInsulInit(EntityUid uid, PsionicInsulationComponent component, ComponentInit args) { if (HasComp(uid)) _invisSystem.ToggleInvisibility(uid); if (_npcFactonSystem.ContainsFaction(uid, "PsionicInterloper")) { component.SuppressedFactions.Add("PsionicInterloper"); _npcFactonSystem.RemoveFaction(uid, "PsionicInterloper"); } if (_npcFactonSystem.ContainsFaction(uid, "GlimmerMonster")) { component.SuppressedFactions.Add("GlimmerMonster"); _npcFactonSystem.RemoveFaction(uid, "GlimmerMonster"); } SetCanSeePsionicInvisiblity(uid, true); } private void OnInsulShutdown(EntityUid uid, PsionicInsulationComponent component, ComponentShutdown args) { SetCanSeePsionicInvisiblity(uid, false); if (!HasComp(uid)) { component.SuppressedFactions.Clear(); return; } foreach (var faction in component.SuppressedFactions) { _npcFactonSystem.AddFaction(uid, faction); } component.SuppressedFactions.Clear(); } private void OnInvisInit(EntityUid uid, PsionicallyInvisibleComponent component, ComponentStartup args) { var visibility = EntityManager.EnsureComponent(uid); _visibilitySystem.AddLayer((uid, visibility), (int) VisibilityFlags.PsionicInvisibility, false); _visibilitySystem.RemoveLayer((uid, visibility), (int) VisibilityFlags.Normal, false); _visibilitySystem.RefreshVisibility(uid, visibility); } private void OnInvisShutdown(EntityUid uid, PsionicallyInvisibleComponent component, ComponentShutdown args) { if (TryComp(uid, out var visibility)) { _visibilitySystem.RemoveLayer((uid, visibility), (int) VisibilityFlags.PsionicInvisibility, false); _visibilitySystem.AddLayer((uid, visibility), (int) VisibilityFlags.Normal, false); _visibilitySystem.RefreshVisibility(uid, visibility); } } private void OnEntInserted(EntityUid uid, PsionicallyInvisibleComponent component, EntInsertedIntoContainerMessage args) { DirtyEntity(args.Entity); } private void OnEntRemoved(EntityUid uid, PsionicallyInvisibleComponent component, EntRemovedFromContainerMessage args) { DirtyEntity(args.Entity); } public void SetCanSeePsionicInvisiblity(EntityUid uid, bool set) { if (set == true) { if (EntityManager.TryGetComponent(uid, out EyeComponent? eye)) { _eye.SetVisibilityMask(uid, eye.VisibilityMask | (int) VisibilityFlags.PsionicInvisibility, eye); } } else { if (EntityManager.TryGetComponent(uid, out EyeComponent? eye)) { _eye.SetVisibilityMask(uid, eye.VisibilityMask & ~(int) VisibilityFlags.PsionicInvisibility, eye); } } } } }