| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171 |
- using Content.Server.Popups;
- using Content.Shared.Abilities.Mime;
- using Content.Shared.Actions;
- using Content.Shared.Actions.Events;
- using Content.Shared.Alert;
- using Content.Shared.Coordinates.Helpers;
- using Content.Shared.Maps;
- using Content.Shared.Paper;
- using Content.Shared.Physics;
- using Robust.Shared.Containers;
- using Robust.Shared.Map;
- using Robust.Shared.Timing;
- using Content.Shared.Speech.Muting;
- namespace Content.Server.Abilities.Mime
- {
- public sealed class MimePowersSystem : EntitySystem
- {
- [Dependency] private readonly PopupSystem _popupSystem = default!;
- [Dependency] private readonly SharedActionsSystem _actionsSystem = default!;
- [Dependency] private readonly AlertsSystem _alertsSystem = default!;
- [Dependency] private readonly TurfSystem _turf = default!;
- [Dependency] private readonly IMapManager _mapMan = default!;
- [Dependency] private readonly SharedContainerSystem _container = default!;
- [Dependency] private readonly IGameTiming _timing = default!;
- public override void Initialize()
- {
- base.Initialize();
- SubscribeLocalEvent<MimePowersComponent, ComponentInit>(OnComponentInit);
- SubscribeLocalEvent<MimePowersComponent, InvisibleWallActionEvent>(OnInvisibleWall);
- SubscribeLocalEvent<MimePowersComponent, BreakVowAlertEvent>(OnBreakVowAlert);
- SubscribeLocalEvent<MimePowersComponent, RetakeVowAlertEvent>(OnRetakeVowAlert);
- }
- public override void Update(float frameTime)
- {
- base.Update(frameTime);
- // Queue to track whether mimes can retake vows yet
- var query = EntityQueryEnumerator<MimePowersComponent>();
- while (query.MoveNext(out var uid, out var mime))
- {
- if (!mime.VowBroken || mime.ReadyToRepent)
- continue;
- if (_timing.CurTime < mime.VowRepentTime)
- continue;
- mime.ReadyToRepent = true;
- _popupSystem.PopupEntity(Loc.GetString("mime-ready-to-repent"), uid, uid);
- }
- }
- private void OnComponentInit(EntityUid uid, MimePowersComponent component, ComponentInit args)
- {
- EnsureComp<MutedComponent>(uid);
- if (component.PreventWriting)
- {
- EnsureComp<BlockWritingComponent>(uid, out var illiterateComponent);
- illiterateComponent.FailWriteMessage = component.FailWriteMessage;
- Dirty(uid, illiterateComponent);
- }
- _alertsSystem.ShowAlert(uid, component.VowAlert);
- _actionsSystem.AddAction(uid, ref component.InvisibleWallActionEntity, component.InvisibleWallAction, uid);
- }
- /// <summary>
- /// Creates an invisible wall in a free space after some checks.
- /// </summary>
- private void OnInvisibleWall(EntityUid uid, MimePowersComponent component, InvisibleWallActionEvent args)
- {
- if (!component.Enabled)
- return;
- if (_container.IsEntityOrParentInContainer(uid))
- return;
- var xform = Transform(uid);
- // Get the tile in front of the mime
- var offsetValue = xform.LocalRotation.ToWorldVec();
- var coords = xform.Coordinates.Offset(offsetValue).SnapToGrid(EntityManager, _mapMan);
- var tile = coords.GetTileRef(EntityManager, _mapMan);
- if (tile == null)
- return;
- // Check if the tile is blocked by a wall or mob, and don't create the wall if so
- if (_turf.IsTileBlocked(tile.Value, CollisionGroup.Impassable | CollisionGroup.Opaque))
- {
- _popupSystem.PopupEntity(Loc.GetString("mime-invisible-wall-failed"), uid, uid);
- return;
- }
- _popupSystem.PopupEntity(Loc.GetString("mime-invisible-wall-popup", ("mime", uid)), uid);
- // Make sure we set the invisible wall to despawn properly
- Spawn(component.WallPrototype, _turf.GetTileCenter(tile.Value));
- // Handle args so cooldown works
- args.Handled = true;
- }
- private void OnBreakVowAlert(Entity<MimePowersComponent> ent, ref BreakVowAlertEvent args)
- {
- if (args.Handled)
- return;
- BreakVow(ent, ent);
- args.Handled = true;
- }
- private void OnRetakeVowAlert(Entity<MimePowersComponent> ent, ref RetakeVowAlertEvent args)
- {
- if (args.Handled)
- return;
- RetakeVow(ent, ent);
- args.Handled = true;
- }
- /// <summary>
- /// Break this mime's vow to not speak.
- /// </summary>
- public void BreakVow(EntityUid uid, MimePowersComponent? mimePowers = null)
- {
- if (!Resolve(uid, ref mimePowers))
- return;
- if (mimePowers.VowBroken)
- return;
- mimePowers.Enabled = false;
- mimePowers.VowBroken = true;
- mimePowers.VowRepentTime = _timing.CurTime + mimePowers.VowCooldown;
- RemComp<MutedComponent>(uid);
- if (mimePowers.PreventWriting)
- RemComp<BlockWritingComponent>(uid);
- _alertsSystem.ClearAlert(uid, mimePowers.VowAlert);
- _alertsSystem.ShowAlert(uid, mimePowers.VowBrokenAlert);
- _actionsSystem.RemoveAction(uid, mimePowers.InvisibleWallActionEntity);
- }
- /// <summary>
- /// Retake this mime's vow to not speak.
- /// </summary>
- public void RetakeVow(EntityUid uid, MimePowersComponent? mimePowers = null)
- {
- if (!Resolve(uid, ref mimePowers))
- return;
- if (!mimePowers.ReadyToRepent)
- {
- _popupSystem.PopupEntity(Loc.GetString("mime-not-ready-repent"), uid, uid);
- return;
- }
- mimePowers.Enabled = true;
- mimePowers.ReadyToRepent = false;
- mimePowers.VowBroken = false;
- AddComp<MutedComponent>(uid);
- if (mimePowers.PreventWriting)
- {
- EnsureComp<BlockWritingComponent>(uid, out var illiterateComponent);
- illiterateComponent.FailWriteMessage = mimePowers.FailWriteMessage;
- Dirty(uid, illiterateComponent);
- }
- _alertsSystem.ClearAlert(uid, mimePowers.VowBrokenAlert);
- _alertsSystem.ShowAlert(uid, mimePowers.VowAlert);
- _actionsSystem.AddAction(uid, ref mimePowers.InvisibleWallActionEntity, mimePowers.InvisibleWallAction, uid);
- }
- }
- }
|