diff --git a/Content.Client/Content.Client.csproj b/Content.Client/Content.Client.csproj
index 66e924d664..2a68133adb 100644
--- a/Content.Client/Content.Client.csproj
+++ b/Content.Client/Content.Client.csproj
@@ -75,6 +75,7 @@
+
diff --git a/Content.Client/EntryPoint.cs b/Content.Client/EntryPoint.cs
index 6b332a56ca..38542f363c 100644
--- a/Content.Client/EntryPoint.cs
+++ b/Content.Client/EntryPoint.cs
@@ -1,4 +1,5 @@
using Content.Client.GameObjects;
+using Content.Client.GameObjects.Components.Power;
using Content.Client.GameObjects.Components.Storage;
using Content.Client.Interfaces.GameObjects;
using SS14.Shared.ContentPack;
@@ -43,6 +44,7 @@ namespace Content.Client
factory.RegisterReference();
factory.Register();
factory.Register();
+ factory.Register();
}
}
}
diff --git a/Content.Client/GameObjects/Components/Power/PowerDebugTool.cs b/Content.Client/GameObjects/Components/Power/PowerDebugTool.cs
new file mode 100644
index 0000000000..6a4e50e4b8
--- /dev/null
+++ b/Content.Client/GameObjects/Components/Power/PowerDebugTool.cs
@@ -0,0 +1,28 @@
+using Content.Shared.GameObjects;
+using Content.Shared.GameObjects.Components.Power;
+using SS14.Client.UserInterface.Controls;
+using SS14.Client.UserInterface.CustomControls;
+using SS14.Shared.GameObjects;
+using SS14.Shared.Interfaces.GameObjects;
+using SS14.Shared.Interfaces.Network;
+
+namespace Content.Client.GameObjects.Components.Power
+{
+ public class PowerDebugTool : SharedPowerDebugTool
+ {
+ public override void HandleMessage(ComponentMessage message, INetChannel netChannel = null, IComponent component = null)
+ {
+ base.HandleMessage(message, netChannel, component);
+
+ switch (message)
+ {
+ case OpenDataWindowMsg msg:
+ var window = new SS14Window();
+ window.Contents.AddChild(new Label() { Text = msg.Data });
+ window.AddToScreen();
+ window.Open();
+ break;
+ }
+ }
+ }
+}
diff --git a/Content.Server/Content.Server.csproj b/Content.Server/Content.Server.csproj
index 378740744c..b229998a91 100644
--- a/Content.Server/Content.Server.csproj
+++ b/Content.Server/Content.Server.csproj
@@ -107,6 +107,8 @@
+
+
@@ -139,5 +141,4 @@
-
-
\ No newline at end of file
+
diff --git a/Content.Server/EntryPoint.cs b/Content.Server/EntryPoint.cs
index 9891a2d5a4..3d61d030e4 100644
--- a/Content.Server/EntryPoint.cs
+++ b/Content.Server/EntryPoint.cs
@@ -68,6 +68,7 @@ namespace Content.Server
//Power Components
factory.Register();
factory.Register();
+ factory.RegisterReference();
factory.Register();
factory.Register();
factory.Register();
@@ -87,6 +88,9 @@ namespace Content.Server
factory.Register();
factory.Register();
+
+ factory.Register();
+ factory.Register();
}
///
diff --git a/Content.Server/GameObjects/Components/Power/PowerDebugTool.cs b/Content.Server/GameObjects/Components/Power/PowerDebugTool.cs
new file mode 100644
index 0000000000..d205b85693
--- /dev/null
+++ b/Content.Server/GameObjects/Components/Power/PowerDebugTool.cs
@@ -0,0 +1,80 @@
+using System.Text;
+using Content.Server.GameObjects.EntitySystems;
+using Content.Shared.GameObjects.Components.Power;
+using SS14.Server.Interfaces.GameObjects;
+using SS14.Shared.GameObjects;
+using SS14.Shared.Interfaces.GameObjects;
+using SS14.Shared.Map;
+
+namespace Content.Server.GameObjects.Components.Power
+{
+ public class PowerDebugTool : SharedPowerDebugTool, IAfterAttack
+ {
+ void IAfterAttack.Afterattack(IEntity user, LocalCoordinates clicklocation, IEntity attacked)
+ {
+ if (attacked == null)
+ {
+ return;
+ }
+
+ var builder = new StringBuilder();
+
+ if (attacked.TryGetComponent(out var node))
+ {
+ builder.AppendFormat("Power Node:\n");
+ if (node.Parent == null)
+ {
+ builder.Append(" No Powernet!\n");
+ }
+ else
+ {
+ builder.AppendFormat(" Powernet: {0}\n", node.Parent.Uid);
+ }
+ }
+
+ if (attacked.TryGetComponent(out var device))
+ {
+ builder.AppendFormat(@"Power Device:
+ Load: {0} W
+ Priority: {1}
+ Drawtype: {2}, Connected: {3}
+ Powered: {4}
+", device.Load, device.Priority, device.DrawType, device.Connected, device.Powered);
+
+ if (device.Connected == DrawTypes.Provider || device.Connected == DrawTypes.Both)
+ {
+ builder.Append(" Providers:\n");
+ foreach (var provider in device.AvailableProviders)
+ {
+ var providerTransform = provider.Owner.GetComponent();
+ builder.AppendFormat(" {0} @ {1}", provider.Name, providerTransform.LocalPosition);
+ if (device.Provider == provider)
+ {
+ builder.Append(" (CURRENT)");
+ }
+ builder.Append('\n');
+ }
+ }
+ }
+
+ if (attacked.TryGetComponent(out var storage))
+ {
+ builder.AppendFormat(@"Power Storage:
+ Capacity: {0}, Charge: {1}, ChargeRate: {2}, DistributionRate: {3}, ChargePowernet: {4}
+", storage.Capacity, storage.Charge, storage.ChargeRate, storage.DistributionRate, storage.ChargePowernet);
+ }
+
+ OpenDataWindowClientSide(user, builder.ToString());
+ }
+
+ private void OpenDataWindowClientSide(IEntity user, string data)
+ {
+ if (!user.TryGetComponent(out var actor))
+ {
+ return;
+ }
+
+ SendNetworkMessage(new OpenDataWindowMsg(data), actor.playerSession.ConnectedClient);
+ }
+ }
+}
diff --git a/Content.Server/GameObjects/Components/Power/PowerDevice.cs b/Content.Server/GameObjects/Components/Power/PowerDevice.cs
index f419b31616..7df5f041d6 100644
--- a/Content.Server/GameObjects/Components/Power/PowerDevice.cs
+++ b/Content.Server/GameObjects/Components/Power/PowerDevice.cs
@@ -4,6 +4,7 @@ using SS14.Shared.GameObjects;
using SS14.Shared.Interfaces.GameObjects;
using SS14.Shared.IoC;
using SS14.Shared.Utility;
+using System;
using System.Collections.Generic;
using System.Linq;
using YamlDotNet.RepresentationModel;
@@ -18,24 +19,45 @@ namespace Content.Server.GameObjects.Components.Power
public override string Name => "PowerDevice";
///
- /// The method of draw we will try to use to place our load set via component parameter, defaults to using power providers
+ /// The method of draw we will try to use to place our load set via component parameter, defaults to using power providers
///
- public virtual DrawTypes Drawtype { get; protected set; } = DrawTypes.Provider;
+ public virtual DrawTypes DrawType { get; protected set; } = DrawTypes.Provider;
///
- /// The power draw method we are currently connected to and using
+ /// The power draw method we are currently connected to and using
///
public DrawTypes Connected { get; protected set; } = DrawTypes.None;
- public bool _powered = false;
+ public bool Powered { get; private set; } = false;
+
+
///
- /// Status indicator variable for powered
+ /// Is an external power source currently available?
///
- public virtual bool Powered
+ public bool ExternalPowered
{
- get => _powered;
- set => SetPowered(value);
+ get => _externalPowered;
+ set
+ {
+ _externalPowered = value;
+ UpdatePowered();
+ }
}
+ private bool _externalPowered = false;
+
+ ///
+ /// Is an internal power source currently available?
+ ///
+ public bool InternalPowered
+ {
+ get => _internalPowered;
+ set
+ {
+ _internalPowered = value;
+ UpdatePowered();
+ }
+ }
+ private bool _internalPowered = false;
///
/// Priority for powernet draw, lower will draw first, defined in powernet.cs
@@ -50,7 +72,7 @@ namespace Content.Server.GameObjects.Components.Power
public float Load
{
get => _load;
- set { UpdateLoad(value); }
+ set => UpdateLoad(value);
}
///
@@ -60,20 +82,22 @@ namespace Content.Server.GameObjects.Components.Power
private PowerProviderComponent _provider;
+
///
/// A power provider that will handle our load, if we are linked to any
///
public PowerProviderComponent Provider
{
get => _provider;
- set {
+ set
+ {
Connected = DrawTypes.Provider;
if (_provider != null)
{
_provider.RemoveDevice(this);
}
- if(value != null)
+ if (value != null)
{
_provider = value;
_provider.AddDevice(this);
@@ -85,11 +109,13 @@ namespace Content.Server.GameObjects.Components.Power
}
}
+ public event EventHandler OnPowerStateChanged;
+
public override void OnAdd()
{
base.OnAdd();
- if (Drawtype == DrawTypes.Both || Drawtype == DrawTypes.Node)
+ if (DrawType == DrawTypes.Node || DrawType == DrawTypes.Both)
{
if (!Owner.TryGetComponent(out PowerNodeComponent node))
{
@@ -106,7 +132,7 @@ namespace Content.Server.GameObjects.Components.Power
{
if (Owner.TryGetComponent(out PowerNodeComponent node))
{
- if(node.Parent != null)
+ if (node.Parent != null)
{
node.Parent.RemoveDevice(this);
}
@@ -123,7 +149,7 @@ namespace Content.Server.GameObjects.Components.Power
{
if (mapping.TryGetNode("Drawtype", out YamlNode node))
{
- Drawtype = node.AsEnum();
+ DrawType = node.AsEnum();
}
if (mapping.TryGetNode("Load", out node))
{
@@ -137,7 +163,7 @@ namespace Content.Server.GameObjects.Components.Power
string IExamine.Examine()
{
- if(!Powered)
+ if (!Powered)
{
return "The device is not powered";
}
@@ -148,44 +174,32 @@ namespace Content.Server.GameObjects.Components.Power
{
var oldLoad = _load;
_load = value;
- if(Connected == DrawTypes.Node)
+ if (Connected == DrawTypes.Node)
{
var node = Owner.GetComponent();
node.Parent.UpdateDevice(this, oldLoad);
}
- else if(Connected == DrawTypes.Provider)
+ else if (Connected == DrawTypes.Provider)
{
Provider.UpdateDevice(this, oldLoad);
}
}
- ///
- /// Changes behavior when receiving a command to become powered or depowered
- ///
- ///
- public virtual void SetPowered(bool value)
+ private void UpdatePowered()
{
- //Let them set us to true
- if (value == true)
+ var oldPowered = Powered;
+ Powered = ExternalPowered || InternalPowered;
+ if (oldPowered != Powered)
{
- _powered = true;
- return;
- }
-
- //A powernet has decided we will not be powered this tick, lets try to power ourselves
- if (value == false && Owner.TryGetComponent(out PowerStorageComponent storage))
- {
- if (storage.CanDeductCharge(Load))
+ if (Powered)
{
- storage.DeductCharge(Load);
- _powered = true;
- return;
+ OnPowerStateChanged?.Invoke(this, new PowerStateEventArgs(true));
+ }
+ else
+ {
+ OnPowerStateChanged?.Invoke(this, new PowerStateEventArgs(false));
}
}
-
- //For some reason above we could not power ourselves, we depower
- _powered = false;
- return;
}
///
@@ -196,7 +210,7 @@ namespace Content.Server.GameObjects.Components.Power
{
AvailableProviders.Add(provider);
- if(Connected != DrawTypes.Node)
+ if (Connected != DrawTypes.Node)
{
ConnectToBestProvider();
}
@@ -234,7 +248,7 @@ namespace Content.Server.GameObjects.Components.Power
}
}
- if(Provider != bestprovider)
+ if (Provider != bestprovider)
Provider = bestprovider;
}
@@ -246,9 +260,15 @@ namespace Content.Server.GameObjects.Components.Power
{
if (!AvailableProviders.Contains(provider))
return;
-
+
AvailableProviders.Remove(provider);
+ if (provider == Provider)
+ {
+ Provider = null;
+ ExternalPowered = false;
+ }
+
if (Connected != DrawTypes.Node)
{
ConnectToBestProvider();
@@ -260,7 +280,7 @@ namespace Content.Server.GameObjects.Components.Power
///
///
///
- private void PowernetConnect(object sender, PowernetEventArgs eventarg)
+ protected virtual void PowernetConnect(object sender, PowernetEventArgs eventarg)
{
//This sets connected = none so it must be first
Provider = null;
@@ -274,7 +294,7 @@ namespace Content.Server.GameObjects.Components.Power
///
///
///
- private void PowernetRegenerate(object sender, PowernetEventArgs eventarg)
+ protected virtual void PowernetRegenerate(object sender, PowernetEventArgs eventarg)
{
eventarg.Powernet.AddDevice(this);
}
@@ -284,13 +304,31 @@ namespace Content.Server.GameObjects.Components.Power
///
///
///
- private void PowernetDisconnect(object sender, PowernetEventArgs eventarg)
+ protected virtual void PowernetDisconnect(object sender, PowernetEventArgs eventarg)
{
eventarg.Powernet.RemoveDevice(this);
Connected = DrawTypes.None;
ConnectToBestProvider();
}
+
+ internal virtual void ProcessInternalPower(float frametime)
+ {
+ if (Owner.TryGetComponent(out var storage) && storage.CanDeductCharge(Load))
+ {
+ // We still keep InternalPowered correct if connected externally,
+ // but don't use it.
+ if (!ExternalPowered)
+ {
+ storage.DeductCharge(Load);
+ }
+ InternalPowered = true;
+ }
+ else
+ {
+ InternalPowered = false;
+ }
+ }
}
public enum DrawTypes
@@ -298,6 +336,16 @@ namespace Content.Server.GameObjects.Components.Power
None = 0,
Node = 1,
Provider = 2,
- Both = 3
+ Both = 3,
+ }
+
+ public class PowerStateEventArgs : EventArgs
+ {
+ public readonly bool Powered;
+
+ public PowerStateEventArgs(bool powered)
+ {
+ Powered = powered;
+ }
}
}
diff --git a/Content.Server/GameObjects/Components/Power/PowerNodeComponent.cs b/Content.Server/GameObjects/Components/Power/PowerNodeComponent.cs
index a549c84d6a..7e51d77a52 100644
--- a/Content.Server/GameObjects/Components/Power/PowerNodeComponent.cs
+++ b/Content.Server/GameObjects/Components/Power/PowerNodeComponent.cs
@@ -13,7 +13,7 @@ namespace Content.Server.GameObjects.Components.Power
public class PowerNodeComponent : Component
{
public override string Name => "PowerNode";
-
+
///
/// The powernet this node is connected to
///
@@ -57,7 +57,7 @@ namespace Content.Server.GameObjects.Components.Power
.Where(x => x.HasComponent())
.OrderByDescending(x => (x.GetComponent().WorldPosition - position).Length);
var choose = wires.FirstOrDefault();
- if(choose != null)
+ if (choose != null)
ConnectToPowernet(choose.GetComponent().Parent);
}
@@ -68,7 +68,7 @@ namespace Content.Server.GameObjects.Components.Power
public void ConnectToPowernet(Powernet toconnect)
{
Parent = toconnect;
- Parent.Nodelist.Add(this);
+ Parent.NodeList.Add(this);
OnPowernetConnect?.Invoke(this, new PowernetEventArgs(Parent));
}
@@ -79,10 +79,10 @@ namespace Content.Server.GameObjects.Components.Power
public void RegeneratePowernet(Powernet toconnect)
{
//This removes the device from things that will be powernet disconnected when dirty powernet is killed
- Parent.Nodelist.Remove(this);
+ Parent.NodeList.Remove(this);
Parent = toconnect;
- Parent.Nodelist.Add(this);
+ Parent.NodeList.Add(this);
OnPowernetRegenerate?.Invoke(this, new PowernetEventArgs(Parent));
}
@@ -91,7 +91,11 @@ namespace Content.Server.GameObjects.Components.Power
///
public void DisconnectFromPowernet()
{
- Parent.Nodelist.Remove(this);
+ if (Parent == null)
+ {
+ return;
+ }
+ Parent.NodeList.Remove(this);
OnPowernetDisconnect?.Invoke(this, new PowernetEventArgs(Parent));
Parent = null;
}
diff --git a/Content.Server/GameObjects/Components/Power/PowerProviderComponent.cs b/Content.Server/GameObjects/Components/Power/PowerProviderComponent.cs
index 332cc5b1a6..af5c810612 100644
--- a/Content.Server/GameObjects/Components/Power/PowerProviderComponent.cs
+++ b/Content.Server/GameObjects/Components/Power/PowerProviderComponent.cs
@@ -19,7 +19,7 @@ namespace Content.Server.GameObjects.Components.Power
public override string Name => "PowerProvider";
///
- public override DrawTypes Drawtype { get; protected set; } = DrawTypes.Node;
+ public override DrawTypes DrawType { get; protected set; } = DrawTypes.Node;
///
/// Variable that determines the range that the power provider will try to supply power to
@@ -29,12 +29,22 @@ namespace Content.Server.GameObjects.Components.Power
///
/// List storing all the power devices that we are currently providing power to
///
- public SortedSet Deviceloadlist = new SortedSet(new Powernet.DevicePriorityCompare());
+ public SortedSet DeviceLoadList = new SortedSet(new Powernet.DevicePriorityCompare());
public List DepoweredDevices = new List();
public override Powernet.Priority Priority { get; protected set; } = Powernet.Priority.Provider;
+ public override void OnRemove()
+ {
+ base.OnRemove();
+
+ foreach (var device in DeviceLoadList)
+ {
+ device.RemoveProvider(this);
+ }
+ }
+
public override void LoadParameters(YamlMappingNode mapping)
{
if (mapping.TryGetNode("Range", out YamlNode node))
@@ -47,78 +57,71 @@ namespace Content.Server.GameObjects.Components.Power
}
}
- ///
- public override void SetPowered(bool value)
+ internal override void ProcessInternalPower(float frametime)
{
- //Let them set us true, we must now power all the devices that rely on us for energy
- if (value == true)
+ // Right now let's just assume that APCs don't have a power demand themselves and as such they're always marked as powered.
+ InternalPowered = true;
+ if (!Owner.TryGetComponent(out var storage))
+ {
+ return;
+ }
+
+ if (ExternalPowered)
{
PowerAllDevices();
return;
}
- //A powernet has decided we will not be powered this tick, lets try to power ourselves
- if (value == false && Owner.TryGetComponent(out PowerStorageComponent storage))
+ if (storage.CanDeductCharge(Load))
{
- //Can the storage cover powering all our devices and us? If so power all
- if (storage.CanDeductCharge(Load))
+ PowerAllDevices();
+ storage.DeductCharge(Load);
+ return;
+ }
+
+ var remainingLoad = storage.AvailableCharge();
+ var usedLoad = 0f;
+ foreach (var device in DeviceLoadList)
+ {
+ if (device.Load > remainingLoad)
{
- storage.DeductCharge(Load);
- _powered = true;
- return;
+ device.ExternalPowered = false;
+ DepoweredDevices.Add(device);
}
- //Does the storage even have any power to give us? If so power as much as we can
- else if (storage.RequestAllCharge() != 0)
+ else
{
- var depowervalue = storage.RequestAllCharge() - Load;
- _powered = true;
- //See code in powernet for same functionality
- foreach (var device in Deviceloadlist)
+ if (!device.ExternalPowered)
{
- device.Powered = false;
- DepoweredDevices.Add(device);
- depowervalue -= device.Load;
- if (depowervalue < 0)
- break;
+ device.ExternalPowered = true;
+ DepoweredDevices.Remove(device);
}
- return;
- }
- //Storage doesn't have anything, depower everything
- else if (storage.RequestAllCharge() == 0)
- {
- DepowerAllDevices();
- return;
+ usedLoad += device.Load;
+ remainingLoad -= device.Load;
}
}
- //For some reason above we could not power ourselves, we depower ourselves and all devices
- DepowerAllDevices();
- return;
+ storage.DeductCharge(usedLoad);
}
-
private void PowerAllDevices()
{
- _powered = true;
foreach (var device in DepoweredDevices)
{
- device.Powered = true;
+ device.ExternalPowered = true;
}
DepoweredDevices.Clear();
}
private void DepowerAllDevices()
{
- _powered = false;
- foreach (var device in DepoweredDevices)
+ foreach (var device in DeviceLoadList)
{
- device.Powered = false;
+ device.ExternalPowered = false;
}
}
- private void PowernetConnect(object sender, PowernetEventArgs eventarg)
+ protected override void PowernetConnect(object sender, PowernetEventArgs eventarg)
{
- eventarg.Powernet.AddDevice(this);
- Connected = DrawTypes.Node;
+ base.PowernetConnect(sender, eventarg);
//Find devices within range to take under our control
var _emanager = IoCManager.Resolve();
@@ -132,25 +135,20 @@ namespace Content.Server.GameObjects.Components.Power
var device = entity.GetComponent();
//Make sure the device can accept power providers to give it power
- if (device.Drawtype == DrawTypes.Provider || device.Drawtype == DrawTypes.Both)
+ if (device.DrawType == DrawTypes.Provider || device.DrawType == DrawTypes.Both)
{
device.AddProvider(this);
}
}
}
- private void PowernetRegenerate(object sender, PowernetEventArgs eventarg)
- {
- eventarg.Powernet.AddDevice(this);
- }
- private void PowernetDisconnect(object sender, PowernetEventArgs eventarg)
+ protected override void PowernetDisconnect(object sender, PowernetEventArgs eventarg)
{
- eventarg.Powernet.RemoveDevice(this);
- Connected = DrawTypes.None;
+ base.PowernetDisconnect(sender, eventarg);
//We don't want to make the devices under us think we're still a valid provider if we have no powernet to connect to
- foreach (var device in Deviceloadlist)
+ foreach (var device in DeviceLoadList.ToList())
{
device.RemoveProvider(this);
}
@@ -161,7 +159,7 @@ namespace Content.Server.GameObjects.Components.Power
///
public void AddDevice(PowerDeviceComponent device)
{
- Deviceloadlist.Add(device);
+ DeviceLoadList.Add(device);
Load += device.Load;
if (!device.Powered)
DepoweredDevices.Add(device);
@@ -172,7 +170,7 @@ namespace Content.Server.GameObjects.Components.Power
///
public void UpdateDevice(PowerDeviceComponent device, float oldLoad)
{
- if (Deviceloadlist.Contains(device))
+ if (DeviceLoadList.Contains(device))
{
Load -= oldLoad;
Load += device.Load;
@@ -184,10 +182,10 @@ namespace Content.Server.GameObjects.Components.Power
///
public void RemoveDevice(PowerDeviceComponent device)
{
- if (Deviceloadlist.Contains(device))
+ if (DeviceLoadList.Contains(device))
{
Load -= device.Load;
- Deviceloadlist.Remove(device);
+ DeviceLoadList.Remove(device);
if (DepoweredDevices.Contains(device))
DepoweredDevices.Remove(device);
}
diff --git a/Content.Server/GameObjects/Components/Power/PowerStorageComponent.cs b/Content.Server/GameObjects/Components/Power/PowerStorageComponent.cs
index 903e3d3669..2236351173 100644
--- a/Content.Server/GameObjects/Components/Power/PowerStorageComponent.cs
+++ b/Content.Server/GameObjects/Components/Power/PowerStorageComponent.cs
@@ -33,7 +33,7 @@ namespace Content.Server.GameObjects.Components.Power
/// Rate at which energy will be distributed to the powernet if needed
///
public float DistributionRate { get; private set; } = 1000;
-
+
private bool _chargepowernet = false;
///
@@ -156,7 +156,7 @@ namespace Content.Server.GameObjects.Components.Power
///
public void ChargePowerTick()
{
- Charge = Math.Max(Charge + ChargeRate, Capacity);
+ Charge = Math.Min(Charge + ChargeRate, Capacity);
}
///
diff --git a/Content.Server/GameObjects/Components/Power/PowerTransferComponent.cs b/Content.Server/GameObjects/Components/Power/PowerTransferComponent.cs
index 6e54451ffa..877c68b516 100644
--- a/Content.Server/GameObjects/Components/Power/PowerTransferComponent.cs
+++ b/Content.Server/GameObjects/Components/Power/PowerTransferComponent.cs
@@ -25,7 +25,7 @@ namespace Content.Server.GameObjects.Components.Power
public override void Initialize()
{
- if(Parent == null)
+ if (Parent == null)
{
SpreadPowernet();
}
@@ -49,7 +49,7 @@ namespace Content.Server.GameObjects.Components.Power
.Where(x => x.HasComponent());
//we have no parent so lets find a partner we can join his powernet
- if(Parent == null || Regenerating)
+ if (Parent == null || Regenerating)
{
foreach (var wire in wires)
{
@@ -74,13 +74,13 @@ namespace Content.Server.GameObjects.Components.Power
.Where(x => x.HasComponent())
.Select(x => x.GetComponent());
- foreach(var node in nodes)
+ foreach (var node in nodes)
{
- if(node.Parent == null)
+ if (node.Parent == null)
{
node.ConnectToPowernet(Parent);
}
- else if(node.Parent.Dirty)
+ else if (node.Parent.Dirty)
{
node.RegeneratePowernet(Parent);
}
@@ -95,7 +95,7 @@ namespace Content.Server.GameObjects.Components.Power
ptc.ConnectToPowernet(Parent);
SpreadPowernet();
}
- else if(ptc.Parent != Parent && !ptc.Parent.Dirty)
+ else if (ptc.Parent != Parent && !ptc.Parent.Dirty)
{
Parent.MergePowernets(ptc.Parent);
}
@@ -109,7 +109,7 @@ namespace Content.Server.GameObjects.Components.Power
public void ConnectToPowernet(Powernet toconnect)
{
Parent = toconnect;
- Parent.Wirelist.Add(this);
+ Parent.WireList.Add(this);
Regenerating = false;
}
@@ -118,7 +118,7 @@ namespace Content.Server.GameObjects.Components.Power
///
public void DisconnectFromPowernet()
{
- Parent.Wirelist.Remove(this);
+ Parent.WireList.Remove(this);
Parent.Dirty = true;
Parent = null;
}
@@ -131,7 +131,7 @@ namespace Content.Server.GameObjects.Components.Power
public bool Attackby(IEntity user, IEntity attackwith)
{
- if(attackwith.TryGetComponent(out WirecutterComponent wirecutter))
+ if (attackwith.TryGetComponent(out WirecutterComponent wirecutter))
{
Owner.Delete();
return true;
diff --git a/Content.Server/GameObjects/Components/Power/PoweredLightComponent.cs b/Content.Server/GameObjects/Components/Power/PoweredLightComponent.cs
new file mode 100644
index 0000000000..c2635b27dd
--- /dev/null
+++ b/Content.Server/GameObjects/Components/Power/PoweredLightComponent.cs
@@ -0,0 +1,33 @@
+using SS14.Server.GameObjects;
+using SS14.Shared.Enums;
+using SS14.Shared.GameObjects;
+
+namespace Content.Server.GameObjects.Components.Power
+{
+ public class PoweredLightComponent : Component
+ {
+ public override string Name => "PoweredLight";
+
+ public override void Initialize()
+ {
+ base.Initialize();
+
+ var device = Owner.GetComponent();
+ var sprite = Owner.GetComponent();
+ var light = Owner.GetComponent();
+ device.OnPowerStateChanged += (sender, args) =>
+ {
+ if (args.Powered)
+ {
+ sprite.LayerSetTexture(0, "Objects/wall_light.png");
+ light.State = LightState.On;
+ }
+ else
+ {
+ sprite.LayerSetTexture(0, "Objects/wall_light_off.png");
+ light.State = LightState.Off;
+ }
+ };
+ }
+ }
+}
diff --git a/Content.Server/GameObjects/Components/Power/Powernet.cs b/Content.Server/GameObjects/Components/Power/Powernet.cs
index b2e8114c69..7a1f429ec7 100644
--- a/Content.Server/GameObjects/Components/Power/Powernet.cs
+++ b/Content.Server/GameObjects/Components/Power/Powernet.cs
@@ -15,28 +15,32 @@ namespace Content.Server.GameObjects.Components.Power
public Powernet()
{
var EntitySystemManager = IoCManager.Resolve();
- EntitySystemManager.GetEntitySystem().Powernets.Add(this);
+ var powerSystem = EntitySystemManager.GetEntitySystem();
+ powerSystem.Powernets.Add(this);
+ Uid = powerSystem.NewUid();
}
+ public int Uid { get; }
+
///
/// The entities that make up the powernet's physical location and allow powernet connection
///
- public List Wirelist { get; set; } = new List();
+ public List WireList { get; set; } = new List();
///
/// Entities that connect directly to the powernet through PTC above to add power or add power load
///
- public List Nodelist { get; set; } = new List();
+ public List NodeList { get; set; } = new List();
///
/// Subset of nodelist that adds a continuous power supply to the network
///
- public Dictionary Generatorlist { get; set; } = new Dictionary();
+ public Dictionary GeneratorList { get; set; } = new Dictionary();
///
/// Subset of nodelist that draw power, stores information on current continuous powernet load
///
- public SortedSet Deviceloadlist { get; set; } = new SortedSet(new DevicePriorityCompare());
+ public SortedSet DeviceLoadList { get; set; } = new SortedSet(new DevicePriorityCompare());
///
/// Comparer that keeps the device dictionary sorted by powernet priority
@@ -156,9 +160,9 @@ namespace Content.Server.GameObjects.Components.Power
var depowervalue = activeload - (activesupply + passivesupply);
//Providers use same method to recreate functionality
- foreach (var device in Deviceloadlist)
+ foreach (var device in DeviceLoadList)
{
- device.Powered = false;
+ device.ExternalPowered = false;
DepoweredDevices.Add(device);
depowervalue -= device.Load;
if (depowervalue < 0)
@@ -171,7 +175,7 @@ namespace Content.Server.GameObjects.Components.Power
{
foreach (var device in DepoweredDevices)
{
- device.Powered = true;
+ device.ExternalPowered = true;
}
DepoweredDevices.Clear();
}
@@ -205,13 +209,13 @@ namespace Content.Server.GameObjects.Components.Power
///
public void DirtyKill()
{
- Wirelist.Clear();
- while (Nodelist.Count != 0)
+ WireList.Clear();
+ while (NodeList.Count != 0)
{
- Nodelist[0].DisconnectFromPowernet();
+ NodeList[0].DisconnectFromPowernet();
}
- Generatorlist.Clear();
- Deviceloadlist.Clear();
+ GeneratorList.Clear();
+ DeviceLoadList.Clear();
DepoweredDevices.Clear();
PowerStorageSupplierlist.Clear();
PowerStorageConsumerlist.Clear();
@@ -226,31 +230,31 @@ namespace Content.Server.GameObjects.Components.Power
{
//TODO: load balance reconciliation between powernets on merge tick here
- foreach (var wire in toMerge.Wirelist)
+ foreach (var wire in toMerge.WireList)
{
wire.Parent = this;
}
- Wirelist.AddRange(toMerge.Wirelist);
- toMerge.Wirelist.Clear();
+ WireList.AddRange(toMerge.WireList);
+ toMerge.WireList.Clear();
- foreach (var node in toMerge.Nodelist)
+ foreach (var node in toMerge.NodeList)
{
node.Parent = this;
}
- Nodelist.AddRange(toMerge.Nodelist);
- toMerge.Nodelist.Clear();
+ NodeList.AddRange(toMerge.NodeList);
+ toMerge.NodeList.Clear();
- foreach (var generator in toMerge.Generatorlist)
+ foreach (var generator in toMerge.GeneratorList)
{
- Generatorlist.Add(generator.Key, generator.Value);
+ GeneratorList.Add(generator.Key, generator.Value);
}
- toMerge.Generatorlist.Clear();
+ toMerge.GeneratorList.Clear();
- foreach (var device in toMerge.Deviceloadlist)
+ foreach (var device in toMerge.DeviceLoadList)
{
- Deviceloadlist.Add(device);
+ DeviceLoadList.Add(device);
}
- toMerge.Deviceloadlist.Clear();
+ toMerge.DeviceLoadList.Clear();
DepoweredDevices.AddRange(toMerge.DepoweredDevices);
toMerge.DepoweredDevices.Clear();
@@ -280,7 +284,7 @@ namespace Content.Server.GameObjects.Components.Power
///
public void AddDevice(PowerDeviceComponent device)
{
- Deviceloadlist.Add(device);
+ DeviceLoadList.Add(device);
Load += device.Load;
if (!device.Powered)
DepoweredDevices.Add(device);
@@ -291,7 +295,7 @@ namespace Content.Server.GameObjects.Components.Power
///
public void UpdateDevice(PowerDeviceComponent device, float oldLoad)
{
- if (Deviceloadlist.Contains(device))
+ if (DeviceLoadList.Contains(device))
{
Load -= oldLoad;
Load += device.Load;
@@ -303,10 +307,10 @@ namespace Content.Server.GameObjects.Components.Power
///
public void RemoveDevice(PowerDeviceComponent device)
{
- if (Deviceloadlist.Contains(device))
+ if (DeviceLoadList.Contains(device))
{
Load -= device.Load;
- Deviceloadlist.Remove(device);
+ DeviceLoadList.Remove(device);
if (DepoweredDevices.Contains(device))
DepoweredDevices.Remove(device);
}
@@ -322,7 +326,7 @@ namespace Content.Server.GameObjects.Components.Power
///
public void AddGenerator(PowerGeneratorComponent generator)
{
- Generatorlist.Add(generator, generator.Supply);
+ GeneratorList.Add(generator, generator.Supply);
Supply += generator.Supply;
}
@@ -331,10 +335,10 @@ namespace Content.Server.GameObjects.Components.Power
///
public void UpdateGenerator(PowerGeneratorComponent generator)
{
- if (Generatorlist.ContainsKey(generator))
+ if (GeneratorList.ContainsKey(generator))
{
- Supply -= Generatorlist[generator];
- Generatorlist[generator] = generator.Supply;
+ Supply -= GeneratorList[generator];
+ GeneratorList[generator] = generator.Supply;
Supply += generator.Supply;
}
}
@@ -344,10 +348,10 @@ namespace Content.Server.GameObjects.Components.Power
///
public void RemoveGenerator(PowerGeneratorComponent generator)
{
- if (Generatorlist.ContainsKey(generator))
+ if (GeneratorList.ContainsKey(generator))
{
- Supply -= Generatorlist[generator];
- Generatorlist.Remove(generator);
+ Supply -= GeneratorList[generator];
+ GeneratorList.Remove(generator);
}
else
{
diff --git a/Content.Server/GameObjects/Components/Weapon/Melee/MeleeWeaponComponent.cs b/Content.Server/GameObjects/Components/Weapon/Melee/MeleeWeaponComponent.cs
index a8a8307aa9..cf9cfb1abf 100644
--- a/Content.Server/GameObjects/Components/Weapon/Melee/MeleeWeaponComponent.cs
+++ b/Content.Server/GameObjects/Components/Weapon/Melee/MeleeWeaponComponent.cs
@@ -31,18 +31,18 @@ namespace Content.Server.GameObjects.Components.Weapon.Melee
}
- void IAfterAttack.Afterattack(IEntity user, LocalCoordinates clicklocation)
+ void IAfterAttack.Afterattack(IEntity user, LocalCoordinates clicklocation, IEntity attacked)
{
var location = user.GetComponent().LocalPosition;
var angle = new Angle(clicklocation.ToWorld().Position - location.ToWorld().Position);
var entities = IoCManager.Resolve().GetEntitiesInArc(user.GetComponent().LocalPosition, Range, angle, ArcWidth);
- foreach(var entity in entities)
+ foreach (var entity in entities)
{
if (!entity.GetComponent().IsMapTransform || entity == user)
continue;
-
- if(entity.TryGetComponent(out DamageableComponent damagecomponent))
+
+ if (entity.TryGetComponent(out DamageableComponent damagecomponent))
{
damagecomponent.TakeDamage(DamageType.Brute, Damage);
}
diff --git a/Content.Server/GameObjects/Components/Weapon/Ranged/RangedWeapon.cs b/Content.Server/GameObjects/Components/Weapon/Ranged/RangedWeapon.cs
index d9aae20c2e..3edad9c967 100644
--- a/Content.Server/GameObjects/Components/Weapon/Ranged/RangedWeapon.cs
+++ b/Content.Server/GameObjects/Components/Weapon/Ranged/RangedWeapon.cs
@@ -9,9 +9,9 @@ namespace Content.Server.GameObjects.Components.Weapon.Ranged
{
public override string Name => "RangedWeapon";
- void IAfterAttack.Afterattack(IEntity user, LocalCoordinates clicklocation)
+ void IAfterAttack.Afterattack(IEntity user, LocalCoordinates clicklocation, IEntity attacked)
{
- if(UserCanFire(user) && WeaponCanFire())
+ if (UserCanFire(user) && WeaponCanFire())
{
Fire(user, clicklocation);
}
diff --git a/Content.Server/GameObjects/EntitySystems/Click/InteractionSystem.cs b/Content.Server/GameObjects/EntitySystems/Click/InteractionSystem.cs
index a48ed41659..7b6dce0985 100644
--- a/Content.Server/GameObjects/EntitySystems/Click/InteractionSystem.cs
+++ b/Content.Server/GameObjects/EntitySystems/Click/InteractionSystem.cs
@@ -65,7 +65,8 @@ namespace Content.Server.GameObjects.EntitySystems
///
///
///
- void Afterattack(IEntity user, LocalCoordinates clicklocation);
+ /// The entity that was clicked on out of range. May be null if no entity was clicked on.true
+ void Afterattack(IEntity user, LocalCoordinates clicklocation, IEntity attacked);
}
///
@@ -198,7 +199,7 @@ namespace Content.Server.GameObjects.EntitySystems
for (var i = 0; i < afterattacks.Count; i++)
{
- afterattacks[i].Afterattack(user, clicklocation);
+ afterattacks[i].Afterattack(user, clicklocation, null);
}
}
@@ -229,7 +230,7 @@ namespace Content.Server.GameObjects.EntitySystems
for (var i = 0; i < afterattacks.Count; i++)
{
- afterattacks[i].Afterattack(user, clicklocation);
+ afterattacks[i].Afterattack(user, clicklocation, attacked);
}
}
@@ -315,7 +316,7 @@ namespace Content.Server.GameObjects.EntitySystems
//See if we have a ranged attack interaction
for (var i = 0; i < afterattacks.Count; i++)
{
- afterattacks[i].Afterattack(user, clicklocation);
+ afterattacks[i].Afterattack(user, clicklocation, attacked);
}
}
}
diff --git a/Content.Server/GameObjects/EntitySystems/PowerSystem.cs b/Content.Server/GameObjects/EntitySystems/PowerSystem.cs
index f7af4d77e7..7de5fab966 100644
--- a/Content.Server/GameObjects/EntitySystems/PowerSystem.cs
+++ b/Content.Server/GameObjects/EntitySystems/PowerSystem.cs
@@ -1,5 +1,7 @@
using Content.Server.GameObjects.Components.Power;
using SS14.Shared.GameObjects.System;
+using SS14.Shared.Interfaces.GameObjects;
+using SS14.Shared.IoC;
using System;
using System.Collections.Generic;
using System.Linq;
@@ -12,6 +14,21 @@ namespace Content.Shared.GameObjects.EntitySystems
{
public List Powernets = new List();
+ private IComponentManager componentManager;
+
+ private int _lastUid = 0;
+
+ public override void Initialize()
+ {
+ base.Initialize();
+ componentManager = IoCManager.Resolve();
+ }
+
+ public int NewUid()
+ {
+ return ++_lastUid;
+ }
+
public override void Update(float frametime)
{
for (int i = 0; i < Powernets.Count; i++)
@@ -20,12 +37,12 @@ namespace Content.Shared.GameObjects.EntitySystems
if (powernet.Dirty)
{
//Tell all the wires of this net to be prepared to create/join new powernets
- foreach (var wire in powernet.Wirelist)
+ foreach (var wire in powernet.WireList)
{
wire.Regenerating = true;
}
- foreach (var wire in powernet.Wirelist)
+ foreach (var wire in powernet.WireList)
{
//Only a few wires should pass this if check since each will create and take all the others into its powernet
if (wire.Regenerating)
@@ -38,10 +55,16 @@ namespace Content.Shared.GameObjects.EntitySystems
}
}
- foreach(var powernet in Powernets)
+ foreach (var powernet in Powernets)
{
powernet.Update(frametime);
}
+
+ // Draw power for devices not connected to anything.
+ foreach (var device in componentManager.GetComponents())
+ {
+ device.ProcessInternalPower(frametime);
+ }
}
}
}
diff --git a/Content.Shared/Content.Shared.csproj b/Content.Shared/Content.Shared.csproj
index c1a950de18..70e509dc1e 100644
--- a/Content.Shared/Content.Shared.csproj
+++ b/Content.Shared/Content.Shared.csproj
@@ -72,6 +72,7 @@
+
@@ -101,4 +102,4 @@
-
\ No newline at end of file
+
diff --git a/Content.Shared/GameObjects/Components/Power/SharedPowerDebugTool.cs b/Content.Shared/GameObjects/Components/Power/SharedPowerDebugTool.cs
new file mode 100644
index 0000000000..55c3feb69e
--- /dev/null
+++ b/Content.Shared/GameObjects/Components/Power/SharedPowerDebugTool.cs
@@ -0,0 +1,24 @@
+using System;
+using SS14.Shared.GameObjects;
+using SS14.Shared.Serialization;
+
+namespace Content.Shared.GameObjects.Components.Power
+{
+ public class SharedPowerDebugTool : Component
+ {
+ public override string Name => "PowerDebugTool";
+ public override uint? NetID => ContentNetIDs.POWER_DEBUG_TOOL;
+
+ [Serializable, NetSerializable]
+ protected class OpenDataWindowMsg : ComponentMessage
+ {
+ public string Data { get; }
+
+ public OpenDataWindowMsg(string data)
+ {
+ Directed = true;
+ Data = data;
+ }
+ }
+ }
+}
diff --git a/Content.Shared/GameObjects/ContentNetIDs.cs b/Content.Shared/GameObjects/ContentNetIDs.cs
index afd6937958..f2d359196b 100644
--- a/Content.Shared/GameObjects/ContentNetIDs.cs
+++ b/Content.Shared/GameObjects/ContentNetIDs.cs
@@ -9,5 +9,6 @@
public const uint HANDS = 1003;
public const uint STORAGE = 1005;
public const uint INVENTORY = 1006;
+ public const uint POWER_DEBUG_TOOL = 1007;
}
}
diff --git a/Resources/Prototypes/Entities/Power.yml b/Resources/Prototypes/Entities/Power.yml
index 249bc8330f..1d83a8c6f6 100644
--- a/Resources/Prototypes/Entities/Power.yml
+++ b/Resources/Prototypes/Entities/Power.yml
@@ -57,6 +57,7 @@
- type: PowerProvider
Range: 5
Priority: Provider
+ Load: 0
- type: entity
parent: WPPnobattery
diff --git a/Resources/Prototypes/Entities/PoweredLighting.yml b/Resources/Prototypes/Entities/PoweredLighting.yml
new file mode 100644
index 0000000000..0cd57da13e
--- /dev/null
+++ b/Resources/Prototypes/Entities/PoweredLighting.yml
@@ -0,0 +1,17 @@
+- type: entity
+ name: Light
+ id: poweredlight
+ parent: __engine_wall_light
+ components:
+ # So we can click on it for deletion.
+ - type: BoundingBox
+ - type: Sprite
+ texture: Objects/wall_light_off.png
+
+ - type: PowerDevice
+ load: 1
+ priority: Low
+
+ - type: PoweredLight
+ - type: PointLight
+ state: Off
diff --git a/Resources/Prototypes/Entities/Tools.yml b/Resources/Prototypes/Entities/Tools.yml
index 9fb88cb60c..18f9dad7b5 100644
--- a/Resources/Prototypes/Entities/Tools.yml
+++ b/Resources/Prototypes/Entities/Tools.yml
@@ -81,3 +81,4 @@
texture: Objects/multitool.png
- type: Icon
texture: Objects/multitool.png
+ - type: PowerDebugTool
diff --git a/engine b/engine
index dc80060757..6f4ea205ef 160000
--- a/engine
+++ b/engine
@@ -1 +1 @@
-Subproject commit dc80060757a740260af0b4e63ed6ff7591947812
+Subproject commit 6f4ea205efdd273bf7dfa29fdd78096877505e9f