diff --git a/Content.Server/GameObjects/Components/Atmos/GasAnalyzerComponent.cs b/Content.Server/GameObjects/Components/Atmos/GasAnalyzerComponent.cs
index 0e5bd87125..777d238060 100644
--- a/Content.Server/GameObjects/Components/Atmos/GasAnalyzerComponent.cs
+++ b/Content.Server/GameObjects/Components/Atmos/GasAnalyzerComponent.cs
@@ -2,37 +2,39 @@
using Content.Server.GameObjects.EntitySystems;
using Content.Server.Interfaces;
using Content.Server.Interfaces.GameObjects.Components.Items;
+using Content.Server.Utility;
using Content.Shared.Atmos;
using Content.Shared.GameObjects.Components;
using Content.Shared.GameObjects.EntitySystems;
-using Content.Shared.Interfaces;
using Content.Shared.Interfaces.GameObjects.Components;
-using Content.Shared.Utility;
using Robust.Server.GameObjects.Components.UserInterface;
using Robust.Server.Interfaces.GameObjects;
using Robust.Server.Interfaces.Player;
using Robust.Shared.GameObjects;
using Robust.Shared.GameObjects.Systems;
+using Robust.Shared.Interfaces.Map;
using Robust.Shared.IoC;
using Robust.Shared.Localization;
using Robust.Shared.Map;
-using Robust.Shared.Utility;
-using System;
+using Robust.Shared.Maths;
using System.Collections.Generic;
namespace Content.Server.GameObjects.Components.Atmos
{
[RegisterComponent]
- public class GasAnalyzerComponent : SharedGasAnalyzerComponent, IAfterInteract, IDropped
+ public class GasAnalyzerComponent : SharedGasAnalyzerComponent, IAfterInteract, IDropped, IUse
{
#pragma warning disable 649
[Dependency] private IServerNotifyManager _notifyManager = default!;
+ [Dependency] private IMapManager _mapManager = default!;
#pragma warning restore 649
private BoundUserInterface _userInterface = default!;
private GasAnalyzerDanger _pressureDanger;
private float _timeSinceSync;
- private const float TimeBetweenSyncs = 10f;
+ private const float TimeBetweenSyncs = 2f;
+ private bool _checkPlayer = false; // Check at the player pos or at some other tile?
+ private GridCoordinates? _position; // The tile that we scanned
public override void Initialize()
{
@@ -49,9 +51,28 @@ namespace Content.Server.GameObjects.Components.Atmos
///
/// Call this from other components to open the gas analyzer UI.
+ /// Uses the player position.
///
+ /// The session to open the ui for
public void OpenInterface(IPlayerSession session)
{
+ _checkPlayer = true;
+ _position = null;
+ _userInterface.Open(session);
+ UpdateUserInterface();
+ Resync();
+ }
+
+ ///
+ /// Call this from other components to open the gas analyzer UI.
+ /// Uses a given position.
+ ///
+ /// The session to open the ui for
+ /// The position to analyze the gas
+ public void OpenInterface(IPlayerSession session, GridCoordinates pos)
+ {
+ _checkPlayer = false;
+ _position = pos;
_userInterface.Open(session);
UpdateUserInterface();
Resync();
@@ -59,6 +80,7 @@ namespace Content.Server.GameObjects.Components.Atmos
public void CloseInterface(IPlayerSession session)
{
+ _position = null;
_userInterface.Close(session);
Resync();
}
@@ -69,6 +91,7 @@ namespace Content.Server.GameObjects.Components.Atmos
if (_timeSinceSync > TimeBetweenSyncs)
{
Resync();
+ UpdateUserInterface();
}
}
@@ -103,9 +126,35 @@ namespace Content.Server.GameObjects.Components.Atmos
private void UpdateUserInterface()
{
string? error = null;
- var gam = EntitySystem.Get().GetGridAtmosphere(Owner.Transform.GridID);
- var tile = gam?.GetTile(Owner.Transform.GridPosition).Air;
+ // Check if the player is still holding the gas analyzer => if not, don't update
+ foreach (var session in _userInterface.SubscribedSessions)
+ {
+ if (session.AttachedEntity == null)
+ return;
+
+ if (!session.AttachedEntity.TryGetComponent(out IHandsComponent handsComponent))
+ return;
+
+ var activeHandEntity = handsComponent?.GetActiveHand?.Owner;
+ if (activeHandEntity == null || !activeHandEntity.TryGetComponent(out GasAnalyzerComponent gasAnalyzer))
+ {
+ return;
+ }
+ }
+
+ var pos = Owner.Transform.GridPosition;
+ if (!_checkPlayer && _position.HasValue)
+ {
+ // Check if position is out of range => don't update
+ if (!_position.Value.InRange(_mapManager, pos, SharedInteractionSystem.InteractionRange))
+ return;
+
+ pos = _position.Value;
+ }
+
+ var gam = EntitySystem.Get().GetGridAtmosphere(pos.GridID);
+ var tile = gam?.GetTile(pos).Air;
if (tile == null)
{
error = "No Atmosphere!";
@@ -172,13 +221,21 @@ namespace Content.Server.GameObjects.Components.Atmos
void IAfterInteract.AfterInteract(AfterInteractEventArgs eventArgs)
{
+ if (!eventArgs.CanReach)
+ {
+ _notifyManager.PopupMessage(eventArgs.User, eventArgs.User, Loc.GetString("You can't reach there!"));
+ return;
+ }
+
if (eventArgs.User.TryGetComponent(out IActorComponent actor))
{
- OpenInterface(actor.playerSession);
+ OpenInterface(actor.playerSession, eventArgs.ClickLocation);
//TODO: show other sprite when ui open?
}
}
+
+
void IDropped.Dropped(DroppedEventArgs eventArgs)
{
if (eventArgs.User.TryGetComponent(out IActorComponent actor))
@@ -187,5 +244,16 @@ namespace Content.Server.GameObjects.Components.Atmos
//TODO: if other sprite is shown, change again
}
}
+
+ bool IUse.UseEntity(UseEntityEventArgs eventArgs)
+ {
+ if (eventArgs.User.TryGetComponent(out IActorComponent actor))
+ {
+ OpenInterface(actor.playerSession);
+ //TODO: show other sprite when ui open?
+ return true;
+ }
+ return false;
+ }
}
}