diff --git a/Content.Server/DeviceNetwork/Systems/DeviceNetworkJammerSystem.cs b/Content.Server/DeviceNetwork/Systems/DeviceNetworkJammerSystem.cs new file mode 100644 index 00000000000000..3d3820562d6fad --- /dev/null +++ b/Content.Server/DeviceNetwork/Systems/DeviceNetworkJammerSystem.cs @@ -0,0 +1,38 @@ +using Content.Server.DeviceNetwork.Components; +using Content.Shared.DeviceNetwork.Components; +using Robust.Server.GameObjects; + +namespace Content.Server.DeviceNetwork.Systems; + +public sealed class DeviceNetworkJammerSystem : EntitySystem +{ + [Dependency] private TransformSystem _transform = default!; + public override void Initialize() + { + base.Initialize(); + + SubscribeLocalEvent(BeforePacketSent); + } + + private void BeforePacketSent(EntityUid uid, TransformComponent xform, BeforePacketSentEvent ev) + { + if (ev.Cancelled) + return; + + var query = EntityQueryEnumerator(); + + while (query.MoveNext(out _, out var jammerComp, out var jammerXform)) + { + if (!jammerComp.JammableNetworks.Contains(ev.NetworkId)) + continue; + + if (jammerXform.Coordinates.InRange(EntityManager, _transform, ev.SenderTransform.Coordinates, jammerComp.Range) + || jammerXform.Coordinates.InRange(EntityManager, _transform, xform.Coordinates, jammerComp.Range)) + { + ev.Cancel(); + return; + } + } + } + +} diff --git a/Content.Server/DeviceNetwork/Systems/DeviceNetworkSystem.cs b/Content.Server/DeviceNetwork/Systems/DeviceNetworkSystem.cs index 83967c9bbd4143..20ee7a5dd1bdfc 100644 --- a/Content.Server/DeviceNetwork/Systems/DeviceNetworkSystem.cs +++ b/Content.Server/DeviceNetwork/Systems/DeviceNetworkSystem.cs @@ -351,13 +351,14 @@ private void SendToConnections(ReadOnlySpan connections, var xform = Transform(packet.Sender); - BeforePacketSentEvent beforeEv = new(packet.Sender, xform, _transformSystem.GetWorldPosition(xform)); + var senderPos = _transformSystem.GetWorldPosition(xform); foreach (var connection in connections) { if (connection.Owner == packet.Sender) continue; + BeforePacketSentEvent beforeEv = new(packet.Sender, xform, senderPos, connection.NetIdEnum.ToString()); RaiseLocalEvent(connection.Owner, beforeEv, false); if (!beforeEv.Cancelled) @@ -386,11 +387,17 @@ public sealed class BeforePacketSentEvent : CancellableEntityEventArgs /// public readonly Vector2 SenderPosition; - public BeforePacketSentEvent(EntityUid sender, TransformComponent xform, Vector2 senderPosition) + /// + /// The network the packet will be sent to. + /// + public readonly string NetworkId; + + public BeforePacketSentEvent(EntityUid sender, TransformComponent xform, Vector2 senderPosition, string networkId) { Sender = sender; SenderTransform = xform; SenderPosition = senderPosition; + NetworkId = networkId; } } diff --git a/Content.Server/DeviceNetwork/Systems/SingletonDeviceNetServerSystem.cs b/Content.Server/DeviceNetwork/Systems/SingletonDeviceNetServerSystem.cs index fd62514d006bc3..cdc083feacd127 100644 --- a/Content.Server/DeviceNetwork/Systems/SingletonDeviceNetServerSystem.cs +++ b/Content.Server/DeviceNetwork/Systems/SingletonDeviceNetServerSystem.cs @@ -1,4 +1,5 @@ -using Content.Server.DeviceNetwork.Components; +using System.Diagnostics.CodeAnalysis; +using Content.Server.DeviceNetwork.Components; using Content.Server.Medical.CrewMonitoring; using Content.Server.Power.Components; using Content.Server.Station.Systems; @@ -38,7 +39,7 @@ public bool IsActiveServer(EntityUid serverId, SingletonDeviceNetServerComponent /// The address of the active server if it exists /// The component type that determines what type of server you're getting the address of /// True if there is an active serve. False otherwise - public bool TryGetActiveServerAddress(EntityUid stationId, out string? address) where TComp : IComponent + public bool TryGetActiveServerAddress(EntityUid stationId, [NotNullWhen(true)] out string? address) where TComp : IComponent { var servers = EntityQueryEnumerator< SingletonDeviceNetServerComponent, diff --git a/Content.Server/Medical/SuitSensors/SuitSensorComponent.cs b/Content.Server/Medical/SuitSensors/SuitSensorComponent.cs index 8d75d3840afe31..9079655c80c15a 100644 --- a/Content.Server/Medical/SuitSensors/SuitSensorComponent.cs +++ b/Content.Server/Medical/SuitSensors/SuitSensorComponent.cs @@ -87,9 +87,3 @@ public sealed partial class SuitSensorComponent : Component [DataField, ViewVariables] public bool PreviousControlsLocked = false; } - -[ByRefEvent] -public record struct SuitSensorsSendAttemptEvent -{ - public bool Cancelled; -}; diff --git a/Content.Server/Medical/SuitSensors/SuitSensorSystem.cs b/Content.Server/Medical/SuitSensors/SuitSensorSystem.cs index f19b3d5b81407e..b807b63e21f668 100644 --- a/Content.Server/Medical/SuitSensors/SuitSensorSystem.cs +++ b/Content.Server/Medical/SuitSensors/SuitSensorSystem.cs @@ -73,11 +73,6 @@ public override void Update(float frameTime) // TODO: This would cause imprecision at different tick rates. sensor.NextUpdate = curTime + sensor.UpdateRate; - var canEv = new SuitSensorsSendAttemptEvent(); - RaiseLocalEvent(uid, ref canEv); - if (canEv.Cancelled) - continue; - // get sensor status var status = GetSensorState(uid, sensor); if (status == null) diff --git a/Content.Server/Radio/EntitySystems/JammerSystem.cs b/Content.Server/Radio/EntitySystems/JammerSystem.cs index fdf02f94df5cbd..1258cc10fa0eed 100644 --- a/Content.Server/Radio/EntitySystems/JammerSystem.cs +++ b/Content.Server/Radio/EntitySystems/JammerSystem.cs @@ -1,8 +1,12 @@ -using Content.Server.Medical.SuitSensors; +using Content.Server.DeviceNetwork.Components; +using Content.Server.DeviceNetwork.Systems; +using Content.Server.Medical.CrewMonitoring; using Content.Server.Popups; using Content.Server.Power.EntitySystems; using Content.Server.PowerCell; using Content.Server.Radio.Components; +using Content.Server.Station.Systems; +using Content.Shared.DeviceNetwork.Components; using Content.Shared.Examine; using Content.Shared.Interaction; using Content.Shared.PowerCell.Components; @@ -15,6 +19,8 @@ public sealed class JammerSystem : EntitySystem [Dependency] private readonly BatterySystem _battery = default!; [Dependency] private readonly PopupSystem _popup = default!; [Dependency] private readonly SharedTransformSystem _transform = default!; + [Dependency] private readonly StationSystem _stationSystem = default!; + [Dependency] private readonly SingletonDeviceNetServerSystem _singletonServerSystem = default!; public override void Initialize() { @@ -24,7 +30,6 @@ public override void Initialize() SubscribeLocalEvent(OnPowerCellChanged); SubscribeLocalEvent(OnExamine); SubscribeLocalEvent(OnRadioSendAttempt); - SubscribeLocalEvent(OnSensorSendAttempt); } public override void Update(float frameTime) @@ -36,6 +41,7 @@ public override void Update(float frameTime) !_battery.TryUseCharge(batteryUid.Value, jam.Wattage * frameTime, battery)) { RemComp(uid); + RemComp(uid); } } } @@ -48,10 +54,19 @@ private void OnActivate(EntityUid uid, RadioJammerComponent comp, ActivateInWorl if (activated) { EnsureComp(uid); + var stationId = _stationSystem.GetOwningStation(uid); + if (stationId != null && _singletonServerSystem.TryGetActiveServerAddress(stationId.Value, out var netId)) + { + EnsureComp(uid, out var jammingComp); + jammingComp.Range = comp.Range; + jammingComp.JammableNetworks.Add(netId); + Dirty(uid, jammingComp); + } } else { RemComp(uid); + RemComp(uid); } var state = Loc.GetString(activated ? "radio-jammer-component-on-state" : "radio-jammer-component-off-state"); var message = Loc.GetString("radio-jammer-component-on-use", ("state", state)); @@ -84,14 +99,6 @@ private void OnRadioSendAttempt(ref RadioSendAttemptEvent args) } } - private void OnSensorSendAttempt(EntityUid uid, SuitSensorComponent comp, ref SuitSensorsSendAttemptEvent args) - { - if (ShouldCancelSend(uid)) - { - args.Cancelled = true; - } - } - private bool ShouldCancelSend(EntityUid sourceUid) { var source = Transform(sourceUid).Coordinates; diff --git a/Content.Shared/DeviceNetwork/Components/DeviceNetworkJammerComponent.cs b/Content.Shared/DeviceNetwork/Components/DeviceNetworkJammerComponent.cs new file mode 100644 index 00000000000000..75de0cb8a254b1 --- /dev/null +++ b/Content.Shared/DeviceNetwork/Components/DeviceNetworkJammerComponent.cs @@ -0,0 +1,24 @@ +using Robust.Shared.GameStates; + +namespace Content.Shared.DeviceNetwork.Components; + +/// +/// Allow entities to jam DeviceNetwork packets. +/// +[RegisterComponent, NetworkedComponent, AutoGenerateComponentState] +public sealed partial class DeviceNetworkJammerComponent : Component +{ + /// + /// Range where packets will be jammed. This is checked both against the sender and receiver. + /// + [DataField, AutoNetworkedField] + public float Range = 5.0f; + + /// + /// Device networks that can be jammed. For a list of default NetworkIds see DeviceNetIdDefaults on Content.Server. + /// Network ids are not guaranteed to be limited to DeviceNetIdDefaults. + /// + [DataField, AutoNetworkedField] + public HashSet JammableNetworks = []; + +}