Predict dumping (#32394)

* Predict dumping

- This got soaped really fucking hard.
- Dumping is predicted, this required disposals to be predicte.d
- Disposals required mailing (because it's tightly coupled), and a smidge of other content systems.
- I also had to fix a compnetworkgenerator issue at the same time so it wouldn't mispredict.

* Fix a bunch of stuff

* nasty merge

* Some reviews

* Some more reviews while I stash

* Fix merge

* Fix merge

* Half of review

* Review

* re(h)f

* lizards

* feexes

* feex
This commit is contained in:
metalgearsloth
2025-04-19 16:20:40 +10:00
committed by GitHub
parent f1f431e720
commit 63dfd21b14
140 changed files with 1655 additions and 1858 deletions

View File

@@ -0,0 +1,25 @@
using Content.Client.Configurable.UI;
using Content.Shared.Configurable;
namespace Content.Client.Configurable;
public sealed class ConfigurationSystem : SharedConfigurationSystem
{
[Dependency] private readonly SharedUserInterfaceSystem _uiSystem = default!;
public override void Initialize()
{
base.Initialize();
SubscribeLocalEvent<ConfigurationComponent, AfterAutoHandleStateEvent>(OnConfigurationState);
}
private void OnConfigurationState(Entity<ConfigurationComponent> ent, ref AfterAutoHandleStateEvent args)
{
if (_uiSystem.TryGetOpenUi<ConfigurationBoundUserInterface>(ent.Owner,
ConfigurationComponent.ConfigurationUiKey.Key,
out var bui))
{
bui.Refresh(ent);
}
}
}

View File

@@ -1,6 +1,8 @@
using System.Text.RegularExpressions; using System.Numerics;
using Robust.Client.GameObjects; using System.Text.RegularExpressions;
using Content.Shared.Configurable;
using Robust.Client.UserInterface; using Robust.Client.UserInterface;
using Robust.Client.UserInterface.Controls;
using static Content.Shared.Configurable.ConfigurationComponent; using static Content.Shared.Configurable.ConfigurationComponent;
namespace Content.Client.Configurable.UI namespace Content.Client.Configurable.UI
@@ -19,16 +21,53 @@ namespace Content.Client.Configurable.UI
base.Open(); base.Open();
_menu = this.CreateWindow<ConfigurationMenu>(); _menu = this.CreateWindow<ConfigurationMenu>();
_menu.OnConfiguration += SendConfiguration; _menu.OnConfiguration += SendConfiguration;
if (EntMan.TryGetComponent(Owner, out ConfigurationComponent? component))
Refresh((Owner, component));
} }
protected override void UpdateState(BoundUserInterfaceState state) public void Refresh(Entity<ConfigurationComponent> entity)
{ {
base.UpdateState(state); if (_menu == null)
if (state is not ConfigurationBoundUserInterfaceState configurationState)
return; return;
_menu?.Populate(configurationState); _menu.Column.Children.Clear();
_menu.Inputs.Clear();
foreach (var field in entity.Comp.Config)
{
var label = new Label
{
Margin = new Thickness(0, 0, 8, 0),
Name = field.Key,
Text = field.Key + ":",
VerticalAlignment = Control.VAlignment.Center,
HorizontalExpand = true,
SizeFlagsStretchRatio = .2f,
MinSize = new Vector2(60, 0)
};
var input = new LineEdit
{
Name = field.Key + "-input",
Text = field.Value ?? "",
IsValid = _menu.Validate,
HorizontalExpand = true,
SizeFlagsStretchRatio = .8f
};
_menu.Inputs.Add((field.Key, input));
var row = new BoxContainer
{
Orientation = BoxContainer.LayoutOrientation.Horizontal
};
ConfigurationMenu.CopyProperties(_menu.Row, row);
row.AddChild(label);
row.AddChild(input);
_menu.Column.AddChild(row);
}
} }
protected override void ReceiveMessage(BoundUserInterfaceMessage message) protected override void ReceiveMessage(BoundUserInterfaceMessage message)

View File

