diff --git a/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorBoundUserInterface.cs b/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorBoundUserInterface.cs index ff1eae36f5..93306f2fd1 100644 --- a/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorBoundUserInterface.cs +++ b/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorBoundUserInterface.cs @@ -1,5 +1,4 @@ using Content.Shared.Singularity.Components; -using Robust.Client.GameObjects; using Robust.Client.UserInterface; namespace Content.Client.ParticleAccelerator.UI @@ -18,9 +17,11 @@ namespace Content.Client.ParticleAccelerator.UI base.Open(); _menu = this.CreateWindow(); + _menu.SetEntity(Owner); + _menu.OnOverallState += SendEnableMessage; _menu.OnPowerState += SendPowerStateMessage; - _menu.OnScanPartsRequested += SendScanPartsMessage; + _menu.OnScan += SendScanPartsMessage; } public void SendEnableMessage(bool enable) diff --git a/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorControlMenu.cs b/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorControlMenu.cs deleted file mode 100644 index 05a296edf3..0000000000 --- a/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorControlMenu.cs +++ /dev/null @@ -1,526 +0,0 @@ -using System.Numerics; -using Content.Client.Resources; -using Content.Client.Stylesheets; -using Content.Client.UserInterface.Controls; -using Content.Shared.Singularity.Components; -using Robust.Client.Animations; -using Robust.Client.Graphics; -using Robust.Client.ResourceManagement; -using Robust.Client.UserInterface; -using Robust.Client.UserInterface.Controls; -using Robust.Client.UserInterface.CustomControls; -using Robust.Shared.Noise; -using Robust.Shared.Prototypes; -using Robust.Shared.Timing; -using static Robust.Client.UserInterface.Controls.BoxContainer; - -namespace Content.Client.ParticleAccelerator.UI -{ - public sealed class ParticleAcceleratorControlMenu : BaseWindow - { - [Dependency] private readonly IPrototypeManager _protoManager = default!; - [Dependency] private readonly IResourceCache _cache = default!; - - private readonly ShaderInstance _greyScaleShader; - - private readonly Label _drawLabel; - private readonly FastNoiseLite _drawNoiseGenerator; - private readonly Button _onButton; - private readonly Button _offButton; - private readonly Button _scanButton; - private readonly Label _statusLabel; - private readonly SpinBox _stateSpinBox; - - private readonly BoxContainer _alarmControl; - private readonly Animation _alarmControlAnimation; - - private readonly PASegmentControl _endCapTexture; - private readonly PASegmentControl _fuelChamberTexture; - private readonly PASegmentControl _controlBoxTexture; - private readonly PASegmentControl _powerBoxTexture; - private readonly PASegmentControl _emitterForeTexture; - private readonly PASegmentControl _emitterPortTexture; - private readonly PASegmentControl _emitterStarboardTexture; - - private float _time; - private int _lastDraw; - private int _lastReceive; - - private bool _blockSpinBox; - private bool _assembled; - private bool _shouldContinueAnimating; - private int _maxStrength = 3; - - public event Action? OnOverallState; - public event Action? OnPowerState; - public event Action? OnScanPartsRequested; - - public ParticleAcceleratorControlMenu() - { - IoCManager.InjectDependencies(this); - SetSize = new Vector2(400, 320); - _greyScaleShader = _protoManager.Index("Greyscale").Instance(); - - _drawNoiseGenerator = new(); - _drawNoiseGenerator.SetFractalType(FastNoiseLite.FractalType.FBm); - _drawNoiseGenerator.SetFrequency(0.5f); - - var font = _cache.GetFont("/Fonts/Boxfont-round/Boxfont Round.ttf", 13); - var panelTex = _cache.GetTexture("/Textures/Interface/Nano/button.svg.96dpi.png"); - - MouseFilter = MouseFilterMode.Stop; - - _alarmControlAnimation = new Animation - { - Length = TimeSpan.FromSeconds(1), - AnimationTracks = - { - new AnimationTrackControlProperty - { - Property = nameof(Control.Visible), - KeyFrames = - { - new AnimationTrackProperty.KeyFrame(true, 0), - new AnimationTrackProperty.KeyFrame(false, 0.75f), - } - } - } - }; - - var back = new StyleBoxTexture - { - Texture = panelTex, - Modulate = Color.FromHex("#25252A"), - }; - back.SetPatchMargin(StyleBox.Margin.All, 10); - - var back2 = new StyleBoxTexture(back) - { - Modulate = Color.FromHex("#202023") - }; - - AddChild(new PanelContainer - { - PanelOverride = back, - MouseFilter = MouseFilterMode.Pass - }); - - _stateSpinBox = new SpinBox { Value = 0, IsValid = StrengthSpinBoxValid }; - _stateSpinBox.InitDefaultButtons(); - _stateSpinBox.ValueChanged += PowerStateChanged; - _stateSpinBox.LineEditDisabled = true; - - _offButton = new Button - { - ToggleMode = false, - Text = Loc.GetString("particle-accelerator-control-menu-off-button"), - StyleClasses = { StyleBase.ButtonOpenRight }, - }; - - _offButton.OnPressed += args => OnOverallState?.Invoke(false); - - _onButton = new Button - { - ToggleMode = false, - Text = Loc.GetString("particle-accelerator-control-menu-on-button"), - StyleClasses = { StyleBase.ButtonOpenLeft }, - }; - _onButton.OnPressed += args => OnOverallState?.Invoke(true); - - var closeButton = new TextureButton - { - StyleClasses = { "windowCloseButton" }, - HorizontalAlignment = HAlignment.Right, - Margin = new Thickness(0, 0, 8, 0) - }; - closeButton.OnPressed += args => Close(); - - var serviceManual = new Label - { - HorizontalAlignment = HAlignment.Center, - StyleClasses = { StyleBase.StyleClassLabelSubText }, - Text = Loc.GetString("particle-accelerator-control-menu-service-manual-reference") - }; - _drawLabel = new Label(); - var imgSize = new Vector2(32, 32); - AddChild(new BoxContainer - { - Orientation = LayoutOrientation.Vertical, - Children = - { - new Control - { - Margin = new Thickness(2, 2, 0, 0), - Children = - { - new Label - { - Text = Loc.GetString("particle-accelerator-control-menu-device-version-label"), - FontOverride = font, - FontColorOverride = StyleNano.NanoGold, - }, - closeButton - } - }, - new PanelContainer - { - PanelOverride = new StyleBoxFlat {BackgroundColor = StyleNano.NanoGold}, - MinSize = new Vector2(0, 2), - }, - new Control - { - MinSize = new Vector2(0, 4) - }, - - new BoxContainer - { - Orientation = LayoutOrientation.Horizontal, - VerticalExpand = true, - Children = - { - new BoxContainer - { - Orientation = LayoutOrientation.Vertical, - Margin = new Thickness(4, 0, 0, 0), - HorizontalExpand = true, - Children = - { - new BoxContainer - { - Orientation = LayoutOrientation.Horizontal, - Children = - { - new Label - { - Text = Loc.GetString("particle-accelerator-control-menu-power-label") + " ", - HorizontalExpand = true, - HorizontalAlignment = HAlignment.Left, - }, - _offButton, - _onButton - } - }, - new BoxContainer - { - Orientation = LayoutOrientation.Horizontal, - Children = - { - new Label - { - Text = Loc.GetString("particle-accelerator-control-menu-strength-label") + " ", - HorizontalExpand = true, - HorizontalAlignment = HAlignment.Left, - }, - _stateSpinBox - } - }, - new Control - { - MinSize = new Vector2(0, 10), - }, - _drawLabel, - new Control - { - VerticalExpand = true, - }, - (_alarmControl = new BoxContainer - { - Orientation = LayoutOrientation.Vertical, - Children = - { - new Label - { - Text = Loc.GetString("particle-accelerator-control-menu-alarm-control"), - FontColorOverride = Color.Red, - Align = Label.AlignMode.Center - }, - serviceManual - }, - Visible = false, - }), - } - }, - new BoxContainer - { - Orientation = LayoutOrientation.Vertical, - MinSize = new Vector2(186, 0), - Children = - { - (_statusLabel = new Label - { - HorizontalAlignment = HAlignment.Center - }), - new Control - { - MinSize = new Vector2(0, 20) - }, - new PanelContainer - { - HorizontalAlignment = HAlignment.Center, - PanelOverride = back2, - Children = - { - new GridContainer - { - Columns = 3, - VSeparationOverride = 0, - HSeparationOverride = 0, - Children = - { - new Control {MinSize = imgSize}, - (_endCapTexture = Segment("end_cap")), - new Control {MinSize = imgSize}, - (_controlBoxTexture = Segment("control_box")), - (_fuelChamberTexture = Segment("fuel_chamber")), - new Control {MinSize = imgSize}, - new Control {MinSize = imgSize}, - (_powerBoxTexture = Segment("power_box")), - new Control {MinSize = imgSize}, - (_emitterStarboardTexture = Segment("emitter_starboard")), - (_emitterForeTexture = Segment("emitter_fore")), - (_emitterPortTexture = Segment("emitter_port")), - } - } - } - }, - (_scanButton = new Button - { - Text = Loc.GetString("particle-accelerator-control-menu-scan-parts-button"), - HorizontalAlignment = HAlignment.Center - }) - } - } - } - }, - new StripeBack - { - Children = - { - new Label - { - Margin = new Thickness(4, 4, 0, 4), - Text = Loc.GetString("particle-accelerator-control-menu-check-containment-field-warning"), - HorizontalAlignment = HAlignment.Center, - StyleClasses = {StyleBase.StyleClassLabelSubText}, - } - } - }, - new BoxContainer - { - Orientation = LayoutOrientation.Horizontal, - Margin = new Thickness(12, 0, 0, 0), - Children = - { - new Label - { - Text = Loc.GetString("particle-accelerator-control-menu-foo-bar-baz"), - StyleClasses = {StyleBase.StyleClassLabelSubText} - } - } - }, - } - }); - - _scanButton.OnPressed += args => OnScanPartsRequested?.Invoke(); - - _alarmControl.AnimationCompleted += s => - { - if (_shouldContinueAnimating) - { - _alarmControl.PlayAnimation(_alarmControlAnimation, "warningAnim"); - } - else - { - _alarmControl.Visible = false; - } - }; - - PASegmentControl Segment(string name) - { - return new(this, _cache, name); - } - - UpdateUI(false, false, false, false); - } - - private bool StrengthSpinBoxValid(int n) - { - return n >= 0 && n <= _maxStrength && !_blockSpinBox; - } - - private void PowerStateChanged(ValueChangedEventArgs e) - { - ParticleAcceleratorPowerState newState; - switch (e.Value) - { - case 0: - newState = ParticleAcceleratorPowerState.Standby; - break; - case 1: - newState = ParticleAcceleratorPowerState.Level0; - break; - case 2: - newState = ParticleAcceleratorPowerState.Level1; - break; - case 3: - newState = ParticleAcceleratorPowerState.Level2; - break; - case 4: - newState = ParticleAcceleratorPowerState.Level3; - break; - default: - return; - } - - _stateSpinBox.SetButtonDisabled(true); - OnPowerState?.Invoke(newState); - } - - protected override DragMode GetDragModeFor(Vector2 relativeMousePos) - { - return DragMode.Move; - } - - public void DataUpdate(ParticleAcceleratorUIState uiState) - { - _assembled = uiState.Assembled; - UpdateUI(uiState.Assembled, uiState.InterfaceBlock, uiState.Enabled, - uiState.WirePowerBlock); - _statusLabel.Text = Loc.GetString("particle-accelerator-control-menu-status-label", - ("status", Loc.GetString(uiState.Assembled ? "particle-accelerator-control-menu-status-operational" : - "particle-accelerator-control-menu-status-incomplete"))); - UpdatePowerState(uiState.State, uiState.Enabled, uiState.Assembled, - uiState.MaxLevel); - UpdatePreview(uiState); - _lastDraw = uiState.PowerDraw; - _lastReceive = uiState.PowerReceive; - } - - private void UpdatePowerState(ParticleAcceleratorPowerState state, bool enabled, bool assembled, - ParticleAcceleratorPowerState maxState) - { - _stateSpinBox.OverrideValue(state switch - { - ParticleAcceleratorPowerState.Standby => 0, - ParticleAcceleratorPowerState.Level0 => 1, - ParticleAcceleratorPowerState.Level1 => 2, - ParticleAcceleratorPowerState.Level2 => 3, - ParticleAcceleratorPowerState.Level3 => 4, - _ => 0 - }); - - - _maxStrength = maxState == ParticleAcceleratorPowerState.Level3 ? 4 : 3; - if (_maxStrength > 3 && enabled && assembled) - { - _shouldContinueAnimating = true; - if (!_alarmControl.HasRunningAnimation("warningAnim")) - _alarmControl.PlayAnimation(_alarmControlAnimation, "warningAnim"); - } - else - _shouldContinueAnimating = false; - } - - private void UpdateUI(bool assembled, bool blocked, bool enabled, bool powerBlock) - { - _onButton.Pressed = enabled; - _offButton.Pressed = !enabled; - - var cantUse = !assembled || blocked || powerBlock; - _onButton.Disabled = cantUse; - _offButton.Disabled = cantUse; - _scanButton.Disabled = blocked; - - var cantChangeLevel = !assembled || blocked; - _stateSpinBox.SetButtonDisabled(cantChangeLevel); - _blockSpinBox = cantChangeLevel; - } - - private void UpdatePreview(ParticleAcceleratorUIState updateMessage) - { - _endCapTexture.SetPowerState(updateMessage, updateMessage.EndCapExists); - _controlBoxTexture.SetPowerState(updateMessage, true); - _fuelChamberTexture.SetPowerState(updateMessage, updateMessage.FuelChamberExists); - _powerBoxTexture.SetPowerState(updateMessage, updateMessage.PowerBoxExists); - _emitterStarboardTexture.SetPowerState(updateMessage, updateMessage.EmitterStarboardExists); - _emitterForeTexture.SetPowerState(updateMessage, updateMessage.EmitterForeExists); - _emitterPortTexture.SetPowerState(updateMessage, updateMessage.EmitterPortExists); - } - - protected override void FrameUpdate(FrameEventArgs args) - { - base.FrameUpdate(args); - - if (!_assembled) - { - _drawLabel.Text = Loc.GetString("particle-accelerator-control-menu-draw-not-available"); - return; - } - - _time += args.DeltaSeconds; - - var watts = 0; - if (_lastDraw != 0) - { - var val = _drawNoiseGenerator.GetNoise(_time, 0f); - watts = (int) (_lastDraw + val * 5); - } - - _drawLabel.Text = Loc.GetString("particle-accelerator-control-menu-draw", - ("watts", $"{watts:##,##0}"), - ("lastReceive", $"{_lastReceive:##,##0}")); - } - - private sealed class PASegmentControl : Control - { - private readonly ParticleAcceleratorControlMenu _menu; - private readonly string _baseState; - private readonly TextureRect _base; - private readonly TextureRect _unlit; - private readonly RSI _rsi; - - public PASegmentControl(ParticleAcceleratorControlMenu menu, IResourceCache cache, string name) - { - _menu = menu; - _baseState = name; - _rsi = cache.GetResource($"/Textures/Structures/Power/Generation/PA/{name}.rsi").RSI; - - AddChild(_base = new TextureRect { Texture = _rsi[$"completed"].Frame0 }); - AddChild(_unlit = new TextureRect()); - MinSize = _rsi.Size; - } - - public void SetPowerState(ParticleAcceleratorUIState state, bool exists) - { - _base.ShaderOverride = exists ? null : _menu._greyScaleShader; - _base.ModulateSelfOverride = exists ? null : new Color(127, 127, 127); - - if (!state.Enabled || !exists) - { - _unlit.Visible = false; - return; - } - - _unlit.Visible = true; - - var suffix = state.State switch - { - ParticleAcceleratorPowerState.Standby => "_unlitp", - ParticleAcceleratorPowerState.Level0 => "_unlitp0", - ParticleAcceleratorPowerState.Level1 => "_unlitp1", - ParticleAcceleratorPowerState.Level2 => "_unlitp2", - ParticleAcceleratorPowerState.Level3 => "_unlitp3", - _ => "" - }; - - if (!_rsi.TryGetState(_baseState + suffix, out var rState)) - { - _unlit.Visible = false; - return; - } - - _unlit.Texture = rState.Frame0; - } - } - } -} diff --git a/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorControlMenu.xaml b/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorControlMenu.xaml new file mode 100644 index 0000000000..63f1583706 --- /dev/null +++ b/Content.Client/ParticleAccelerator/UI/ParticleAcceleratorControlMenu.xaml @@ -0,0 +1,74 @@ + + + + + + + + + + + +