using System.Globalization; using System.Linq; using Content.Client.Stylesheets; using Content.Shared.Atmos; using Content.Shared.Atmos.Components; using Content.Shared.Atmos.Monitor; using Content.Shared.FixedPoint; using Robust.Client.AutoGenerated; using Robust.Client.Graphics; using Robust.Client.ResourceManagement; using Robust.Client.UserInterface.Controls; using Robust.Client.UserInterface.XAML; using Robust.Shared.Map; namespace Content.Client._NF.Atmos.Consoles; [GenerateTypedNameReferences] public sealed partial class AtmosAlarmGaslockEntryContainer : BoxContainer { public NetEntity NetEntity; public EntityCoordinates? Coordinates; private readonly IEntityManager _entManager; private readonly IResourceCache _cache; public event Action? SendChangeDirectionMessageAction; public event Action? SendPressureChangeAction; public event Action? SendChangeEnabledAction; public event Action? SendUndockAction; private bool _lastDirectionInwards; private bool _lastEnabled; private bool _lastDocked; private readonly Dictionary _gasShorthands = new() { [Gas.Ammonia] = "NH₃", [Gas.CarbonDioxide] = "CO₂", [Gas.Frezon] = "F", [Gas.Nitrogen] = "N₂", [Gas.NitrousOxide] = "N₂O", [Gas.Oxygen] = "O₂", [Gas.Plasma] = "P", [Gas.Tritium] = "T", [Gas.WaterVapor] = "H₂O", [Gas.Respiron] = "R", // Frontier }; public AtmosAlarmGaslockEntryContainer(NetEntity uid, EntityCoordinates? coordinates) { RobustXamlLoader.Load(this); _entManager = IoCManager.Resolve(); _cache = IoCManager.Resolve(); NetEntity = uid; Coordinates = coordinates; // Load fonts var headerFont = new VectorFont(_cache.GetResource("/Fonts/NotoSans/NotoSans-Bold.ttf"), 11); NoDataLabel.FontOverride = headerFont; DirectionLabel.OnPressed += _ => TrySendDirectionChangeAction(); PressureInput.OnTextEntered += _ => TrySendPressureChangeAction(); EnabledLabel.OnPressed += _ => TrySendEnableChangeAction(); DockedLabel.OnPressed += _ => TrySendUndockAction(); } public void TrySendDirectionChangeAction() { SendChangeDirectionMessageAction?.Invoke(NetEntity, !_lastDirectionInwards); } public void TrySendPressureChangeAction() { if (SendPressureChangeAction == null) return; if (!float.TryParse(PressureInput.Text, out var result)) return; SendPressureChangeAction(NetEntity, result); } public void TrySendEnableChangeAction() { SendChangeEnabledAction?.Invoke(NetEntity, !_lastEnabled); } public void TrySendUndockAction() { if (SendUndockAction == null) return; if (!_lastDocked) return; SendUndockAction(NetEntity); } public void UpdateEntry(AtmosAlertsComputerEntry entry, bool isFocus, AtmosAlertsFocusGaslockData? focusData = null) { NetEntity = entry.NetEntity; Coordinates = _entManager.GetCoordinates(entry.Coordinates); // Load fonts var normalFont = new VectorFont(_cache.GetResource("/Fonts/NotoSansDisplay/NotoSansDisplay-Regular.ttf"), 11); AlarmStateLabel.Text = Loc.GetString("atmos-alerts-window-normal-state"); AlarmStateLabel.FontColorOverride = StyleNano.GoodGreenFore; // Update alarm name AlarmNameLabel.Text = Loc.GetString("atmos-alerts-window-alarm-label", ("name", entry.EntityName), ("address", entry.Address)); // Focus updates FocusContainer.Visible = isFocus; if (isFocus) SetAsFocus(); else RemoveAsFocus(); // Frontier: update state if (focusData != null) { _lastDirectionInwards = focusData.Value.PumpingInwards; _lastEnabled = focusData.Value.Enabled; _lastDocked = focusData.Value.DockedEntity != NetEntity.Invalid; } // End Frontier if (!isFocus || entry.Group != AtmosAlertsComputerGroup.Gaslock) return; MainDataContainer.Visible = entry.AlarmState != AtmosAlarmType.Invalid; NoDataLabel.Visible = entry.AlarmState == AtmosAlarmType.Invalid; if (focusData == null) return; DirectionLabel.Text = Loc.GetString(focusData.Value.PumpingInwards ? "atmos-alerts-window-direction-inwards" : "atmos-alerts-window-direction-outwards"); // Update pressure (if user is not editing text) if (!PressureInput.HasKeyboardFocus()) PressureInput.Text = focusData.Value.Pressure.ToString(CultureInfo.InvariantCulture); EnabledLabel.Text = Loc.GetString(focusData.Value.Enabled ? "atmos-alerts-window-enabled-on" : "atmos-alerts-window-enabled-off"); DockedLabel.Text = Loc.GetString(focusData.Value.DockedEntity == NetEntity.Invalid ? "atmos-alerts-window-docked-off" : "atmos-alerts-window-docked-on"); DockedLabel.Disabled = focusData.Value.DockedEntity == NetEntity.Invalid; // Update other present gases GasGridContainer.RemoveAllChildren(); var gasData = focusData.Value.GasData; if (!gasData.Any()) { // No other gases var gasLabel = new Label { Text = Loc.GetString("atmos-alerts-window-other-gases-value-nil"), FontOverride = normalFont, FontColorOverride = StyleNano.DisabledFore, HorizontalAlignment = HAlignment.Center, VerticalAlignment = VAlignment.Center, HorizontalExpand = true, Margin = new Thickness(0, 2, 0, 0), SetHeight = 24f, }; GasGridContainer.AddChild(gasLabel); } else { // Add an entry for each gas foreach (var (gas, (_, percent)) in gasData) { FixedPoint2 gasPercent = percent * 100f; var gasShorthand = _gasShorthands.GetValueOrDefault(gas, "X"); var gasLabel = new Label { Text = Loc.GetString("atmos-alerts-window-other-gases-value", ("shorthand", gasShorthand), ("value", gasPercent)), FontOverride = normalFont, FontColorOverride = StyleNano.GoodGreenFore, HorizontalAlignment = HAlignment.Center, VerticalAlignment = VAlignment.Center, HorizontalExpand = true, Margin = new Thickness(0, 2, 0, 0), SetHeight = 24f, }; GasGridContainer.AddChild(gasLabel); } } } public void SetAsFocus() { FocusButton.AddStyleClass(StyleNano.StyleClassButtonColorGreen); ArrowTexture.TexturePath = "/Textures/Interface/Nano/inverted_triangle.svg.png"; } public void RemoveAsFocus() { FocusButton.RemoveStyleClass(StyleNano.StyleClassButtonColorGreen); ArrowTexture.TexturePath = "/Textures/Interface/Nano/triangle_right.png"; FocusContainer.Visible = false; } }