@@ -1,12 +1,8 @@
using System.Collections.Generic; using System.Numerics;
using System.Numerics;
using System.Text.RegularExpressions; using System.Text.RegularExpressions;
using Robust.Client.UserInterface; using Robust.Client.UserInterface;
using Robust.Client.UserInterface.Controls; using Robust.Client.UserInterface.Controls;
using Robust.Client.UserInterface.CustomControls; using Robust.Client.UserInterface.CustomControls;
using Robust.Shared.Localization;
using Robust.Shared.Maths;
using static Content.Shared.Configurable.ConfigurationComponent;
using static Robust.Client.UserInterface.Controls.BaseButton; using static Robust.Client.UserInterface.Controls.BaseButton;
using static Robust.Client.UserInterface.Controls.BoxContainer; using static Robust.Client.UserInterface.Controls.BoxContainer;
@@ -14,10 +10,10 @@ namespace Content.Client.Configurable.UI
{ {
public sealed class ConfigurationMenu : DefaultWindow public sealed class ConfigurationMenu : DefaultWindow
{ {
private readonly BoxContainer _column; public readonly BoxContainer Column;
private readonly BoxContainer _row; public readonly BoxContainer Row;
private readonly List<(string name, LineEdit input)> _inputs; public readonly List<(string name, LineEdit input)> Inputs;
[ViewVariables] [ViewVariables]
public Regex? Validation { get; internal set; } public Regex? Validation { get; internal set; }
@@ -28,7 +24,7 @@ namespace Content.Client.Configurable.UI
{ {
MinSize = SetSize = new Vector2(300, 250); MinSize = SetSize = new Vector2(300, 250);
_inputs = new List<(string name, LineEdit input)>(); Inputs = new List<(string name, LineEdit input)>();
Title = Loc.GetString("configuration-menu-device-title"); Title = Loc.GetString("configuration-menu-device-title");
@@ -39,14 +35,14 @@ namespace Content.Client.Configurable.UI
HorizontalExpand = true HorizontalExpand = true
}; };
_column = new BoxContainer Column = new BoxContainer
{ {
Orientation = LayoutOrientation.Vertical, Orientation = LayoutOrientation.Vertical,
Margin = new Thickness(8), Margin = new Thickness(8),
SeparationOverride = 16, SeparationOverride = 16,
}; };
_row = new BoxContainer Row = new BoxContainer
{ {
Orientation = LayoutOrientation.Horizontal, Orientation = LayoutOrientation.Horizontal,
SeparationOverride = 16, SeparationOverride = 16,
@@ -69,61 +65,20 @@ namespace Content.Client.Configurable.UI
ModulateSelfOverride = Color.FromHex("#202025") ModulateSelfOverride = Color.FromHex("#202025")
}; };
outerColumn.AddChild(_column); outerColumn.AddChild(Column);
baseContainer.AddChild(outerColumn); baseContainer.AddChild(outerColumn);
baseContainer.AddChild(confirmButton); baseContainer.AddChild(confirmButton);
Contents.AddChild(baseContainer); Contents.AddChild(baseContainer);
} }
public void Populate(ConfigurationBoundUserInterfaceState state)
{
_column.Children.Clear();
_inputs.Clear();
foreach (var field in state.Config)
{
var label = new Label
{
Margin = new Thickness(0, 0, 8, 0),
Name = field.Key,
Text = field.Key + ":",
VerticalAlignment = VAlignment.Center,
HorizontalExpand = true,
SizeFlagsStretchRatio = .2f,
MinSize = new Vector2(60, 0)
};
var input = new LineEdit
{
Name = field.Key + "-input",
Text = field.Value ?? "",
IsValid = Validate,
HorizontalExpand = true,
SizeFlagsStretchRatio = .8f
};
_inputs.Add((field.Key, input));
var row = new BoxContainer
{
Orientation = LayoutOrientation.Horizontal
};
CopyProperties(_row, row);
row.AddChild(label);
row.AddChild(input);
_column.AddChild(row);
}
}
private void OnConfirm(ButtonEventArgs args) private void OnConfirm(ButtonEventArgs args)
{ {
var config = GenerateDictionary(_inputs, "Text"); var config = GenerateDictionary(Inputs, "Text");
OnConfiguration?.Invoke(config); OnConfiguration?.Invoke(config);
Close(); Close();
} }
private bool Validate(string value) public bool Validate(string value)
{ {
return Validation?.IsMatch(value) != false; return Validation?.IsMatch(value) != false;
} }
@@ -140,7 +95,7 @@ namespace Content.Client.Configurable.UI
return dictionary; return dictionary;
} }
private static void CopyProperties<T>(T from, T to) where T : Control public static void CopyProperties<T>(T from, T to) where T : Control
{ {
foreach (var property in from.AllAttachedProperties) foreach (var property in from.AllAttachedProperties)
{ {

View File

@@ -13,7 +13,7 @@ namespace Content.Client.Decals
[Dependency] private readonly IOverlayManager _overlayManager = default!; [Dependency] private readonly IOverlayManager _overlayManager = default!;
[Dependency] private readonly SpriteSystem _sprites = default!; [Dependency] private readonly SpriteSystem _sprites = default!;
private DecalOverlay _overlay = default!; private DecalOverlay? _overlay;
private HashSet<uint> _removedUids = new(); private HashSet<uint> _removedUids = new();
private readonly List<Vector2i> _removedChunks = new(); private readonly List<Vector2i> _removedChunks = new();
@@ -31,6 +31,9 @@ namespace Content.Client.Decals
public void ToggleOverlay() public void ToggleOverlay()
{ {
if (_overlay == null)
return;
if (_overlayManager.HasOverlay<DecalOverlay>()) if (_overlayManager.HasOverlay<DecalOverlay>())
{ {
_overlayManager.RemoveOverlay(_overlay); _overlayManager.RemoveOverlay(_overlay);
@@ -44,6 +47,10 @@ namespace Content.Client.Decals
public override void Shutdown() public override void Shutdown()
{ {
base.Shutdown(); base.Shutdown();
if (_overlay == null)
return;
_overlayManager.RemoveOverlay(_overlay); _overlayManager.RemoveOverlay(_overlay);
} }

View File

@@ -0,0 +1,8 @@
using Content.Shared.DeviceNetwork.Systems;
namespace Content.Client.DeviceNetwork.Systems;
public sealed class DeviceNetworkSystem : SharedDeviceNetworkSystem
{
}

View File

@@ -1,9 +0,0 @@
using Content.Shared.Disposal.Components;
namespace Content.Client.Disposal;
[RegisterComponent]
public sealed partial class DisposalUnitComponent : SharedDisposalUnitComponent
{
}

View File

@@ -0,0 +1,79 @@
using Content.Client.Disposal.Unit;
using Content.Client.Power.EntitySystems;
using Content.Shared.Disposal;
using Content.Shared.Disposal.Components;
using Robust.Client.UserInterface;
using Robust.Client.UserInterface.Controls;
namespace Content.Client.Disposal.Mailing;
public sealed class MailingUnitBoundUserInterface : BoundUserInterface
{
[ViewVariables]
public MailingUnitWindow? MailingUnitWindow;
public MailingUnitBoundUserInterface(EntityUid owner, Enum uiKey) : base(owner, uiKey)
{
}
private void ButtonPressed(DisposalUnitComponent.UiButton button)
{
SendMessage(new DisposalUnitComponent.UiButtonPressedMessage(button));
// If we get client-side power stuff then we can predict the button presses but for now we won't as it stuffs
// the pressure lerp up.
}
private void TargetSelected(ItemList.ItemListSelectedEventArgs args)
{
var item = args.ItemList[args.ItemIndex];
SendMessage(new TargetSelectedMessage(item.Text));
}
protected override void Open()
{
base.Open();
MailingUnitWindow = this.CreateWindow<MailingUnitWindow>();
MailingUnitWindow.OpenCenteredRight();
MailingUnitWindow.Eject.OnPressed += _ => ButtonPressed(DisposalUnitComponent.UiButton.Eject);
MailingUnitWindow.Engage.OnPressed += _ => ButtonPressed(DisposalUnitComponent.UiButton.Engage);
MailingUnitWindow.Power.OnPressed += _ => ButtonPressed(DisposalUnitComponent.UiButton.Power);
MailingUnitWindow.TargetListContainer.OnItemSelected += TargetSelected;
if (EntMan.TryGetComponent(Owner, out MailingUnitComponent? component))
Refresh((Owner, component));
}
public void Refresh(Entity<MailingUnitComponent> entity)
{
if (MailingUnitWindow == null)
return;
// TODO: This should be decoupled from disposals
if (EntMan.TryGetComponent(entity.Owner, out DisposalUnitComponent? disposals))
{
var disposalSystem = EntMan.System<DisposalUnitSystem>();
var disposalState = disposalSystem.GetState(Owner, disposals);
var fullPressure = disposalSystem.EstimatedFullPressure(Owner, disposals);
MailingUnitWindow.UnitState.Text = Loc.GetString($"disposal-unit-state-{disposalState}");
MailingUnitWindow.FullPressure = fullPressure;
MailingUnitWindow.PressureBar.UpdatePressure(fullPressure);
MailingUnitWindow.Power.Pressed = EntMan.System<PowerReceiverSystem>().IsPowered(Owner);
MailingUnitWindow.Engage.Pressed = disposals.Engaged;
}
MailingUnitWindow.Title = Loc.GetString("ui-mailing-unit-window-title", ("tag", entity.Comp.Tag ?? " "));
//UnitTag.Text = state.Tag;
MailingUnitWindow.Target.Text = entity.Comp.Target;
MailingUnitWindow.TargetListContainer.Clear();
foreach (var target in entity.Comp.TargetList)
{
MailingUnitWindow.TargetListContainer.AddItem(target);
}
}
}

View File

@@ -0,0 +1,22 @@
using Content.Shared.Disposal;
using Content.Shared.Disposal.Components;
using Content.Shared.Disposal.Mailing;
namespace Content.Client.Disposal.Mailing;
public sealed class MailingUnitSystem : SharedMailingUnitSystem
{
public override void Initialize()
{
base.Initialize();
SubscribeLocalEvent<MailingUnitComponent, AfterAutoHandleStateEvent>(OnMailingState);
}
private void OnMailingState(Entity<MailingUnitComponent> ent, ref AfterAutoHandleStateEvent args)
{
if (UserInterfaceSystem.TryGetOpenUi<MailingUnitBoundUserInterface>(ent.Owner, MailingUnitUiKey.Key, out var bui))
{
bui.Refresh(ent);
}
}
}

View File

@@ -1,5 +1,6 @@
<DefaultWindow xmlns="https://spacestation14.io" <controls:FancyWindow xmlns="https://spacestation14.io"
xmlns:ui="clr-namespace:Content.Client.Disposal.UI" xmlns:controls="clr-namespace:Content.Client.UserInterface.Controls"
xmlns:disposal="clr-namespace:Content.Client.Disposal"
MinSize="300 400" MinSize="300 400"
SetSize="300 400" SetSize="300 400"
Resizable="False"> Resizable="False">
@@ -7,6 +8,7 @@
<BoxContainer Orientation="Horizontal" SeparationOverride="8"> <BoxContainer Orientation="Horizontal" SeparationOverride="8">
<Label Text="{Loc 'ui-mailing-unit-target-label'}" /> <Label Text="{Loc 'ui-mailing-unit-target-label'}" />
<Label Name="Target" <Label Name="Target"
Access="Public"
Text="" /> Text="" />
</BoxContainer> </BoxContainer>
<ItemList Name="TargetListContainer" <ItemList Name="TargetListContainer"
@@ -18,14 +20,15 @@
</ItemList> </ItemList>
<BoxContainer Orientation="Horizontal" SeparationOverride="4"> <BoxContainer Orientation="Horizontal" SeparationOverride="4">
<Label Text="{Loc 'ui-disposal-unit-label-state'}" /> <Label Text="{Loc 'ui-disposal-unit-label-state'}" />
<Label Name="UnitState" <Label Name="UnitState" Access="Public"
Text="{Loc 'ui-disposal-unit-label-status'}" /> Text="{Loc 'ui-disposal-unit-label-status'}" />
</BoxContainer> </BoxContainer>
<Control MinSize="0 5" /> <Control MinSize="0 5" />
<BoxContainer Orientation="Horizontal" <BoxContainer Orientation="Horizontal"
SeparationOverride="4"> SeparationOverride="4">
<Label Text="{Loc 'ui-disposal-unit-label-pressure'}" /> <Label Text="{Loc 'ui-disposal-unit-label-pressure'}" />
<ui:PressureBar Name="PressureBar" <disposal:PressureBar Name="PressureBar"
Access="Public"
MinSize="190 20" MinSize="190 20"
HorizontalAlignment="Right" HorizontalAlignment="Right"
MinValue="0" MinValue="0"
@@ -50,4 +53,4 @@
StyleClasses="OpenLeft" /> StyleClasses="OpenLeft" />
</BoxContainer> </BoxContainer>
</BoxContainer> </BoxContainer>
</DefaultWindow> </controls:FancyWindow>

View File

@@ -0,0 +1,27 @@
using Content.Client.UserInterface.Controls;
using Robust.Client.AutoGenerated;
using Robust.Client.UserInterface.XAML;
using Robust.Shared.Timing;
namespace Content.Client.Disposal.Mailing
{
/// <summary>
/// Client-side UI used to control a <see cref="Shared.Disposal.Components.MailingUnitComponent"/>
/// </summary>
[GenerateTypedNameReferences]
public sealed partial class MailingUnitWindow : FancyWindow
{
public TimeSpan FullPressure;
public MailingUnitWindow()
{
RobustXamlLoader.Load(this);
}
protected override void FrameUpdate(FrameEventArgs args)
{
base.FrameUpdate(args);
PressureBar.UpdatePressure(FullPressure);
}
}
}

View File

@@ -1,9 +1,10 @@
using Content.Shared.Disposal; using Content.Shared.Disposal;
using Content.Shared.Disposal.Unit;
using Robust.Client.Graphics; using Robust.Client.Graphics;
using Robust.Client.UserInterface.Controls; using Robust.Client.UserInterface.Controls;
using Robust.Shared.Timing; using Robust.Shared.Timing;
namespace Content.Client.Disposal.UI; namespace Content.Client.Disposal;
public sealed class PressureBar : ProgressBar public sealed class PressureBar : ProgressBar
{ {

View File

@@ -1,187 +0,0 @@
using System.Diagnostics.CodeAnalysis;
using Content.Shared.Disposal;
using Content.Shared.Disposal.Components;
using Content.Shared.DragDrop;
using Content.Shared.Emag.Systems;
using Robust.Client.GameObjects;
using Robust.Client.Animations;
using Robust.Client.Graphics;
using Robust.Shared.Audio;
using Robust.Shared.Audio.Systems;
using Robust.Shared.GameStates;
using Robust.Shared.Physics.Events;
using static Content.Shared.Disposal.Components.SharedDisposalUnitComponent;
namespace Content.Client.Disposal.Systems;
public sealed class DisposalUnitSystem : SharedDisposalUnitSystem
{
[Dependency] private readonly AppearanceSystem _appearanceSystem = default!;
[Dependency] private readonly AnimationPlayerSystem _animationSystem = default!;
[Dependency] private readonly SharedAudioSystem _audioSystem = default!;
private const string AnimationKey = "disposal_unit_animation";
private const string DefaultFlushState = "disposal-flush";
private const string DefaultChargeState = "disposal-charging";
public override void Initialize()
{
base.Initialize();
SubscribeLocalEvent<DisposalUnitComponent, ComponentHandleState>(OnHandleState);
SubscribeLocalEvent<DisposalUnitComponent, PreventCollideEvent>(OnPreventCollide);
SubscribeLocalEvent<DisposalUnitComponent, CanDropTargetEvent>(OnCanDragDropOn);
SubscribeLocalEvent<DisposalUnitComponent, GotEmaggedEvent>(OnEmagged);
SubscribeLocalEvent<DisposalUnitComponent, ComponentInit>(OnComponentInit);
SubscribeLocalEvent<DisposalUnitComponent, AppearanceChangeEvent>(OnAppearanceChange);
}
private void OnHandleState(EntityUid uid, DisposalUnitComponent component, ref ComponentHandleState args)
{
if (args.Current is not DisposalUnitComponentState state)
return;
component.FlushSound = state.FlushSound;
component.State = state.State;
component.NextPressurized = state.NextPressurized;
component.AutomaticEngageTime = state.AutomaticEngageTime;
component.NextFlush = state.NextFlush;
component.Powered = state.Powered;
component.Engaged = state.Engaged;
component.RecentlyEjected.Clear();
component.RecentlyEjected.AddRange(EnsureEntityList<DisposalUnitComponent>(state.RecentlyEjected, uid));
}
public override bool HasDisposals(EntityUid? uid)
{
return HasComp<DisposalUnitComponent>(uid);
}
public override bool ResolveDisposals(EntityUid uid, [NotNullWhen(true)] ref SharedDisposalUnitComponent? component)
{
if (component != null)
return true;
TryComp<DisposalUnitComponent>(uid, out var storage);
component = storage;
return component != null;
}
public override void DoInsertDisposalUnit(EntityUid uid, EntityUid toInsert, EntityUid user, SharedDisposalUnitComponent? disposal = null)
{
return;
}
private void OnComponentInit(EntityUid uid, SharedDisposalUnitComponent sharedDisposalUnit, ComponentInit args)
{
if (!TryComp<SpriteComponent>(uid, out var sprite) || !TryComp<AppearanceComponent>(uid, out var appearance))
return;
UpdateState(uid, sharedDisposalUnit, sprite, appearance);
}
private void OnAppearanceChange(EntityUid uid, SharedDisposalUnitComponent unit, ref AppearanceChangeEvent args)
{
if (args.Sprite == null)
return;
UpdateState(uid, unit, args.Sprite, args.Component);
}
/// <summary>
/// Update visuals and tick animation
/// </summary>
private void UpdateState(EntityUid uid, SharedDisposalUnitComponent unit, SpriteComponent sprite, AppearanceComponent appearance)
{
if (!_appearanceSystem.TryGetData<VisualState>(uid, Visuals.VisualState, out var state, appearance))
return;
sprite.LayerSetVisible(DisposalUnitVisualLayers.Unanchored, state == VisualState.UnAnchored);
sprite.LayerSetVisible(DisposalUnitVisualLayers.Base, state == VisualState.Anchored);
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayFlush, state is VisualState.OverlayFlushing or VisualState.OverlayCharging);
var chargingState = sprite.LayerMapTryGet(DisposalUnitVisualLayers.BaseCharging, out var chargingLayer)
? sprite.LayerGetState(chargingLayer)
: new RSI.StateId(DefaultChargeState);
// This is a transient state so not too worried about replaying in range.
if (state == VisualState.OverlayFlushing)
{
if (!_animationSystem.HasRunningAnimation(uid, AnimationKey))
{
var flushState = sprite.LayerMapTryGet(DisposalUnitVisualLayers.OverlayFlush, out var flushLayer)
? sprite.LayerGetState(flushLayer)
: new RSI.StateId(DefaultFlushState);
// Setup the flush animation to play
var anim = new Animation
{
Length = unit.FlushDelay,
AnimationTracks =
{
new AnimationTrackSpriteFlick
{
LayerKey = DisposalUnitVisualLayers.OverlayFlush,
KeyFrames =
{
// Play the flush animation
new AnimationTrackSpriteFlick.KeyFrame(flushState, 0),
// Return to base state (though, depending on how the unit is
// configured we might get an appearance change event telling
// us to go to charging state)
new AnimationTrackSpriteFlick.KeyFrame(chargingState, (float) unit.FlushDelay.TotalSeconds)
}
},
}
};
if (unit.FlushSound != null)
{
anim.AnimationTracks.Add(
new AnimationTrackPlaySound
{
KeyFrames =
{
new AnimationTrackPlaySound.KeyFrame(_audioSystem.ResolveSound(unit.FlushSound), 0)
}
});
}
_animationSystem.Play(uid, anim, AnimationKey);
}
}
else if (state == VisualState.OverlayCharging)
sprite.LayerSetState(DisposalUnitVisualLayers.OverlayFlush, chargingState);
else
_animationSystem.Stop(uid, AnimationKey);
if (!_appearanceSystem.TryGetData<HandleState>(uid, Visuals.Handle, out var handleState, appearance))
handleState = HandleState.Normal;
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayEngaged, handleState != HandleState.Normal);
if (!_appearanceSystem.TryGetData<LightStates>(uid, Visuals.Light, out var lightState, appearance))
lightState = LightStates.Off;
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayCharging,
(lightState & LightStates.Charging) != 0);
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayReady,
(lightState & LightStates.Ready) != 0);
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayFull,
(lightState & LightStates.Full) != 0);
}
}
public enum DisposalUnitVisualLayers : byte
{
Unanchored,
Base,
BaseCharging,
OverlayFlush,
OverlayCharging,
OverlayReady,
OverlayFull,
OverlayEngaged
}

View File

@@ -1,9 +1,8 @@
using JetBrains.Annotations; using JetBrains.Annotations;
using Robust.Client.GameObjects;
using Robust.Client.UserInterface; using Robust.Client.UserInterface;
using static Content.Shared.Disposal.Components.SharedDisposalRouterComponent; using static Content.Shared.Disposal.Components.SharedDisposalRouterComponent;
namespace Content.Client.Disposal.UI namespace Content.Client.Disposal.Tube
{ {
/// <summary> /// <summary>
/// Initializes a <see cref="DisposalRouterWindow"/> and updates it when new server messages are received. /// Initializes a <see cref="DisposalRouterWindow"/> and updates it when new server messages are received.

View File

@@ -1,11 +1,10 @@
using Content.Shared.Disposal.Components; using Content.Shared.Disposal.Components;
using Robust.Client.AutoGenerated; using Robust.Client.AutoGenerated;
using Robust.Client.UserInterface.Controls;
using Robust.Client.UserInterface.CustomControls; using Robust.Client.UserInterface.CustomControls;
using Robust.Client.UserInterface.XAML; using Robust.Client.UserInterface.XAML;
using static Content.Shared.Disposal.Components.SharedDisposalRouterComponent; using static Content.Shared.Disposal.Components.SharedDisposalRouterComponent;
namespace Content.Client.Disposal.UI namespace Content.Client.Disposal.Tube
{ {
/// <summary> /// <summary>
/// Client-side UI used to control a <see cref="SharedDisposalRouterComponent"/> /// Client-side UI used to control a <see cref="SharedDisposalRouterComponent"/>

View File

@@ -1,9 +1,8 @@
using JetBrains.Annotations; using JetBrains.Annotations;
using Robust.Client.GameObjects;
using Robust.Client.UserInterface; using Robust.Client.UserInterface;
using static Content.Shared.Disposal.Components.SharedDisposalTaggerComponent; using static Content.Shared.Disposal.Components.SharedDisposalTaggerComponent;
namespace Content.Client.Disposal.UI namespace Content.Client.Disposal.Tube
{ {
/// <summary> /// <summary>
/// Initializes a <see cref="DisposalTaggerWindow"/> and updates it when new server messages are received. /// Initializes a <see cref="DisposalTaggerWindow"/> and updates it when new server messages are received.

View File

@@ -1,11 +1,10 @@
using Content.Shared.Disposal.Components; using Content.Shared.Disposal.Components;
using Robust.Client.AutoGenerated; using Robust.Client.AutoGenerated;
using Robust.Client.UserInterface.Controls;
using Robust.Client.UserInterface.CustomControls; using Robust.Client.UserInterface.CustomControls;
using Robust.Client.UserInterface.XAML; using Robust.Client.UserInterface.XAML;
using static Content.Shared.Disposal.Components.SharedDisposalTaggerComponent; using static Content.Shared.Disposal.Components.SharedDisposalTaggerComponent;
namespace Content.Client.Disposal.UI namespace Content.Client.Disposal.Tube
{ {
/// <summary> /// <summary>
/// Client-side UI used to control a <see cref="SharedDisposalTaggerComponent"/> /// Client-side UI used to control a <see cref="SharedDisposalTaggerComponent"/>

View File

@@ -0,0 +1,8 @@
using Content.Shared.Disposal.Unit;
namespace Content.Client.Disposal.Tube;
public sealed class DisposalTubeSystem : SharedDisposalTubeSystem
{
}

View File

@@ -1,103 +0,0 @@
using Content.Client.Disposal.Systems;
using Content.Shared.Disposal;
using Content.Shared.Disposal.Components;
using JetBrains.Annotations;
using Robust.Client.GameObjects;
using Robust.Client.UserInterface.Controls;
using static Content.Shared.Disposal.Components.SharedDisposalUnitComponent;
namespace Content.Client.Disposal.UI
{
/// <summary>
/// Initializes a <see cref="MailingUnitWindow"/> or a <see cref="DisposalUnitWindow"/> and updates it when new server messages are received.
/// </summary>
[UsedImplicitly]
public sealed class DisposalUnitBoundUserInterface : BoundUserInterface
{
// What are you doing here
[ViewVariables]
public MailingUnitWindow? MailingUnitWindow;
[ViewVariables]
public DisposalUnitWindow? DisposalUnitWindow;
public DisposalUnitBoundUserInterface(EntityUid owner, Enum uiKey) : base(owner, uiKey)
{
}
private void ButtonPressed(UiButton button)
{
SendMessage(new UiButtonPressedMessage(button));
// If we get client-side power stuff then we can predict the button presses but for now we won't as it stuffs
// the pressure lerp up.
}
private void TargetSelected(ItemList.ItemListSelectedEventArgs args)
{
var item = args.ItemList[args.ItemIndex];
SendMessage(new TargetSelectedMessage(item.Text));
}
protected override void Open()
{
base.Open();
if (UiKey is MailingUnitUiKey)
{
MailingUnitWindow = new MailingUnitWindow();
MailingUnitWindow.OpenCenteredRight();
MailingUnitWindow.OnClose += Close;
MailingUnitWindow.Eject.OnPressed += _ => ButtonPressed(UiButton.Eject);
MailingUnitWindow.Engage.OnPressed += _ => ButtonPressed(UiButton.Engage);
MailingUnitWindow.Power.OnPressed += _ => ButtonPressed(UiButton.Power);
MailingUnitWindow.TargetListContainer.OnItemSelected += TargetSelected;
}
else if (UiKey is DisposalUnitUiKey)
{
DisposalUnitWindow = new DisposalUnitWindow();
DisposalUnitWindow.OpenCenteredRight();
DisposalUnitWindow.OnClose += Close;
DisposalUnitWindow.Eject.OnPressed += _ => ButtonPressed(UiButton.Eject);
DisposalUnitWindow.Engage.OnPressed += _ => ButtonPressed(UiButton.Engage);
DisposalUnitWindow.Power.OnPressed += _ => ButtonPressed(UiButton.Power);
}
}
protected override void UpdateState(BoundUserInterfaceState state)
{
base.UpdateState(state);
if (state is not MailingUnitBoundUserInterfaceState && state is not DisposalUnitBoundUserInterfaceState)
{
return;
}
switch (state)
{
case MailingUnitBoundUserInterfaceState mailingUnitState:
MailingUnitWindow?.UpdateState(mailingUnitState);
break;
case DisposalUnitBoundUserInterfaceState disposalUnitState:
DisposalUnitWindow?.UpdateState(disposalUnitState);
break;
}
}
protected override void Dispose(bool disposing)
{
base.Dispose(disposing);
if (!disposing)
return;
MailingUnitWindow?.Dispose();
DisposalUnitWindow?.Dispose();
}
}
}

View File

@@ -1,43 +0,0 @@
using Content.Shared.Disposal.Components;
using Robust.Client.AutoGenerated;
using Robust.Client.UserInterface.CustomControls;
using Robust.Client.UserInterface.XAML;
using Robust.Shared.Timing;
using static Content.Shared.Disposal.Components.SharedDisposalUnitComponent;
namespace Content.Client.Disposal.UI
{
/// <summary>
/// Client-side UI used to control a <see cref="SharedDisposalUnitComponent"/>
/// </summary>
[GenerateTypedNameReferences]
public sealed partial class DisposalUnitWindow : DefaultWindow
{
public TimeSpan FullPressure;
public DisposalUnitWindow()
{
IoCManager.InjectDependencies(this);
RobustXamlLoader.Load(this);
}
/// <summary>
/// Update the interface state for the disposals window.
/// </summary>
/// <returns>true if we should stop updating every frame.</returns>
public void UpdateState(DisposalUnitBoundUserInterfaceState state)
{
Title = state.UnitName;
UnitState.Text = state.UnitState;
Power.Pressed = state.Powered;
Engage.Pressed = state.Engaged;
FullPressure = state.FullPressureTime;
}
protected override void FrameUpdate(FrameEventArgs args)
{
base.FrameUpdate(args);
PressureBar.UpdatePressure(FullPressure);
}
}
}

View File

@@ -1,55 +0,0 @@
using Content.Shared.Disposal;
using Robust.Client.AutoGenerated;
using Robust.Client.UserInterface.CustomControls;
using Robust.Client.UserInterface.XAML;
using Robust.Shared.Timing;
namespace Content.Client.Disposal.UI
{
/// <summary>
/// Client-side UI used to control a <see cref="MailingUnitComponent"/>
/// </summary>
[GenerateTypedNameReferences]
public sealed partial class MailingUnitWindow : DefaultWindow
{
public TimeSpan FullPressure;
public MailingUnitWindow()
{
RobustXamlLoader.Load(this);
}
/// <summary>
/// Update the interface state for the disposals window.
/// </summary>
/// <returns>true if we should stop updating every frame.</returns>
public bool UpdateState(MailingUnitBoundUserInterfaceState state)
{
var disposalState = state.DisposalState;
Title = Loc.GetString("ui-mailing-unit-window-title", ("tag", state.Tag ?? " "));
UnitState.Text = disposalState.UnitState;
FullPressure = disposalState.FullPressureTime;
var pressureReached = PressureBar.UpdatePressure(disposalState.FullPressureTime);
Power.Pressed = disposalState.Powered;
Engage.Pressed = disposalState.Engaged;
//UnitTag.Text = state.Tag;
Target.Text = state.Target;
TargetListContainer.Clear();
foreach (var target in state.TargetList)
{
TargetListContainer.AddItem(target);
}
return !disposalState.Powered || pressureReached;
}
protected override void FrameUpdate(FrameEventArgs args)
{
base.FrameUpdate(args);
PressureBar.UpdatePressure(FullPressure);
}
}
}

View File

@@ -0,0 +1,63 @@
using Content.Client.Disposal.Mailing;
using Content.Client.Power.EntitySystems;
using Content.Shared.Disposal.Components;
using JetBrains.Annotations;
using Robust.Client.UserInterface;
namespace Content.Client.Disposal.Unit
{
/// <summary>
/// Initializes a <see cref="MailingUnitWindow"/> or a <see cref="_disposalUnitWindow"/> and updates it when new server messages are received.
/// </summary>
[UsedImplicitly]
public sealed class DisposalUnitBoundUserInterface : BoundUserInterface
{
[ViewVariables] private DisposalUnitWindow? _disposalUnitWindow;
public DisposalUnitBoundUserInterface(EntityUid owner, Enum uiKey) : base(owner, uiKey)
{
}
private void ButtonPressed(DisposalUnitComponent.UiButton button)
{
SendPredictedMessage(new DisposalUnitComponent.UiButtonPressedMessage(button));
// If we get client-side power stuff then we can predict the button presses but for now we won't as it stuffs
// the pressure lerp up.
}
protected override void Open()
{
base.Open();
_disposalUnitWindow = this.CreateWindow<DisposalUnitWindow>();
_disposalUnitWindow.OpenCenteredRight();
_disposalUnitWindow.Eject.OnPressed += _ => ButtonPressed(DisposalUnitComponent.UiButton.Eject);
_disposalUnitWindow.Engage.OnPressed += _ => ButtonPressed(DisposalUnitComponent.UiButton.Engage);
_disposalUnitWindow.Power.OnPressed += _ => ButtonPressed(DisposalUnitComponent.UiButton.Power);
if (EntMan.TryGetComponent(Owner, out DisposalUnitComponent? component))
{
Refresh((Owner, component));
}
}
public void Refresh(Entity<DisposalUnitComponent> entity)
{
if (_disposalUnitWindow == null)
return;
var disposalSystem = EntMan.System<DisposalUnitSystem>();
_disposalUnitWindow.Title = EntMan.GetComponent<MetaDataComponent>(entity.Owner).EntityName;
var state = disposalSystem.GetState(entity.Owner, entity.Comp);
_disposalUnitWindow.UnitState.Text = Loc.GetString($"disposal-unit-state-{state}");
_disposalUnitWindow.Power.Pressed = EntMan.System<PowerReceiverSystem>().IsPowered(Owner);
_disposalUnitWindow.Engage.Pressed = entity.Comp.Engaged;
_disposalUnitWindow.FullPressure = disposalSystem.EstimatedFullPressure(entity.Owner, entity.Comp);
}
}
}

View File

@@ -0,0 +1,156 @@
using Content.Shared.Disposal.Components;
using Content.Shared.Disposal.Unit;
using Robust.Client.Animations;
using Robust.Client.GameObjects;
using Robust.Client.Graphics;
using Robust.Shared.Audio.Systems;
namespace Content.Client.Disposal.Unit;
public sealed class DisposalUnitSystem : SharedDisposalUnitSystem
{
[Dependency] private readonly AppearanceSystem _appearanceSystem = default!;
[Dependency] private readonly AnimationPlayerSystem _animationSystem = default!;
[Dependency] private readonly SharedAudioSystem _audioSystem = default!;
[Dependency] private readonly SharedUserInterfaceSystem _uiSystem = default!;
private const string AnimationKey = "disposal_unit_animation";
private const string DefaultFlushState = "disposal-flush";
private const string DefaultChargeState = "disposal-charging";
public override void Initialize()
{
base.Initialize();
SubscribeLocalEvent<DisposalUnitComponent, AfterAutoHandleStateEvent>(OnHandleState);
SubscribeLocalEvent<DisposalUnitComponent, AppearanceChangeEvent>(OnAppearanceChange);
}
private void OnHandleState(EntityUid uid, DisposalUnitComponent component, ref AfterAutoHandleStateEvent args)
{
UpdateUI((uid, component));
}
protected override void UpdateUI(Entity<DisposalUnitComponent> entity)
{
if (_uiSystem.TryGetOpenUi<DisposalUnitBoundUserInterface>(entity.Owner, DisposalUnitComponent.DisposalUnitUiKey.Key, out var bui))
{
bui.Refresh(entity);
}
}
protected override void OnDisposalInit(Entity<DisposalUnitComponent> ent, ref ComponentInit args)
{
base.OnDisposalInit(ent, ref args);
if (!TryComp<SpriteComponent>(ent, out var sprite) || !TryComp<AppearanceComponent>(ent, out var appearance))
return;
UpdateState(ent, sprite, appearance);
}
private void OnAppearanceChange(Entity<DisposalUnitComponent> ent, ref AppearanceChangeEvent args)
{
if (args.Sprite == null)
return;
UpdateState(ent, args.Sprite, args.Component);
}
/// <summary>
/// Update visuals and tick animation
/// </summary>
private void UpdateState(Entity<DisposalUnitComponent> ent, SpriteComponent sprite, AppearanceComponent appearance)
{
if (!_appearanceSystem.TryGetData<DisposalUnitComponent.VisualState>(ent, DisposalUnitComponent.Visuals.VisualState, out var state, appearance))
return;
sprite.LayerSetVisible(DisposalUnitVisualLayers.Unanchored, state == DisposalUnitComponent.VisualState.UnAnchored);
sprite.LayerSetVisible(DisposalUnitVisualLayers.Base, state == DisposalUnitComponent.VisualState.Anchored);
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayFlush, state is DisposalUnitComponent.VisualState.OverlayFlushing or DisposalUnitComponent.VisualState.OverlayCharging);
var chargingState = sprite.LayerMapTryGet(DisposalUnitVisualLayers.BaseCharging, out var chargingLayer)
? sprite.LayerGetState(chargingLayer)
: new RSI.StateId(DefaultChargeState);
// This is a transient state so not too worried about replaying in range.
if (state == DisposalUnitComponent.VisualState.OverlayFlushing)
{
if (!_animationSystem.HasRunningAnimation(ent, AnimationKey))
{
var flushState = sprite.LayerMapTryGet(DisposalUnitVisualLayers.OverlayFlush, out var flushLayer)
? sprite.LayerGetState(flushLayer)
: new RSI.StateId(DefaultFlushState);
// Setup the flush animation to play
var anim = new Animation
{
Length = ent.Comp.FlushDelay,
AnimationTracks =
{
new AnimationTrackSpriteFlick
{
LayerKey = DisposalUnitVisualLayers.OverlayFlush,
KeyFrames =
{
// Play the flush animation
new AnimationTrackSpriteFlick.KeyFrame(flushState, 0),
// Return to base state (though, depending on how the unit is
// configured we might get an appearance change event telling
// us to go to charging state)
new AnimationTrackSpriteFlick.KeyFrame(chargingState, (float) ent.Comp.FlushDelay.TotalSeconds)
}
},
}
};
if (ent.Comp.FlushSound != null)
{
anim.AnimationTracks.Add(
new AnimationTrackPlaySound
{
KeyFrames =
{
new AnimationTrackPlaySound.KeyFrame(_audioSystem.ResolveSound(ent.Comp.FlushSound), 0)
}
});
}
_animationSystem.Play(ent, anim, AnimationKey);
}
}
else if (state == DisposalUnitComponent.VisualState.OverlayCharging)
sprite.LayerSetState(DisposalUnitVisualLayers.OverlayFlush, chargingState);
else
_animationSystem.Stop(ent.Owner, AnimationKey);
if (!_appearanceSystem.TryGetData<DisposalUnitComponent.HandleState>(ent, DisposalUnitComponent.Visuals.Handle, out var handleState, appearance))
handleState = DisposalUnitComponent.HandleState.Normal;
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayEngaged, handleState != DisposalUnitComponent.HandleState.Normal);
if (!_appearanceSystem.TryGetData<DisposalUnitComponent.LightStates>(ent, DisposalUnitComponent.Visuals.Light, out var lightState, appearance))
lightState = DisposalUnitComponent.LightStates.Off;
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayCharging,
(lightState & DisposalUnitComponent.LightStates.Charging) != 0);
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayReady,
(lightState & DisposalUnitComponent.LightStates.Ready) != 0);
sprite.LayerSetVisible(DisposalUnitVisualLayers.OverlayFull,
(lightState & DisposalUnitComponent.LightStates.Full) != 0);
}
}
public enum DisposalUnitVisualLayers : byte
{
Unanchored,
Base,
BaseCharging,
OverlayFlush,
OverlayCharging,
OverlayReady,
OverlayFull,
OverlayEngaged
}

View File

@@ -1,20 +1,21 @@
<DefaultWindow xmlns="https://spacestation14.io" <controls:FancyWindow xmlns="https://spacestation14.io"
xmlns:ui="clr-namespace:Content.Client.Disposal.UI" xmlns:controls="clr-namespace:Content.Client.UserInterface.Controls"
xmlns:disposal="clr-namespace:Content.Client.Disposal"
MinSize="300 140" MinSize="300 140"
SetSize="300 140" SetSize="300 160"
Resizable="False"> Resizable="False">
<BoxContainer Orientation="Vertical"> <BoxContainer Orientation="Vertical" Margin="10">
<BoxContainer Orientation="Horizontal" <BoxContainer Orientation="Horizontal"
SeparationOverride="4"> SeparationOverride="4">
<Label Text="{Loc 'ui-disposal-unit-label-state'}" /> <Label Text="{Loc 'ui-disposal-unit-label-state'}" />
<Label Name="UnitState" <Label Name="UnitState" Access="Public"
Text="{Loc 'ui-disposal-unit-label-status'}" /> Text="{Loc 'ui-disposal-unit-label-status'}" />
</BoxContainer> </BoxContainer>
<Control MinSize="0 5" /> <Control MinSize="0 5" />
<BoxContainer Orientation="Horizontal" <BoxContainer Orientation="Horizontal"
SeparationOverride="4"> SeparationOverride="4">
<Label Text="{Loc 'ui-disposal-unit-label-pressure'}" /> <Label Text="{Loc 'ui-disposal-unit-label-pressure'}" />
<ui:PressureBar Name="PressureBar" <disposal:PressureBar Name="PressureBar"
MinSize="190 20" MinSize="190 20"
HorizontalAlignment="Right" HorizontalAlignment="Right"
MinValue="0" MinValue="0"
@@ -23,7 +24,7 @@
Value="0.5" /> Value="0.5" />
</BoxContainer> </BoxContainer>
<Control MinSize="0 10" /> <Control MinSize="0 10" />
<BoxContainer Orientation="Horizontal"> <BoxContainer Orientation="Horizontal" HorizontalExpand="True">
<Button Name="Engage" <Button Name="Engage"
Access="Public" Access="Public"
Text="{Loc 'ui-disposal-unit-button-flush'}" Text="{Loc 'ui-disposal-unit-button-flush'}"
@@ -39,4 +40,4 @@
StyleClasses="OpenLeft" /> StyleClasses="OpenLeft" />
</BoxContainer> </BoxContainer>
</BoxContainer> </BoxContainer>
</DefaultWindow> </controls:FancyWindow>

View File

@@ -0,0 +1,28 @@
using Content.Client.UserInterface.Controls;
using Robust.Client.AutoGenerated;
using Robust.Client.UserInterface.XAML;
using Robust.Shared.Timing;
namespace Content.Client.Disposal.Unit
{
/// <summary>
/// Client-side UI used to control a <see cref="Shared.Disposal.Components.DisposalUnitComponent"/>
/// </summary>
[GenerateTypedNameReferences]
public sealed partial class DisposalUnitWindow : FancyWindow
{
public TimeSpan FullPressure;
public DisposalUnitWindow()
{
IoCManager.InjectDependencies(this);
RobustXamlLoader.Load(this);
}
protected override void FrameUpdate(FrameEventArgs args)
{
base.FrameUpdate(args);
PressureBar.UpdatePressure(FullPressure);
}
}
}

View File

@@ -1,4 +1,3 @@
using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Systems; using Content.Shared.DeviceNetwork.Systems;
namespace Content.Client.NetworkConfigurator.Systems; namespace Content.Client.NetworkConfigurator.Systems;

View File

@@ -3,6 +3,7 @@ using Content.Client.Power.Components;
using Content.Shared.Power.Components; using Content.Shared.Power.Components;
using Content.Shared.Power.EntitySystems; using Content.Shared.Power.EntitySystems;
using Content.Shared.Examine; using Content.Shared.Examine;
using Content.Shared.Power;
using Robust.Shared.GameStates; using Robust.Shared.GameStates;
namespace Content.Client.Power.EntitySystems; namespace Content.Client.Power.EntitySystems;
@@ -26,9 +27,20 @@ public sealed class PowerReceiverSystem : SharedPowerReceiverSystem
if (args.Current is not ApcPowerReceiverComponentState state) if (args.Current is not ApcPowerReceiverComponentState state)
return; return;
var powerChanged = component.Powered != state.Powered;
component.Powered = state.Powered; component.Powered = state.Powered;
component.NeedsPower = state.NeedsPower; component.NeedsPower = state.NeedsPower;
component.PowerDisabled = state.PowerDisabled; component.PowerDisabled = state.PowerDisabled;
// SO client systems can handle it. The main reason for this is we can't guarantee compstate ordering.
if (powerChanged)
RaisePower((uid, component));
}
protected override void RaisePower(Entity<SharedApcPowerReceiverComponent> entity)
{
var ev = new PowerChangedEvent(entity.Comp.Powered, 0f);
RaiseLocalEvent(entity.Owner, ref ev);
} }
public override bool ResolveApc(EntityUid entity, [NotNullWhen(true)] ref SharedApcPowerReceiverComponent? component) public override bool ResolveApc(EntityUid entity, [NotNullWhen(true)] ref SharedApcPowerReceiverComponent? component)

View File

@@ -11,9 +11,6 @@ public sealed class StorageFillVisualizerSystem : VisualizerSystem<StorageFillVi
if (args.Sprite == null) if (args.Sprite == null)
return; return;
if (!TryComp(uid, out SpriteComponent? sprite))
return;
if (!AppearanceSystem.TryGetData<int>(uid, StorageFillVisuals.FillLevel, out var level, args.Component)) if (!AppearanceSystem.TryGetData<int>(uid, StorageFillVisuals.FillLevel, out var level, args.Component))
return; return;

View File

@@ -1,12 +1,10 @@
using System.Numerics; using System.Numerics;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components; using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Robust.Shared.GameObjects; using Robust.Shared.GameObjects;
using Robust.Shared.IoC;
using Robust.Shared.Map; using Robust.Shared.Map;
using Robust.Shared.Map.Components; using Content.Shared.DeviceNetwork.Components;
namespace Content.IntegrationTests.Tests.DeviceNetwork namespace Content.IntegrationTests.Tests.DeviceNetwork
{ {

View File

@@ -1,14 +1,14 @@
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Robust.Shared.GameObjects; using Robust.Shared.GameObjects;
using Robust.Shared.Reflection; using Robust.Shared.Reflection;
using Content.Shared.DeviceNetwork.Components;
namespace Content.IntegrationTests.Tests.DeviceNetwork namespace Content.IntegrationTests.Tests.DeviceNetwork;
[Reflect(false)]
public sealed class DeviceNetworkTestSystem : EntitySystem
{ {
[Reflect(false)]
public sealed class DeviceNetworkTestSystem : EntitySystem
{
public NetworkPayload LastPayload = default; public NetworkPayload LastPayload = default;
public override void Initialize() public override void Initialize()
@@ -27,5 +27,4 @@ namespace Content.IntegrationTests.Tests.DeviceNetwork
{ {
LastPayload = args.Data; LastPayload = args.Data;
} }
}
} }

View File

@@ -1,13 +1,12 @@
#nullable enable annotations #nullable enable annotations
using System.Linq; using System.Linq;
using System.Numerics; using System.Numerics;
using Content.Server.Disposal.Tube.Components; using Content.Server.Disposal.Unit;
using Content.Server.Disposal.Unit.Components;
using Content.Server.Disposal.Unit.EntitySystems;
using Content.Server.Power.Components; using Content.Server.Power.Components;
using Content.Shared.Disposal; using Content.Server.Power.EntitySystems;
using Content.Shared.Disposal.Components; using Content.Shared.Disposal.Components;
using NUnit.Framework; using Content.Shared.Disposal.Tube;
using Content.Shared.Disposal.Unit;
using Robust.Shared.GameObjects; using Robust.Shared.GameObjects;
using Robust.Shared.Reflection; using Robust.Shared.Reflection;
@@ -30,7 +29,6 @@ namespace Content.IntegrationTests.Tests.Disposal
{ {
var (_, toInsert, unit) = ev; var (_, toInsert, unit) = ev;
var insertTransform = EntityManager.GetComponent<TransformComponent>(toInsert); var insertTransform = EntityManager.GetComponent<TransformComponent>(toInsert);
var unitTransform = EntityManager.GetComponent<TransformComponent>(unit);
// Not in a tube yet // Not in a tube yet
Assert.That(insertTransform.ParentUid, Is.EqualTo(unit)); Assert.That(insertTransform.ParentUid, Is.EqualTo(unit));
}, after: new[] { typeof(SharedDisposalUnitSystem) }); }, after: new[] { typeof(SharedDisposalUnitSystem) });
@@ -163,6 +161,8 @@ namespace Content.IntegrationTests.Tests.Disposal
var entityManager = server.ResolveDependency<IEntityManager>(); var entityManager = server.ResolveDependency<IEntityManager>();
var xformSystem = entityManager.System<SharedTransformSystem>(); var xformSystem = entityManager.System<SharedTransformSystem>();
var disposalSystem = entityManager.System<DisposalUnitSystem>(); var disposalSystem = entityManager.System<DisposalUnitSystem>();
var power = entityManager.System<PowerReceiverSystem>();
await server.WaitAssertion(() => await server.WaitAssertion(() =>
{ {
// Spawn the entities // Spawn the entities
@@ -191,7 +191,7 @@ namespace Content.IntegrationTests.Tests.Disposal
xformSystem.AnchorEntity(unitUid, entityManager.GetComponent<TransformComponent>(unitUid)); xformSystem.AnchorEntity(unitUid, entityManager.GetComponent<TransformComponent>(unitUid));
// No power // No power
Assert.That(unitComponent.Powered, Is.False); Assert.That(power.IsPowered(unitUid), Is.False);
// Can't insert the trunk or the unit into itself // Can't insert the trunk or the unit into itself
UnitInsertContains(unitUid, unitComponent, false, disposalSystem, disposalUnit, disposalTrunk); UnitInsertContains(unitUid, unitComponent, false, disposalSystem, disposalUnit, disposalTrunk);
@@ -227,9 +227,9 @@ namespace Content.IntegrationTests.Tests.Disposal
await server.WaitAssertion(() => await server.WaitAssertion(() =>
{ {
// Remove power need // Remove power need
Assert.That(entityManager.TryGetComponent(disposalUnit, out ApcPowerReceiverComponent power)); Assert.That(entityManager.TryGetComponent(disposalUnit, out ApcPowerReceiverComponent powerComp));
power!.NeedsPower = false; power.SetNeedsPower(disposalUnit, false);
unitComponent.Powered = true; //Power state changed event doesn't get fired smh powerComp.Powered = true;
// Flush with a mob and an item // Flush with a mob and an item
Flush(disposalUnit, unitComponent, true, disposalSystem, human, wrench); Flush(disposalUnit, unitComponent, true, disposalSystem, human, wrench);

View File

@@ -2,7 +2,6 @@ using Content.Server.Administration.Logs;
using Content.Server.Administration.Managers; using Content.Server.Administration.Managers;
using Content.Server.Administration.UI; using Content.Server.Administration.UI;
using Content.Server.Disposal.Tube; using Content.Server.Disposal.Tube;
using Content.Server.Disposal.Tube.Components;
using Content.Server.EUI; using Content.Server.EUI;
using Content.Server.GameTicking; using Content.Server.GameTicking;
using Content.Server.Ghost.Roles; using Content.Server.Ghost.Roles;
@@ -24,7 +23,6 @@ using Content.Shared.Verbs;
using Robust.Server.Console; using Robust.Server.Console;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;
using Robust.Shared.Console; using Robust.Shared.Console;
using Robust.Shared.Map;
using Robust.Shared.Map.Components; using Robust.Shared.Map.Components;
using Robust.Shared.Player; using Robust.Shared.Player;
using Robust.Shared.Prototypes; using Robust.Shared.Prototypes;

View File

@@ -1,5 +1,4 @@
using Content.Server.Atmos.Monitor.Components; using Content.Server.Atmos.Monitor.Components;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Pinpointer; using Content.Server.Pinpointer;
using Content.Server.Power.Components; using Content.Server.Power.Components;

View File

@@ -17,6 +17,7 @@ using Robust.Shared.Map.Components;
using Robust.Shared.Timing; using Robust.Shared.Timing;
using System.Diagnostics.CodeAnalysis; using System.Diagnostics.CodeAnalysis;
using System.Linq; using System.Linq;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Atmos.Consoles; namespace Content.Server.Atmos.Consoles;

View File

@@ -1,11 +1,8 @@
using Content.Server.Atmos.Monitor.Components; using Content.Server.Atmos.Monitor.Components;
using Content.Server.Atmos.Piping.Components; using Content.Server.Atmos.Piping.Components;
using Content.Server.DeviceLinking.Systems; using Content.Server.DeviceLinking.Systems;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Popups; using Content.Server.Popups;
using Content.Server.Power.Components;
using Content.Server.Power.EntitySystems; using Content.Server.Power.EntitySystems;
using Content.Shared.Access.Components; using Content.Shared.Access.Components;
using Content.Shared.Access.Systems; using Content.Shared.Access.Systems;
@@ -22,8 +19,9 @@ using Content.Shared.Interaction;
using Content.Shared.Power; using Content.Shared.Power;
using Content.Shared.Wires; using Content.Shared.Wires;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;
using Robust.Shared.Player;
using System.Linq; using System.Linq;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Atmos.Monitor.Systems; namespace Content.Server.Atmos.Monitor.Systems;

View File

@@ -1,19 +1,17 @@
using System.Diagnostics.CodeAnalysis; using System.Diagnostics.CodeAnalysis;
using System.Linq; using System.Linq;
using Content.Server.Atmos.Monitor.Components; using Content.Server.Atmos.Monitor.Components;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Power.Components;
using Content.Shared.Atmos.Monitor; using Content.Shared.Atmos.Monitor;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Power; using Content.Shared.Power;
using Content.Shared.Tag; using Content.Shared.Tag;
using Robust.Server.Audio; using Robust.Server.Audio;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;
using Robust.Shared.Audio; using Robust.Shared.Audio;
using Robust.Shared.Prototypes; using Robust.Shared.Prototypes;
using Robust.Shared.Utility; using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Atmos.Monitor.Systems; namespace Content.Server.Atmos.Monitor.Systems;

View File

@@ -15,6 +15,7 @@ using Content.Shared.Atmos.Monitor;
using Content.Shared.Atmos.Piping.Components; using Content.Shared.Atmos.Piping.Components;
using Content.Shared.Database; using Content.Shared.Database;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Power; using Content.Shared.Power;
using Content.Shared.Tag; using Content.Shared.Tag;
using Robust.Shared.Prototypes; using Robust.Shared.Prototypes;

View File

@@ -1,18 +1,12 @@
using Content.Server.AlertLevel;
using Content.Server.Atmos.Monitor.Components; using Content.Server.Atmos.Monitor.Components;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems;
using Content.Server.Power.Components;
using Content.Server.Power.EntitySystems; using Content.Server.Power.EntitySystems;
using Content.Shared.Access.Systems; using Content.Shared.Access.Systems;
using Content.Shared.AlertLevel;
using Content.Shared.Atmos.Monitor; using Content.Shared.Atmos.Monitor;
using Content.Shared.CCVar; using Content.Shared.CCVar;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork.Systems; using Content.Shared.DeviceNetwork.Systems;
using Content.Shared.Interaction; using Content.Shared.Interaction;
using Content.Shared.Emag.Systems; using Content.Shared.Emag.Systems;
using Robust.Server.GameObjects;
using Robust.Shared.Configuration; using Robust.Shared.Configuration;
namespace Content.Server.Atmos.Monitor.Systems; namespace Content.Server.Atmos.Monitor.Systems;

View File

@@ -1,9 +1,9 @@
using Content.Server.Atmos.Monitor.Components; using Content.Server.Atmos.Monitor.Components;
using Content.Server.Atmos.Monitor.Systems; using Content.Server.Atmos.Monitor.Systems;
using Content.Server.DeviceNetwork.Components;
using Content.Server.Wires; using Content.Server.Wires;
using Content.Shared.Atmos.Monitor.Components; using Content.Shared.Atmos.Monitor.Components;
using Content.Shared.Wires; using Content.Shared.Wires;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Atmos.Monitor; namespace Content.Server.Atmos.Monitor;

View File

@@ -1,8 +1,6 @@
using Content.Server.Atmos.EntitySystems; using Content.Server.Atmos.EntitySystems;
using Content.Server.Atmos.Monitor.Systems; using Content.Server.Atmos.Monitor.Systems;
using Content.Server.Atmos.Piping.Components; using Content.Server.Atmos.Piping.Components;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.NodeContainer.EntitySystems; using Content.Server.NodeContainer.EntitySystems;
using Content.Server.NodeContainer.Nodes; using Content.Server.NodeContainer.Nodes;
@@ -12,8 +10,10 @@ using Content.Shared.Atmos.Piping.Binary.Systems;
using Content.Shared.Atmos.Piping.Components; using Content.Shared.Atmos.Piping.Components;
using Content.Shared.Audio; using Content.Shared.Audio;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using JetBrains.Annotations; using JetBrains.Annotations;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Atmos.Piping.Binary.EntitySystems namespace Content.Server.Atmos.Piping.Binary.EntitySystems
{ {

View File

@@ -1,4 +1,3 @@
using Content.Server.Atmos.Piping.Binary.Components;
using Content.Server.Atmos.Piping.Unary.EntitySystems; using Content.Server.Atmos.Piping.Unary.EntitySystems;
using Content.Shared.Atmos; using Content.Shared.Atmos;
using Content.Shared.Atmos.Piping.Binary.Components; using Content.Shared.Atmos.Piping.Binary.Components;

View File

@@ -2,10 +2,7 @@ using Content.Server.Atmos.EntitySystems;
using Content.Server.Atmos.Monitor.Systems; using Content.Server.Atmos.Monitor.Systems;
using Content.Server.Atmos.Piping.Components; using Content.Server.Atmos.Piping.Components;
using Content.Server.Atmos.Piping.Unary.Components; using Content.Server.Atmos.Piping.Unary.Components;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.NodeContainer;
using Content.Server.NodeContainer.EntitySystems; using Content.Server.NodeContainer.EntitySystems;
using Content.Server.NodeContainer.Nodes; using Content.Server.NodeContainer.Nodes;
using Content.Server.Power.Components; using Content.Server.Power.Components;
@@ -18,7 +15,9 @@ using Content.Shared.UserInterface;
using Content.Shared.Administration.Logs; using Content.Shared.Administration.Logs;
using Content.Shared.Database; using Content.Shared.Database;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Examine; using Content.Shared.Examine;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Atmos.Piping.Unary.EntitySystems namespace Content.Server.Atmos.Piping.Unary.EntitySystems
{ {

View File

@@ -3,8 +3,6 @@ using Content.Server.Atmos.Monitor.Systems;
using Content.Server.Atmos.Piping.Components; using Content.Server.Atmos.Piping.Components;
using Content.Server.Atmos.Piping.Unary.Components; using Content.Server.Atmos.Piping.Unary.Components;
using Content.Server.DeviceLinking.Systems; using Content.Server.DeviceLinking.Systems;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.NodeContainer.EntitySystems; using Content.Server.NodeContainer.EntitySystems;
using Content.Server.NodeContainer.Nodes; using Content.Server.NodeContainer.Nodes;
@@ -20,7 +18,9 @@ using Content.Shared.Audio;
using Content.Shared.Database; using Content.Shared.Database;
using Content.Shared.DeviceLinking.Events; using Content.Shared.DeviceLinking.Events;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Components;
using Content.Shared.DoAfter; using Content.Shared.DoAfter;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Examine; using Content.Shared.Examine;
using Content.Shared.Interaction; using Content.Shared.Interaction;
using Content.Shared.Power; using Content.Shared.Power;

View File

@@ -1,25 +1,22 @@
using Content.Server.Atmos.EntitySystems; using Content.Server.Atmos.EntitySystems;
using Content.Server.Atmos.Monitor.Components;
using Content.Server.Atmos.Monitor.Systems; using Content.Server.Atmos.Monitor.Systems;
using Content.Server.Atmos.Piping.Components; using Content.Server.Atmos.Piping.Components;
using Content.Server.Atmos.Piping.Unary.Components; using Content.Server.Atmos.Piping.Unary.Components;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.NodeContainer;
using Content.Server.NodeContainer.EntitySystems; using Content.Server.NodeContainer.EntitySystems;
using Content.Server.NodeContainer.Nodes; using Content.Server.NodeContainer.Nodes;
using Content.Server.Power.Components;
using Content.Server.Power.EntitySystems; using Content.Server.Power.EntitySystems;
using Content.Shared.Administration.Logs; using Content.Shared.Administration.Logs;
using Content.Shared.Atmos; using Content.Shared.Atmos;
using Content.Shared.Atmos.Piping.Unary.Visuals;
using Content.Shared.Atmos.Monitor; using Content.Shared.Atmos.Monitor;
using Content.Shared.Atmos.Piping.Components; using Content.Shared.Atmos.Piping.Components;
using Content.Shared.Atmos.Piping.Unary.Components; using Content.Shared.Atmos.Piping.Unary.Components;
using Content.Shared.Atmos.Piping.Unary.Visuals;
using Content.Shared.Audio; using Content.Shared.Audio;
using Content.Shared.Database; using Content.Shared.Database;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Power; using Content.Shared.Power;
using Content.Shared.Tools.Systems; using Content.Shared.Tools.Systems;
using JetBrains.Annotations; using JetBrains.Annotations;

View File

@@ -3,6 +3,7 @@ using System.Linq;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.PDA; using Content.Server.PDA;
using Content.Shared.CartridgeLoader; using Content.Shared.CartridgeLoader;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Interaction; using Content.Shared.Interaction;
using Robust.Server.Containers; using Robust.Server.Containers;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;

View File

@@ -1,11 +1,10 @@
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Shared.CartridgeLoader; using Content.Shared.CartridgeLoader;
using Content.Shared.CartridgeLoader.Cartridges; using Content.Shared.CartridgeLoader.Cartridges;
using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Components;
using Content.Shared.Popups; using Content.Shared.Popups;
using Robust.Shared.Audio; using Robust.Shared.Audio;
using Robust.Shared.Audio.Systems; using Robust.Shared.Audio.Systems;
using Robust.Shared.Player;
using Robust.Shared.Random; using Robust.Shared.Random;
namespace Content.Server.CartridgeLoader.Cartridges; namespace Content.Server.CartridgeLoader.Cartridges;

View File

@@ -1,9 +1,7 @@
using Content.Server.Administration.Logs; using Content.Server.Administration.Logs;
using Content.Server.AlertLevel; using Content.Server.AlertLevel;
using Content.Server.Chat.Systems; using Content.Server.Chat.Systems;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Interaction;
using Content.Server.Popups; using Content.Server.Popups;
using Content.Server.RoundEnd; using Content.Server.RoundEnd;
using Content.Server.Screens.Components; using Content.Server.Screens.Components;
@@ -16,6 +14,7 @@ using Content.Shared.Chat;
using Content.Shared.Communications; using Content.Shared.Communications;
using Content.Shared.Database; using Content.Shared.Database;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Components;
using Content.Shared.IdentityManagement; using Content.Shared.IdentityManagement;
using Content.Shared.Popups; using Content.Shared.Popups;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;

View File

@@ -1,91 +1,8 @@
using Content.Shared.Configurable; using Content.Shared.Configurable;
using Content.Shared.Interaction;
using Content.Shared.Tools.Components;
using Content.Shared.Tools.Systems;
using Robust.Server.GameObjects;
using Robust.Shared.Containers;
using Robust.Shared.Player;
using static Content.Shared.Configurable.ConfigurationComponent;
namespace Content.Server.Configurable; namespace Content.Server.Configurable;
public sealed class ConfigurationSystem : EntitySystem public sealed class ConfigurationSystem : SharedConfigurationSystem
{ {
[Dependency] private readonly UserInterfaceSystem _uiSystem = default!;
[Dependency] private readonly SharedToolSystem _toolSystem = default!;
public override void Initialize()
{
base.Initialize();
SubscribeLocalEvent<ConfigurationComponent, ConfigurationUpdatedMessage>(OnUpdate);
SubscribeLocalEvent<ConfigurationComponent, ComponentStartup>(OnStartup);
SubscribeLocalEvent<ConfigurationComponent, InteractUsingEvent>(OnInteractUsing);
SubscribeLocalEvent<ConfigurationComponent, ContainerIsInsertingAttemptEvent>(OnInsert);
}
private void OnInteractUsing(EntityUid uid, ConfigurationComponent component, InteractUsingEvent args)
{
// TODO use activatable ui system
if (args.Handled)
return;
if (!_toolSystem.HasQuality(args.Used, component.QualityNeeded))
return;
args.Handled = _uiSystem.TryOpenUi(uid, ConfigurationUiKey.Key, args.User);
}
private void OnStartup(EntityUid uid, ConfigurationComponent component, ComponentStartup args)
{
UpdateUi(uid, component);
}
private void UpdateUi(EntityUid uid, ConfigurationComponent component)
{
if (_uiSystem.HasUi(uid, ConfigurationUiKey.Key))
_uiSystem.SetUiState(uid, ConfigurationUiKey.Key, new ConfigurationBoundUserInterfaceState(component.Config));
}
private void OnUpdate(EntityUid uid, ConfigurationComponent component, ConfigurationUpdatedMessage args)
{
foreach (var key in component.Config.Keys)
{
var value = args.Config.GetValueOrDefault(key);
if (string.IsNullOrWhiteSpace(value) || component.Validation != null && !component.Validation.IsMatch(value))
continue;
component.Config[key] = value;
}
UpdateUi(uid, component);
var updatedEvent = new ConfigurationUpdatedEvent(component);
RaiseLocalEvent(uid, updatedEvent, false);
// TODO support float (spinbox) and enum (drop-down) configurations
// TODO support verbs.
}
private void OnInsert(EntityUid uid, ConfigurationComponent component, ContainerIsInsertingAttemptEvent args)
{
if (!_toolSystem.HasQuality(args.EntityUid, component.QualityNeeded))
return;
args.Cancel();
}
/// <summary>
/// Sent when configuration values got changes
/// </summary>
public sealed class ConfigurationUpdatedEvent : EntityEventArgs
{
public ConfigurationComponent Configuration;
public ConfigurationUpdatedEvent(ConfigurationComponent configuration)
{
Configuration = configuration;
}
}
} }

View File

@@ -1,4 +1,5 @@
using Content.Server.Administration.Logs; using Content.Server.Administration.Logs;
using Content.Shared.Containers;
using Content.Shared.Database; using Content.Shared.Database;
using Content.Shared.Popups; using Content.Shared.Popups;
using Content.Shared.Throwing; using Content.Shared.Throwing;
@@ -52,10 +53,3 @@ public sealed class ThrowInsertContainerSystem : EntitySystem
_adminLogger.Add(LogType.Landed, LogImpact.Low, $"{ToPrettyString(args.Thrown)} thrown by {ToPrettyString(args.Component.Thrower.Value):player} landed in {ToPrettyString(ent)}"); _adminLogger.Add(LogType.Landed, LogImpact.Low, $"{ToPrettyString(args.Thrown)} thrown by {ToPrettyString(args.Component.Thrower.Value):player} landed in {ToPrettyString(ent)}");
} }
} }
/// <summary>
/// Sent before the insertion is made.
/// Allows preventing the insertion if any system on the entity should need to.
/// </summary>
[ByRefEvent]
public record struct BeforeThrowInsertEvent(EntityUid ThrownEntity, bool Cancelled = false);

View File

@@ -1,10 +1,10 @@
using Content.Server.DeviceLinking.Components; using Content.Server.DeviceLinking.Components;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Shared.DeviceLinking; using Content.Shared.DeviceLinking;
using Content.Shared.DeviceLinking.Events; using Content.Shared.DeviceLinking.Events;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.DeviceLinking.Systems; namespace Content.Server.DeviceLinking.Systems;

View File

@@ -2,6 +2,7 @@ using Content.Server.DeviceLinking.Components;
using Content.Server.DeviceNetwork; using Content.Server.DeviceNetwork;
using Content.Server.Doors.Systems; using Content.Server.Doors.Systems;
using Content.Shared.DeviceLinking.Events; using Content.Shared.DeviceLinking.Events;
using Content.Shared.DeviceNetwork;
using Content.Shared.Doors.Components; using Content.Shared.Doors.Components;
using Content.Shared.Doors; using Content.Shared.Doors;
using JetBrains.Annotations; using JetBrains.Annotations;

View File

@@ -1,6 +1,6 @@
using Content.Server.DeviceLinking.Components; using Content.Server.DeviceLinking.Components;
using Content.Server.DeviceNetwork;
using Content.Shared.DeviceLinking.Events; using Content.Shared.DeviceLinking.Events;
using Content.Shared.DeviceNetwork;
namespace Content.Server.DeviceLinking.Systems; namespace Content.Server.DeviceLinking.Systems;

View File

@@ -2,6 +2,7 @@ using Content.Server.DeviceLinking.Components;
using Content.Server.DeviceNetwork; using Content.Server.DeviceNetwork;
using Content.Shared.DeviceLinking; using Content.Shared.DeviceLinking;
using Content.Shared.DeviceLinking.Events; using Content.Shared.DeviceLinking.Events;
using Content.Shared.DeviceNetwork;
using Content.Shared.Examine; using Content.Shared.Examine;
using Content.Shared.Interaction; using Content.Shared.Interaction;
using Content.Shared.Popups; using Content.Shared.Popups;

View File

@@ -2,6 +2,7 @@ using Content.Server.DeviceLinking.Components;
using Content.Server.DeviceNetwork; using Content.Server.DeviceNetwork;
using Content.Shared.DeviceLinking; using Content.Shared.DeviceLinking;
using Content.Shared.DeviceLinking.Events; using Content.Shared.DeviceLinking.Events;
using Content.Shared.DeviceNetwork;
namespace Content.Server.DeviceLinking.Systems; namespace Content.Server.DeviceLinking.Systems;

View File

@@ -4,6 +4,7 @@ using Content.Server.NodeContainer.EntitySystems;
using JetBrains.Annotations; using JetBrains.Annotations;
using Content.Server.Power.EntitySystems; using Content.Server.Power.EntitySystems;
using Content.Server.Power.Nodes; using Content.Server.Power.Nodes;
using Content.Shared.DeviceNetwork.Events;
namespace Content.Server.DeviceNetwork.Systems namespace Content.Server.DeviceNetwork.Systems
{ {

View File

@@ -1,9 +1,7 @@
using System.Linq; using System.Linq;
using Content.Server.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Components; using Content.Shared.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.DeviceNetwork.Systems; using Content.Shared.DeviceNetwork.Systems;
using Content.Shared.Interaction;
using JetBrains.Annotations; using JetBrains.Annotations;
using Robust.Shared.Map.Events; using Robust.Shared.Map.Events;

View File

@@ -1,4 +1,5 @@
using Content.Shared.DeviceNetwork.Components; using Content.Shared.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.DeviceNetwork.Systems; using Content.Shared.DeviceNetwork.Systems;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;

View File

@@ -1,6 +1,7 @@
using Content.Server.DeviceNetwork.Components; using Content.Server.DeviceNetwork.Components;
using Content.Server.Power.Components; using Content.Server.Power.Components;
using Content.Server.Power.EntitySystems; using Content.Server.Power.EntitySystems;
using Content.Shared.DeviceNetwork.Events;
namespace Content.Server.DeviceNetwork.Systems; namespace Content.Server.DeviceNetwork.Systems;

View File

@@ -1,12 +1,12 @@
using Content.Server.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using JetBrains.Annotations; using JetBrains.Annotations;
using Robust.Shared.Prototypes; using Robust.Shared.Prototypes;
using Robust.Shared.Random; using Robust.Shared.Random;
using System.Buffers; using System.Buffers;
using System.Diagnostics.CodeAnalysis; using System.Diagnostics.CodeAnalysis;
using System.Numerics;
using Content.Shared.DeviceNetwork.Components; using Content.Shared.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.DeviceNetwork.Systems;
using Content.Shared.Examine; using Content.Shared.Examine;
namespace Content.Server.DeviceNetwork.Systems namespace Content.Server.DeviceNetwork.Systems
@@ -16,7 +16,7 @@ namespace Content.Server.DeviceNetwork.Systems
/// Device networking allows machines and devices to communicate with each other while adhering to restrictions like range or being connected to the same powernet. /// Device networking allows machines and devices to communicate with each other while adhering to restrictions like range or being connected to the same powernet.
/// </summary> /// </summary>
[UsedImplicitly] [UsedImplicitly]
public sealed class DeviceNetworkSystem : EntitySystem public sealed class DeviceNetworkSystem : SharedDeviceNetworkSystem
{ {
[Dependency] private readonly IRobustRandom _random = default!; [Dependency] private readonly IRobustRandom _random = default!;
[Dependency] private readonly IPrototypeManager _protoMan = default!; [Dependency] private readonly IPrototypeManager _protoMan = default!;
@@ -60,16 +60,7 @@ namespace Content.Server.DeviceNetwork.Systems
SwapQueues(); SwapQueues();
} }
/// <summary> public override bool QueuePacket(EntityUid uid, string? address, NetworkPayload data, uint? frequency = null, int? network = null, DeviceNetworkComponent? device = null)
/// Sends the given payload as a device network packet to the entity with the given address and frequency.
/// Addresses are given to the DeviceNetworkComponent of an entity when connecting.
/// </summary>
/// <param name="uid">The EntityUid of the sending entity</param>
/// <param name="address">The address of the entity that the packet gets sent to. If null, the message is broadcast to all devices on that frequency (except the sender)</param>
/// <param name="frequency">The frequency to send on</param>
/// <param name="data">The data to be sent</param>
/// <returns>Returns true when the packet was successfully enqueued.</returns>
public bool QueuePacket(EntityUid uid, string? address, NetworkPayload data, uint? frequency = null, int? network = null, DeviceNetworkComponent? device = null)
{ {
if (!Resolve(uid, ref device, false)) if (!Resolve(uid, ref device, false))
return false; return false;
@@ -368,96 +359,4 @@ namespace Content.Server.DeviceNetwork.Systems
} }
} }
} }
/// <summary>
/// Event raised before a device network packet is send.
/// Subscribed to by other systems to prevent the packet from being sent.
/// </summary>
public sealed class BeforePacketSentEvent : CancellableEntityEventArgs
{
/// <summary>
/// The EntityUid of the entity the packet was sent from.
/// </summary>
public readonly EntityUid Sender;
public readonly TransformComponent SenderTransform;
/// <summary>
/// The senders current position in world coordinates.
/// </summary>
public readonly Vector2 SenderPosition;
/// <summary>
/// The network the packet will be sent to.
/// </summary>
public readonly string NetworkId;
public BeforePacketSentEvent(EntityUid sender, TransformComponent xform, Vector2 senderPosition, string networkId)
{
Sender = sender;
SenderTransform = xform;
SenderPosition = senderPosition;
NetworkId = networkId;
}
}
/// <summary>
/// Sent to the sending entity before broadcasting network packets to recipients
/// </summary>
public sealed class BeforeBroadcastAttemptEvent : CancellableEntityEventArgs
{
public readonly IReadOnlySet<DeviceNetworkComponent> Recipients;
public HashSet<DeviceNetworkComponent>? ModifiedRecipients;
public BeforeBroadcastAttemptEvent(IReadOnlySet<DeviceNetworkComponent> recipients)
{
Recipients = recipients;
}
}
/// <summary>
/// Event raised when a device network packet gets sent.
/// </summary>
public sealed class DeviceNetworkPacketEvent : EntityEventArgs
{
/// <summary>
/// The id of the network that this packet is being sent on.
/// </summary>
public int NetId;
/// <summary>
/// The frequency the packet is sent on.
/// </summary>
public readonly uint Frequency;
/// <summary>
/// Address of the intended recipient. Null if the message was broadcast.
/// </summary>
public string? Address;
/// <summary>
/// The device network address of the sending entity.
/// </summary>
public readonly string SenderAddress;
/// <summary>
/// The entity that sent the packet.
/// </summary>
public EntityUid Sender;
/// <summary>
/// The data that is being sent.
/// </summary>
public readonly NetworkPayload Data;
public DeviceNetworkPacketEvent(int netId, string? address, uint frequency, string senderAddress, EntityUid sender, NetworkPayload data)
{
NetId = netId;
Address = address;
Frequency = frequency;
SenderAddress = senderAddress;
Sender = sender;
Data = data;
}
}
} }

View File

@@ -1,7 +1,8 @@
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Components.Devices; using Content.Server.DeviceNetwork.Components.Devices;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Interaction; using Content.Shared.Interaction;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.DeviceNetwork.Systems.Devices namespace Content.Server.DeviceNetwork.Systems.Devices
{ {

View File

@@ -1,7 +1,6 @@
using System.Linq; using System.Linq;
using Content.Server.Administration.Logs; using Content.Server.Administration.Logs;
using Content.Server.DeviceLinking.Systems; using Content.Server.DeviceLinking.Systems;
using Content.Server.DeviceNetwork.Components;
using Content.Shared.Access.Components; using Content.Shared.Access.Components;
using Content.Shared.Access.Systems; using Content.Shared.Access.Systems;
using Content.Shared.Database; using Content.Shared.Database;

View File

@@ -1,9 +1,9 @@
using System.Diagnostics.CodeAnalysis; using System.Diagnostics.CodeAnalysis;
using Content.Server.DeviceNetwork.Components; using Content.Server.DeviceNetwork.Components;
using Content.Server.Medical.CrewMonitoring; using Content.Server.Medical.CrewMonitoring;
using Content.Server.Power.Components;
using Content.Server.Station.Systems; using Content.Server.Station.Systems;
using Content.Shared.Power; using Content.Shared.Power;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.DeviceNetwork.Systems; namespace Content.Server.DeviceNetwork.Systems;

View File

@@ -1,5 +1,6 @@
using Content.Server.DeviceNetwork.Components; using Content.Server.DeviceNetwork.Components;
using Content.Server.Station.Systems; using Content.Server.Station.Systems;
using Content.Shared.DeviceNetwork.Events;
using JetBrains.Annotations; using JetBrains.Annotations;
using Robust.Shared.Map; using Robust.Shared.Map;

View File

@@ -1,4 +1,5 @@
using Content.Server.DeviceNetwork.Components; using Content.Server.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork.Events;
using JetBrains.Annotations; using JetBrains.Annotations;
namespace Content.Server.DeviceNetwork.Systems namespace Content.Server.DeviceNetwork.Systems

View File

@@ -1,4 +1,5 @@
using Content.Server.DeviceNetwork.Components; using Content.Server.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork.Events;
using JetBrains.Annotations; using JetBrains.Annotations;
namespace Content.Server.DeviceNetwork.Systems namespace Content.Server.DeviceNetwork.Systems

View File

@@ -1,204 +1,8 @@
using Content.Server.Configurable; using Content.Shared.Disposal.Mailing;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems;
using Content.Server.Disposal.Unit.EntitySystems;
using Content.Server.Power.Components;
using Content.Shared.DeviceNetwork;
using Content.Shared.Disposal;
using Content.Shared.Interaction;
using Robust.Server.GameObjects;
using Robust.Shared.Player;
using Robust.Shared.Utility;
namespace Content.Server.Disposal.Mailing; namespace Content.Server.Disposal.Mailing;
public sealed class MailingUnitSystem : EntitySystem public sealed class MailingUnitSystem : SharedMailingUnitSystem
{ {
[Dependency] private readonly DeviceNetworkSystem _deviceNetworkSystem = default!;
[Dependency] private readonly UserInterfaceSystem _userInterfaceSystem = default!;
private const string MailTag = "mail";
private const string TagConfigurationKey = "tag";
private const string NetTag = "tag";
private const string NetSrc = "src";
private const string NetTarget = "target";
private const string NetCmdSent = "mail_sent";
private const string NetCmdRequest = "get_mailer_tag";
private const string NetCmdResponse = "mailer_tag";
public override void Initialize()
{
base.Initialize();
SubscribeLocalEvent<MailingUnitComponent, ComponentInit>(OnComponentInit);
SubscribeLocalEvent<MailingUnitComponent, DeviceNetworkPacketEvent>(OnPacketReceived);
SubscribeLocalEvent<MailingUnitComponent, BeforeDisposalFlushEvent>(OnBeforeFlush);
SubscribeLocalEvent<MailingUnitComponent, ConfigurationSystem.ConfigurationUpdatedEvent>(OnConfigurationUpdated);
SubscribeLocalEvent<MailingUnitComponent, ActivateInWorldEvent>(HandleActivate, before: new[] { typeof(DisposalUnitSystem) });
SubscribeLocalEvent<MailingUnitComponent, DisposalUnitUIStateUpdatedEvent>(OnDisposalUnitUIStateChange);
SubscribeLocalEvent<MailingUnitComponent, TargetSelectedMessage>(OnTargetSelected);
}
private void OnComponentInit(EntityUid uid, MailingUnitComponent component, ComponentInit args)
{
UpdateTargetList(uid, component);
}
private void OnPacketReceived(EntityUid uid, MailingUnitComponent component, DeviceNetworkPacketEvent args)
{
if (!args.Data.TryGetValue(DeviceNetworkConstants.Command, out string? command) || !IsPowered(uid))
return;
switch (command)
{
case NetCmdRequest:
SendTagRequestResponse(uid, args, component.Tag);
break;
case NetCmdResponse when args.Data.TryGetValue(NetTag, out string? tag):
//Add the received tag request response to the list of targets
component.TargetList.Add(tag);
UpdateUserInterface(uid, component);
break;
}
}
/// <summary>
/// Sends the given tag as a response to a <see cref="NetCmdRequest"/> if it's not null
/// </summary>
private void SendTagRequestResponse(EntityUid uid, DeviceNetworkPacketEvent args, string? tag)
{
if (tag == null)
return;
var payload = new NetworkPayload
{
[DeviceNetworkConstants.Command] = NetCmdResponse,
[NetTag] = tag
};
_deviceNetworkSystem.QueuePacket(uid, args.Address, payload, args.Frequency);
}
/// <summary>
/// Prevents the unit from flushing if no target is selected
/// </summary>
private void OnBeforeFlush(EntityUid uid, MailingUnitComponent component, BeforeDisposalFlushEvent args)
{
if (string.IsNullOrEmpty(component.Target))
{
args.Cancel();
return;
}
args.Tags.Add(MailTag);
args.Tags.Add(component.Target);
BroadcastSentMessage(uid, component);
}
/// <summary>
/// Broadcast that a mail was sent including the src and target tags
/// </summary>
private void BroadcastSentMessage(EntityUid uid, MailingUnitComponent component, DeviceNetworkComponent? device = null)
{
if (string.IsNullOrEmpty(component.Tag) || string.IsNullOrEmpty(component.Target) || !Resolve(uid, ref device))
return;
var payload = new NetworkPayload
{
[DeviceNetworkConstants.Command] = NetCmdSent,
[NetSrc] = component.Tag,
[NetTarget] = component.Target
};
_deviceNetworkSystem.QueuePacket(uid, null, payload, null, null, device);
}
/// <summary>
/// Clears the units target list and broadcasts a <see cref="NetCmdRequest"/>.
/// The target list will then get populated with <see cref="NetCmdResponse"/> responses from all active mailing units on the same grid
/// </summary>
private void UpdateTargetList(EntityUid uid, MailingUnitComponent component, DeviceNetworkComponent? device = null)
{
if (!Resolve(uid, ref device, false))
return;
var payload = new NetworkPayload
{
[DeviceNetworkConstants.Command] = NetCmdRequest
};
component.TargetList.Clear();
_deviceNetworkSystem.QueuePacket(uid, null, payload, null, null, device);
}
/// <summary>
/// Gets called when the units tag got updated
/// </summary>
private void OnConfigurationUpdated(EntityUid uid, MailingUnitComponent component, ConfigurationSystem.ConfigurationUpdatedEvent args)
{
var configuration = args.Configuration.Config;
if (!configuration.ContainsKey(TagConfigurationKey) || configuration[TagConfigurationKey] == string.Empty)
{
component.Tag = null;
return;
}
component.Tag = configuration[TagConfigurationKey];
UpdateUserInterface(uid, component);
}
private void HandleActivate(EntityUid uid, MailingUnitComponent component, ActivateInWorldEvent args)
{
if (args.Handled || !args.Complex)
return;
if (!EntityManager.TryGetComponent(args.User, out ActorComponent? actor))
{
return;
}
args.Handled = true;
UpdateTargetList(uid, component);
_userInterfaceSystem.OpenUi(uid, MailingUnitUiKey.Key, actor.PlayerSession);
}
/// <summary>
/// Gets called when the disposal unit components ui state changes. This is required because the mailing unit requires a disposal unit component and overrides its ui
/// </summary>
private void OnDisposalUnitUIStateChange(EntityUid uid, MailingUnitComponent component, DisposalUnitUIStateUpdatedEvent args)
{
component.DisposalUnitInterfaceState = args.State;
UpdateUserInterface(uid, component);
}
private void UpdateUserInterface(EntityUid uid, MailingUnitComponent component)
{
if (component.DisposalUnitInterfaceState == null)
return;
var state = new MailingUnitBoundUserInterfaceState(component.DisposalUnitInterfaceState, component.Target, component.TargetList.ShallowClone(), component.Tag);
_userInterfaceSystem.SetUiState(uid, MailingUnitUiKey.Key, state);
}
private void OnTargetSelected(EntityUid uid, MailingUnitComponent component, TargetSelectedMessage args)
{
component.Target = args.Target;
UpdateUserInterface(uid, component);
}
/// <summary>
/// Checks if the unit is powered if an <see cref="ApcPowerReceiverComponent"/> is present
/// </summary>
/// <returns>True if the power receiver component is powered or not present</returns>
private bool IsPowered(EntityUid uid, ApcPowerReceiverComponent? powerReceiver = null)
{
if (Resolve(uid, ref powerReceiver) && !powerReceiver.Powered)
return false;
return true;
}
} }

View File

@@ -1,11 +0,0 @@
using Content.Server.Disposal.Unit.EntitySystems;
namespace Content.Server.Disposal.Tube.Components
{
[RegisterComponent]
[Access(typeof(DisposalTubeSystem), typeof(DisposalUnitSystem))]
public sealed partial class DisposalEntryComponent : Component
{
public const string HolderPrototypeId = "DisposalHolder";
}
}

View File

@@ -1,4 +1,4 @@
namespace Content.Server.Disposal.Tube.Components; namespace Content.Server.Disposal.Tube;
[RegisterComponent] [RegisterComponent]
[Access(typeof(DisposalTubeSystem))] [Access(typeof(DisposalTubeSystem))]

View File

@@ -1,4 +1,4 @@
namespace Content.Server.Disposal.Tube.Components; namespace Content.Server.Disposal.Tube;
[RegisterComponent] [RegisterComponent]
[Access(typeof(DisposalTubeSystem))] [Access(typeof(DisposalTubeSystem))]

View File

@@ -1,12 +1,6 @@
using Content.Server.UserInterface;
using Robust.Server.GameObjects;
using Robust.Shared.Audio; using Robust.Shared.Audio;
using Robust.Shared.Physics;
using Robust.Shared.Physics.Components;
using Robust.Shared.Player;
using static Content.Shared.Disposal.Components.SharedDisposalRouterComponent;
namespace Content.Server.Disposal.Tube.Components namespace Content.Server.Disposal.Tube
{ {
[RegisterComponent] [RegisterComponent]
[Access(typeof(DisposalTubeSystem))] [Access(typeof(DisposalTubeSystem))]

View File

@@ -1,8 +1,7 @@
using Content.Server.Disposal.Tube.Systems;
using Content.Shared.DeviceLinking; using Content.Shared.DeviceLinking;
using Robust.Shared.Prototypes; using Robust.Shared.Prototypes;
namespace Content.Server.Disposal.Tube.Components; namespace Content.Server.Disposal.Tube;
/// <summary> /// <summary>
/// Requires <see cref="DisposalJunctionComponent"/> to function. /// Requires <see cref="DisposalJunctionComponent"/> to function.

View File

@@ -1,8 +1,7 @@
using Content.Server.DeviceLinking.Systems; using Content.Server.DeviceLinking.Systems;
using Content.Server.Disposal.Tube.Components;
using Content.Shared.DeviceLinking.Events; using Content.Shared.DeviceLinking.Events;
namespace Content.Server.Disposal.Tube.Systems; namespace Content.Server.Disposal.Tube;
/// <summary> /// <summary>
/// Handles signals and the routing get next direction event. /// Handles signals and the routing get next direction event.

View File

@@ -1,13 +1,6 @@
using Content.Server.Disposal.Unit.Components;
using Content.Server.UserInterface;
using Robust.Server.GameObjects;
using Robust.Shared.Audio; using Robust.Shared.Audio;
using Robust.Shared.Physics;
using Robust.Shared.Physics.Components;
using Robust.Shared.Player;
using static Content.Shared.Disposal.Components.SharedDisposalTaggerComponent;
namespace Content.Server.Disposal.Tube.Components namespace Content.Server.Disposal.Tube
{ {
[RegisterComponent] [RegisterComponent]
public sealed partial class DisposalTaggerComponent : DisposalTransitComponent public sealed partial class DisposalTaggerComponent : DisposalTransitComponent

View File

@@ -1,4 +1,4 @@
namespace Content.Server.Disposal.Tube.Components namespace Content.Server.Disposal.Tube
{ {
// TODO: Different types of tubes eject in random direction with no exit point // TODO: Different types of tubes eject in random direction with no exit point
[RegisterComponent] [RegisterComponent]

View File

@@ -1,9 +1,9 @@
using Content.Server.Disposal.Unit.EntitySystems; using Content.Server.Disposal.Unit;
using Content.Shared.Damage; using Content.Shared.Damage;
using Robust.Shared.Audio; using Robust.Shared.Audio;
using Robust.Shared.Containers; using Robust.Shared.Containers;
namespace Content.Server.Disposal.Tube.Components; namespace Content.Server.Disposal.Tube;
[RegisterComponent] [RegisterComponent]
[Access(typeof(DisposalTubeSystem), typeof(DisposableSystem))] [Access(typeof(DisposalTubeSystem), typeof(DisposableSystem))]

View File

@@ -2,12 +2,12 @@ using System.Linq;
using System.Text; using System.Text;
using Content.Server.Atmos.EntitySystems; using Content.Server.Atmos.EntitySystems;
using Content.Server.Construction.Completions; using Content.Server.Construction.Completions;
using Content.Server.Disposal.Tube.Components; using Content.Server.Disposal.Unit;
using Content.Server.Disposal.Unit.Components;
using Content.Server.Disposal.Unit.EntitySystems;
using Content.Server.Popups; using Content.Server.Popups;
using Content.Shared.Destructible; using Content.Shared.Destructible;
using Content.Shared.Disposal.Components; using Content.Shared.Disposal.Components;
using Content.Shared.Disposal.Tube;
using Content.Shared.Disposal.Unit;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;
using Robust.Shared.Audio; using Robust.Shared.Audio;
using Robust.Shared.Audio.Systems; using Robust.Shared.Audio.Systems;
@@ -16,12 +16,10 @@ using Robust.Shared.Map.Components;
using Robust.Shared.Physics; using Robust.Shared.Physics;
using Robust.Shared.Physics.Components; using Robust.Shared.Physics.Components;
using Robust.Shared.Random; using Robust.Shared.Random;
using static Content.Shared.Disposal.Components.SharedDisposalRouterComponent;
using static Content.Shared.Disposal.Components.SharedDisposalTaggerComponent;
namespace Content.Server.Disposal.Tube namespace Content.Server.Disposal.Tube
{ {
public sealed class DisposalTubeSystem : EntitySystem public sealed class DisposalTubeSystem : SharedDisposalTubeSystem
{ {
[Dependency] private readonly IRobustRandom _random = default!; [Dependency] private readonly IRobustRandom _random = default!;
[Dependency] private readonly SharedAppearanceSystem _appearanceSystem = default!; [Dependency] private readonly SharedAppearanceSystem _appearanceSystem = default!;
@@ -49,8 +47,8 @@ namespace Content.Server.Disposal.Tube
SubscribeLocalEvent<DisposalBendComponent, GetDisposalsConnectableDirectionsEvent>(OnGetBendConnectableDirections); SubscribeLocalEvent<DisposalBendComponent, GetDisposalsConnectableDirectionsEvent>(OnGetBendConnectableDirections);
SubscribeLocalEvent<DisposalBendComponent, GetDisposalsNextDirectionEvent>(OnGetBendNextDirection); SubscribeLocalEvent<DisposalBendComponent, GetDisposalsNextDirectionEvent>(OnGetBendNextDirection);
SubscribeLocalEvent<DisposalEntryComponent, GetDisposalsConnectableDirectionsEvent>(OnGetEntryConnectableDirections); SubscribeLocalEvent<Shared.Disposal.Tube.DisposalEntryComponent, GetDisposalsConnectableDirectionsEvent>(OnGetEntryConnectableDirections);
SubscribeLocalEvent<DisposalEntryComponent, GetDisposalsNextDirectionEvent>(OnGetEntryNextDirection); SubscribeLocalEvent<Shared.Disposal.Tube.DisposalEntryComponent, GetDisposalsNextDirectionEvent>(OnGetEntryNextDirection);
SubscribeLocalEvent<DisposalJunctionComponent, GetDisposalsConnectableDirectionsEvent>(OnGetJunctionConnectableDirections); SubscribeLocalEvent<DisposalJunctionComponent, GetDisposalsConnectableDirectionsEvent>(OnGetJunctionConnectableDirections);
SubscribeLocalEvent<DisposalJunctionComponent, GetDisposalsNextDirectionEvent>(OnGetJunctionNextDirection); SubscribeLocalEvent<DisposalJunctionComponent, GetDisposalsNextDirectionEvent>(OnGetJunctionNextDirection);
@@ -64,13 +62,13 @@ namespace Content.Server.Disposal.Tube
SubscribeLocalEvent<DisposalTaggerComponent, GetDisposalsConnectableDirectionsEvent>(OnGetTaggerConnectableDirections); SubscribeLocalEvent<DisposalTaggerComponent, GetDisposalsConnectableDirectionsEvent>(OnGetTaggerConnectableDirections);
SubscribeLocalEvent<DisposalTaggerComponent, GetDisposalsNextDirectionEvent>(OnGetTaggerNextDirection); SubscribeLocalEvent<DisposalTaggerComponent, GetDisposalsNextDirectionEvent>(OnGetTaggerNextDirection);
Subs.BuiEvents<DisposalRouterComponent>(DisposalRouterUiKey.Key, subs => Subs.BuiEvents<DisposalRouterComponent>(SharedDisposalRouterComponent.DisposalRouterUiKey.Key, subs =>
{ {
subs.Event<BoundUIOpenedEvent>(OnOpenRouterUI); subs.Event<BoundUIOpenedEvent>(OnOpenRouterUI);
subs.Event<SharedDisposalRouterComponent.UiActionMessage>(OnUiAction); subs.Event<SharedDisposalRouterComponent.UiActionMessage>(OnUiAction);
}); });
Subs.BuiEvents<DisposalTaggerComponent>(DisposalTaggerUiKey.Key, subs => Subs.BuiEvents<DisposalTaggerComponent>(SharedDisposalTaggerComponent.DisposalTaggerUiKey.Key, subs =>
{ {
subs.Event<BoundUIOpenedEvent>(OnOpenTaggerUI); subs.Event<BoundUIOpenedEvent>(OnOpenTaggerUI);
subs.Event<SharedDisposalTaggerComponent.UiActionMessage>(OnUiAction); subs.Event<SharedDisposalTaggerComponent.UiActionMessage>(OnUiAction);
@@ -161,12 +159,12 @@ namespace Content.Server.Disposal.Tube
args.Next = previousDF == ev.Connectable[0] ? ev.Connectable[1] : ev.Connectable[0]; args.Next = previousDF == ev.Connectable[0] ? ev.Connectable[1] : ev.Connectable[0];
} }
private void OnGetEntryConnectableDirections(EntityUid uid, DisposalEntryComponent component, ref GetDisposalsConnectableDirectionsEvent args) private void OnGetEntryConnectableDirections(EntityUid uid, Shared.Disposal.Tube.DisposalEntryComponent component, ref GetDisposalsConnectableDirectionsEvent args)
{ {
args.Connectable = new[] { Transform(uid).LocalRotation.GetDir() }; args.Connectable = new[] { Transform(uid).LocalRotation.GetDir() };
} }
private void OnGetEntryNextDirection(EntityUid uid, DisposalEntryComponent component, ref GetDisposalsNextDirectionEvent args) private void OnGetEntryNextDirection(EntityUid uid, Shared.Disposal.Tube.DisposalEntryComponent component, ref GetDisposalsNextDirectionEvent args)
{ {
// Ejects contents when they come from the same direction the entry is facing. // Ejects contents when they come from the same direction the entry is facing.
if (args.Holder.PreviousDirectionFrom != Direction.Invalid) if (args.Holder.PreviousDirectionFrom != Direction.Invalid)
@@ -283,10 +281,10 @@ namespace Content.Server.Disposal.Tube
private void OnOpenTaggerUI(EntityUid uid, DisposalTaggerComponent tagger, BoundUIOpenedEvent args) private void OnOpenTaggerUI(EntityUid uid, DisposalTaggerComponent tagger, BoundUIOpenedEvent args)
{ {
if (_uiSystem.HasUi(uid, DisposalTaggerUiKey.Key)) if (_uiSystem.HasUi(uid, SharedDisposalTaggerComponent.DisposalTaggerUiKey.Key))
{ {
_uiSystem.SetUiState(uid, DisposalTaggerUiKey.Key, _uiSystem.SetUiState(uid, SharedDisposalTaggerComponent.DisposalTaggerUiKey.Key,
new DisposalTaggerUserInterfaceState(tagger.Tag)); new SharedDisposalTaggerComponent.DisposalTaggerUserInterfaceState(tagger.Tag));
} }
} }
@@ -298,7 +296,7 @@ namespace Content.Server.Disposal.Tube
{ {
if (router.Tags.Count <= 0) if (router.Tags.Count <= 0)
{ {
_uiSystem.SetUiState(uid, DisposalRouterUiKey.Key, new DisposalRouterUserInterfaceState("")); _uiSystem.SetUiState(uid, SharedDisposalRouterComponent.DisposalRouterUiKey.Key, new SharedDisposalRouterComponent.DisposalRouterUserInterfaceState(""));
return; return;
} }
@@ -312,7 +310,7 @@ namespace Content.Server.Disposal.Tube
taglist.Remove(taglist.Length - 2, 2); taglist.Remove(taglist.Length - 2, 2);
_uiSystem.SetUiState(uid, DisposalRouterUiKey.Key, new DisposalRouterUserInterfaceState(taglist.ToString())); _uiSystem.SetUiState(uid, SharedDisposalRouterComponent.DisposalRouterUiKey.Key, new SharedDisposalRouterComponent.DisposalRouterUserInterfaceState(taglist.ToString()));
} }
private void OnAnchorChange(EntityUid uid, DisposalTubeComponent component, ref AnchorStateChangedEvent args) private void OnAnchorChange(EntityUid uid, DisposalTubeComponent component, ref AnchorStateChangedEvent args)
@@ -419,13 +417,13 @@ namespace Content.Server.Disposal.Tube
_popups.PopupEntity(Loc.GetString("disposal-tube-component-popup-directions-text", ("directions", directions)), tubeId, recipient); _popups.PopupEntity(Loc.GetString("disposal-tube-component-popup-directions-text", ("directions", directions)), tubeId, recipient);
} }
public bool TryInsert(EntityUid uid, DisposalUnitComponent from, IEnumerable<string>? tags = default, DisposalEntryComponent? entry = null) public override bool TryInsert(EntityUid uid, DisposalUnitComponent from, IEnumerable<string>? tags = default, DisposalEntryComponent? entry = null)
{ {
if (!Resolve(uid, ref entry)) if (!Resolve(uid, ref entry))
return false; return false;
var xform = Transform(uid); var xform = Transform(uid);
var holder = Spawn(DisposalEntryComponent.HolderPrototypeId, _transform.GetMapCoordinates(uid, xform: xform)); var holder = Spawn(entry.HolderPrototypeId, _transform.GetMapCoordinates(uid, xform: xform));
var holderComponent = Comp<DisposalHolderComponent>(holder); var holderComponent = Comp<DisposalHolderComponent>(holder);
foreach (var entity in from.Container.ContainedEntities.ToArray()) foreach (var entity in from.Container.ContainedEntities.ToArray())
@@ -436,7 +434,7 @@ namespace Content.Server.Disposal.Tube
_atmosSystem.Merge(holderComponent.Air, from.Air); _atmosSystem.Merge(holderComponent.Air, from.Air);
from.Air.Clear(); from.Air.Clear();
if (tags != default) if (tags != null)
holderComponent.Tags.UnionWith(tags); holderComponent.Tags.UnionWith(tags);
return _disposableSystem.EnterTube(holder, uid, holderComponent); return _disposableSystem.EnterTube(holder, uid, holderComponent);

View File

@@ -1,4 +1,4 @@
using Content.Server.Disposal.Unit.Components; using Content.Server.Disposal.Unit;
namespace Content.Server.Disposal.Tube; namespace Content.Server.Disposal.Tube;

View File

@@ -1,6 +1,5 @@
using Content.Server.Administration; using Content.Server.Administration;
using Content.Server.Disposal.Tube; using Content.Server.Disposal.Tube;
using Content.Server.Disposal.Tube.Components;
using Content.Shared.Administration; using Content.Shared.Administration;
using Robust.Shared.Console; using Robust.Shared.Console;

View File

@@ -1,4 +1,4 @@
namespace Content.Server.Disposal.Unit.Components; namespace Content.Server.Disposal.Unit;
/// <summary> /// <summary>
/// A component added to entities that are currently in disposals. /// A component added to entities that are currently in disposals.

View File

@@ -1,8 +1,7 @@
using Content.Server.Atmos.EntitySystems; using Content.Server.Atmos.EntitySystems;
using Content.Server.Body.Systems; using Content.Server.Body.Systems;
using Content.Server.Disposal.Unit.Components;
namespace Content.Server.Disposal.Unit.EntitySystems; namespace Content.Server.Disposal.Unit;
public sealed class BeingDisposedSystem : EntitySystem public sealed class BeingDisposedSystem : EntitySystem
{ {

View File

@@ -1,13 +0,0 @@
using Content.Server.Atmos;
using Content.Shared.Atmos;
using Content.Shared.Disposal.Components;
namespace Content.Server.Disposal.Unit.Components;
// GasMixture life.
[RegisterComponent]
public sealed partial class DisposalUnitComponent : SharedDisposalUnitComponent
{
[DataField("air")]
public GasMixture Air = new(Atmospherics.CellVolume);
}

View File

@@ -1,9 +1,8 @@
using Content.Server.Atmos.EntitySystems; using Content.Server.Atmos.EntitySystems;
using Content.Server.Disposal.Tube; using Content.Server.Disposal.Tube;
using Content.Server.Disposal.Tube.Components;
using Content.Server.Disposal.Unit.Components;
using Content.Shared.Body.Components; using Content.Shared.Body.Components;
using Content.Shared.Damage; using Content.Shared.Damage;
using Content.Shared.Disposal.Components;
using Content.Shared.Item; using Content.Shared.Item;
using Content.Shared.Throwing; using Content.Shared.Throwing;
using Robust.Shared.Audio.Systems; using Robust.Shared.Audio.Systems;
@@ -12,7 +11,7 @@ using Robust.Shared.Map.Components;
using Robust.Shared.Physics.Components; using Robust.Shared.Physics.Components;
using Robust.Shared.Physics.Systems; using Robust.Shared.Physics.Systems;
namespace Content.Server.Disposal.Unit.EntitySystems namespace Content.Server.Disposal.Unit
{ {
public sealed class DisposableSystem : EntitySystem public sealed class DisposableSystem : EntitySystem
{ {

View File

@@ -1,9 +1,8 @@
using Content.Server.Atmos; using Content.Server.Atmos;
using Content.Server.Disposal.Tube.Components;
using Content.Shared.Atmos; using Content.Shared.Atmos;
using Robust.Shared.Containers; using Robust.Shared.Containers;
namespace Content.Server.Disposal.Unit.Components namespace Content.Server.Disposal.Unit
{ {
[RegisterComponent] [RegisterComponent]
public sealed partial class DisposalHolderComponent : Component, IGasMixtureHolder public sealed partial class DisposalHolderComponent : Component, IGasMixtureHolder

View File

@@ -0,0 +1,44 @@
using Content.Server.Atmos.EntitySystems;
using Content.Shared.Atmos;
using Content.Shared.Destructible;
using Content.Shared.Disposal.Components;
using Content.Shared.Disposal.Unit;
using Content.Shared.Explosion;
namespace Content.Server.Disposal.Unit;
public sealed class DisposalUnitSystem : SharedDisposalUnitSystem
{
[Dependency] private readonly AtmosphereSystem _atmosSystem = default!;
public override void Initialize()
{
base.Initialize();
SubscribeLocalEvent<DisposalUnitComponent, DestructionEventArgs>(OnDestruction);
SubscribeLocalEvent<DisposalUnitComponent, BeforeExplodeEvent>(OnExploded);
}
protected override void HandleAir(EntityUid uid, DisposalUnitComponent component, TransformComponent xform)
{
var air = component.Air;
var indices = TransformSystem.GetGridTilePositionOrDefault((uid, xform));
if (_atmosSystem.GetTileMixture(xform.GridUid, xform.MapUid, indices, true) is { Temperature: > 0f } environment)
{
var transferMoles = 0.1f * (0.25f * Atmospherics.OneAtmosphere * 1.01f - air.Pressure) * air.Volume / (environment.Temperature * Atmospherics.R);
component.Air = environment.Remove(transferMoles);
}
}
private void OnDestruction(EntityUid uid, DisposalUnitComponent component, DestructionEventArgs args)
{
TryEjectContents(uid, component);
}
private void OnExploded(Entity<DisposalUnitComponent> ent, ref BeforeExplodeEvent args)
{
args.Contents.AddRange(ent.Comp.Container.ContainedEntities);
}
}

View File

@@ -1,4 +1,4 @@
namespace Content.Server.Disposal.Unit.EntitySystems namespace Content.Server.Disposal.Unit
{ {
public record DoInsertDisposalUnitEvent(EntityUid? User, EntityUid ToInsert, EntityUid Unit); public record DoInsertDisposalUnitEvent(EntityUid? User, EntityUid ToInsert, EntityUid Unit);
} }

View File

@@ -7,6 +7,7 @@ using Content.Shared.Fax;
using Content.Shared.Follower; using Content.Shared.Follower;
using Content.Shared.Ghost; using Content.Shared.Ghost;
using Content.Shared.Paper; using Content.Shared.Paper;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Fax.AdminUI; namespace Content.Server.Fax.AdminUI;

View File

@@ -1,8 +1,6 @@
using Content.Server.Administration; using Content.Server.Administration;
using Content.Server.Administration.Managers; using Content.Server.Administration.Managers;
using Content.Server.Chat.Managers; using Content.Server.Chat.Managers;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Popups; using Content.Server.Popups;
using Content.Server.Power.Components; using Content.Server.Power.Components;
@@ -12,7 +10,7 @@ using Content.Shared.Administration.Logs;
using Content.Shared.Containers.ItemSlots; using Content.Shared.Containers.ItemSlots;
using Content.Shared.Database; using Content.Shared.Database;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.Emag.Components; using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Emag.Systems; using Content.Shared.Emag.Systems;
using Content.Shared.Fax; using Content.Shared.Fax;
using Content.Shared.Fax.Systems; using Content.Shared.Fax.Systems;
@@ -27,9 +25,9 @@ using Robust.Shared.Audio;
using Robust.Shared.Audio.Systems; using Robust.Shared.Audio.Systems;
using Robust.Shared.Containers; using Robust.Shared.Containers;
using Robust.Shared.Player; using Robust.Shared.Player;
using Robust.Shared.Prototypes;
using Content.Shared.NameModifier.Components; using Content.Shared.NameModifier.Components;
using Content.Shared.Power; using Content.Shared.Power;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Fax; namespace Content.Server.Fax;

View File

@@ -19,6 +19,8 @@ using Robust.Shared.Timing;
using Robust.Shared.Audio.Systems; using Robust.Shared.Audio.Systems;
using Content.Shared.Damage.Systems; using Content.Shared.Damage.Systems;
using Content.Shared.Damage.Components; using Content.Shared.Damage.Components;
using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Power; using Content.Shared.Power;
namespace Content.Server.Light.EntitySystems namespace Content.Server.Light.EntitySystems

View File

@@ -2,6 +2,8 @@ using System.Linq;
using Content.Server.DeviceNetwork; using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.PowerCell; using Content.Server.PowerCell;
using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Medical.CrewMonitoring; using Content.Shared.Medical.CrewMonitoring;
using Content.Shared.Medical.SuitSensor; using Content.Shared.Medical.SuitSensor;
using Content.Shared.Pinpointer; using Content.Shared.Pinpointer;

View File

@@ -1,10 +1,10 @@
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Medical.SuitSensors; using Content.Server.Medical.SuitSensors;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Medical.SuitSensor; using Content.Shared.Medical.SuitSensor;
using Robust.Shared.Timing; using Robust.Shared.Timing;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Medical.CrewMonitoring; namespace Content.Server.Medical.CrewMonitoring;

View File

@@ -1,7 +1,5 @@
using System.Numerics; using System.Numerics;
using Content.Server.Access.Systems; using Content.Server.Access.Systems;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Emp; using Content.Server.Emp;
using Content.Server.Medical.CrewMonitoring; using Content.Server.Medical.CrewMonitoring;
@@ -26,6 +24,7 @@ using Robust.Shared.Map;
using Robust.Shared.Prototypes; using Robust.Shared.Prototypes;
using Robust.Shared.Random; using Robust.Shared.Random;
using Robust.Shared.Timing; using Robust.Shared.Timing;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.Medical.SuitSensors; namespace Content.Server.Medical.SuitSensors;

View File

@@ -2,27 +2,23 @@ using Content.Server.Access.Systems;
using Content.Server.AlertLevel; using Content.Server.AlertLevel;
using Content.Server.CartridgeLoader; using Content.Server.CartridgeLoader;
using Content.Server.Chat.Managers; using Content.Server.Chat.Managers;
using Content.Server.DeviceNetwork.Components;
using Content.Server.Instruments; using Content.Server.Instruments;
using Content.Server.Light.EntitySystems;
using Content.Server.PDA.Ringer; using Content.Server.PDA.Ringer;
using Content.Server.Station.Systems; using Content.Server.Station.Systems;
using Content.Server.Store.Components;
using Content.Server.Store.Systems; using Content.Server.Store.Systems;
using Content.Server.Traitor.Uplink; using Content.Server.Traitor.Uplink;
using Content.Shared.Access.Components; using Content.Shared.Access.Components;
using Content.Shared.CartridgeLoader; using Content.Shared.CartridgeLoader;
using Content.Shared.Chat; using Content.Shared.Chat;
using Content.Shared.Light; using Content.Shared.Light;
using Content.Shared.Light.Components;
using Content.Shared.Light.EntitySystems; using Content.Shared.Light.EntitySystems;
using Content.Shared.PDA; using Content.Shared.PDA;
using Content.Shared.Store.Components;
using Robust.Server.Containers; using Robust.Server.Containers;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;
using Robust.Shared.Containers; using Robust.Shared.Containers;
using Robust.Shared.Player; using Robust.Shared.Player;
using Robust.Shared.Utility; using Robust.Shared.Utility;
using Content.Shared.DeviceNetwork.Components;
namespace Content.Server.PDA namespace Content.Server.PDA
{ {

View File

@@ -15,7 +15,6 @@ namespace Content.Server.Power.EntitySystems
public sealed class PowerReceiverSystem : SharedPowerReceiverSystem public sealed class PowerReceiverSystem : SharedPowerReceiverSystem
{ {
[Dependency] private readonly IAdminManager _adminManager = default!; [Dependency] private readonly IAdminManager _adminManager = default!;
private EntityQuery<ApcPowerReceiverComponent> _recQuery; private EntityQuery<ApcPowerReceiverComponent> _recQuery;
private EntityQuery<ApcPowerProviderComponent> _provQuery; private EntityQuery<ApcPowerProviderComponent> _provQuery;

View File

@@ -9,6 +9,7 @@ using Content.Server.NodeContainer.Nodes;
using Content.Server.Power.Components; using Content.Server.Power.Components;
using Content.Shared.Atmos; using Content.Shared.Atmos;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
using Content.Shared.Examine; using Content.Shared.Examine;
using Content.Shared.Power; using Content.Shared.Power;
using Content.Shared.Power.EntitySystems; using Content.Shared.Power.EntitySystems;

View File

@@ -1,4 +1,3 @@
using Content.Server.DeviceNetwork.Components;
using Content.Server.Power.EntitySystems; using Content.Server.Power.EntitySystems;
using Content.Server.PowerCell; using Content.Server.PowerCell;
using Content.Shared.DeviceNetwork.Components; using Content.Shared.DeviceNetwork.Components;

View File

@@ -1,5 +1,4 @@
using Content.Server.Administration.Logs; using Content.Server.Administration.Logs;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Radio.EntitySystems; using Content.Server.Radio.EntitySystems;
using Content.Shared.Lock; using Content.Shared.Lock;
@@ -10,7 +9,7 @@ using Content.Shared.Robotics.Components;
using Content.Shared.Robotics.Systems; using Content.Shared.Robotics.Systems;
using Robust.Server.GameObjects; using Robust.Server.GameObjects;
using Robust.Shared.Timing; using Robust.Shared.Timing;
using System.Diagnostics.CodeAnalysis; using Content.Shared.DeviceNetwork.Events;
namespace Content.Server.Research.Systems; namespace Content.Server.Research.Systems;

View File

@@ -4,8 +4,6 @@ using Content.Server.AlertLevel;
using Content.Shared.CCVar; using Content.Shared.CCVar;
using Content.Server.Chat.Managers; using Content.Server.Chat.Managers;
using Content.Server.Chat.Systems; using Content.Server.Chat.Systems;
using Content.Server.DeviceNetwork;
using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.GameTicking; using Content.Server.GameTicking;
using Content.Server.Screens.Components; using Content.Server.Screens.Components;
@@ -21,6 +19,7 @@ using Robust.Shared.Configuration;
using Robust.Shared.Player; using Robust.Shared.Player;
using Robust.Shared.Prototypes; using Robust.Shared.Prototypes;
using Robust.Shared.Timing; using Robust.Shared.Timing;
using Content.Shared.DeviceNetwork.Components;
using Timer = Robust.Shared.Timing.Timer; using Timer = Robust.Shared.Timing.Timer;
namespace Content.Server.RoundEnd namespace Content.Server.RoundEnd

View File

@@ -2,6 +2,8 @@ using Content.Shared.TextScreen;
using Content.Server.Screens.Components; using Content.Server.Screens.Components;
using Content.Server.DeviceNetwork.Components; using Content.Server.DeviceNetwork.Components;
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Shared.DeviceNetwork.Components;
using Content.Shared.DeviceNetwork.Events;
using Robust.Shared.Timing; using Robust.Shared.Timing;
@@ -63,7 +65,7 @@ public sealed class ScreenSystem : EntitySystem
/// <summary> /// <summary>
/// Determines if/how a timer packet affects this screen. /// Determines if/how a timer packet affects this screen.
/// Currently there are 2 broadcast domains: Arrivals, and every other screen. /// Currently there are 2 broadcast domains: Arrivals, and every other screen.
/// Domain is determined by the <see cref="DeviceNetworkComponent.TransmitFrequencyId"/> on each timer. /// Domain is determined by the <see cref="Shared.DeviceNetwork.Components.DeviceNetworkComponent.TransmitFrequencyId"/> on each timer.
/// Each broadcast domain is divided into subnets. Screen MapUid determines subnet. /// Each broadcast domain is divided into subnets. Screen MapUid determines subnet.
/// Subnets are the shuttle, source, and dest. Source/dest change each jump. /// Subnets are the shuttle, source, and dest. Source/dest change each jump.
/// This is required to send different timers to the shuttle/terminal/station. /// This is required to send different timers to the shuttle/terminal/station.

View File

@@ -2,6 +2,7 @@
using Content.Server.DeviceNetwork.Systems; using Content.Server.DeviceNetwork.Systems;
using Content.Server.Power.Components; using Content.Server.Power.Components;
using Content.Shared.DeviceNetwork; using Content.Shared.DeviceNetwork;
using Content.Shared.DeviceNetwork.Events;
namespace Content.Server.SensorMonitoring; namespace Content.Server.SensorMonitoring;

Some files were not shown because too many files have changed in this diff Show More