2023-05-28 05:25:54 -05:00
using Content.Server.Administration.Logs ;
2022-06-23 00:27:49 -04:00
using Content.Server.Popups ;
2023-04-27 20:49:41 +06:00
using Content.Server.Chat.Managers ;
2023-10-19 12:34:31 -07:00
using Content.Server.Singularity.Events ;
2022-06-23 00:27:49 -04:00
using Content.Shared.Construction.Components ;
2023-05-28 05:25:54 -05:00
using Content.Shared.Database ;
2022-08-05 00:22:37 -04:00
using Content.Shared.Examine ;
2022-06-23 00:27:49 -04:00
using Content.Shared.Interaction ;
2022-08-05 00:22:37 -04:00
using Content.Shared.Popups ;
2023-10-19 12:34:31 -07:00
using Content.Shared.Singularity.Components ;
using Content.Shared.Tag ;
using Robust.Server.GameObjects ;
using Robust.Shared.Physics ;
2022-09-14 17:26:26 +10:00
using Robust.Shared.Physics.Components ;
using Robust.Shared.Physics.Events ;
2021-05-13 02:05:46 +02:00
2022-08-05 00:22:37 -04:00
namespace Content.Server.Singularity.EntitySystems ;
public sealed class ContainmentFieldGeneratorSystem : EntitySystem
2021-05-13 02:05:46 +02:00
{
2023-05-28 05:25:54 -05:00
[Dependency] private readonly IAdminLogManager _adminLogger = default ! ;
2022-12-19 18:47:15 -08:00
[Dependency] private readonly AppearanceSystem _visualizer = default ! ;
2023-09-11 19:18:06 +10:00
[Dependency] private readonly PhysicsSystem _physics = default ! ;
[Dependency] private readonly PopupSystem _popupSystem = default ! ;
[Dependency] private readonly SharedPointLightSystem _light = default ! ;
[Dependency] private readonly TagSystem _tags = default ! ;
2023-04-27 20:49:41 +06:00
[Dependency] private readonly IChatManager _chatManager = default ! ;
2022-08-05 00:22:37 -04:00
public override void Initialize ( )
2021-05-13 02:05:46 +02:00
{
2022-08-05 00:22:37 -04:00
base . Initialize ( ) ;
SubscribeLocalEvent < ContainmentFieldGeneratorComponent , StartCollideEvent > ( HandleGeneratorCollide ) ;
SubscribeLocalEvent < ContainmentFieldGeneratorComponent , ExaminedEvent > ( OnExamine ) ;
SubscribeLocalEvent < ContainmentFieldGeneratorComponent , InteractHandEvent > ( OnInteract ) ;
SubscribeLocalEvent < ContainmentFieldGeneratorComponent , AnchorStateChangedEvent > ( OnAnchorChanged ) ;
SubscribeLocalEvent < ContainmentFieldGeneratorComponent , ReAnchorEvent > ( OnReanchorEvent ) ;
SubscribeLocalEvent < ContainmentFieldGeneratorComponent , UnanchorAttemptEvent > ( OnUnanchorAttempt ) ;
SubscribeLocalEvent < ContainmentFieldGeneratorComponent , ComponentRemove > ( OnComponentRemoved ) ;
2022-12-19 18:47:15 -08:00
SubscribeLocalEvent < ContainmentFieldGeneratorComponent , EventHorizonAttemptConsumeEntityEvent > ( PreventBreach ) ;
2022-08-05 00:22:37 -04:00
}
2022-02-08 14:08:11 +11:00
2022-08-05 00:22:37 -04:00
public override void Update ( float frameTime )
{
base . Update ( frameTime ) ;
2022-06-23 00:27:49 -04:00
2023-05-28 05:25:54 -05:00
var query = EntityQueryEnumerator < ContainmentFieldGeneratorComponent > ( ) ;
while ( query . MoveNext ( out var uid , out var generator ) )
2022-06-23 00:27:49 -04:00
{
2022-08-05 00:22:37 -04:00
if ( generator . PowerBuffer < = 0 ) //don't drain power if there's no power, or if it's somehow less than 0.
2022-08-14 22:37:58 -04:00
continue ;
2022-06-23 00:27:49 -04:00
2022-08-05 00:22:37 -04:00
generator . Accumulator + = frameTime ;
if ( generator . Accumulator > = generator . Threshold )
2022-06-23 00:27:49 -04:00
{
2023-10-19 12:34:31 -07:00
LosePower ( ( uid , generator ) , generator . PowerLoss ) ;
2022-08-05 00:22:37 -04:00
generator . Accumulator - = generator . Threshold ;
2022-06-23 00:27:49 -04:00
}
2022-08-05 00:22:37 -04:00
}
}
#region Events
2022-06-23 00:27:49 -04:00
2022-08-05 00:22:37 -04:00
/// <summary>
/// A generator receives power from a source colliding with it.
/// </summary>
2023-10-19 12:34:31 -07:00
private void HandleGeneratorCollide ( Entity < ContainmentFieldGeneratorComponent > generator , ref StartCollideEvent args )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
if ( _tags . HasTag ( args . OtherEntity , generator . Comp . IDTag ) )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
ReceivePower ( generator . Comp . PowerReceived , generator ) ;
generator . Comp . Accumulator = 0f ;
2022-06-23 00:27:49 -04:00
}
2022-08-05 00:22:37 -04:00
}
private void OnExamine ( EntityUid uid , ContainmentFieldGeneratorComponent component , ExaminedEvent args )
{
if ( component . Enabled )
args . PushMarkup ( Loc . GetString ( "comp-containment-on" ) ) ;
else
args . PushMarkup ( Loc . GetString ( "comp-containment-off" ) ) ;
}
2023-10-19 12:34:31 -07:00
private void OnInteract ( Entity < ContainmentFieldGeneratorComponent > generator , ref InteractHandEvent args )
2022-08-05 00:22:37 -04:00
{
if ( args . Handled )
return ;
2022-06-23 00:27:49 -04:00
2023-10-19 12:34:31 -07:00
if ( TryComp ( generator , out TransformComponent ? transformComp ) & & transformComp . Anchored )
2022-06-23 00:27:49 -04:00
{
2023-10-19 12:34:31 -07:00
if ( ! generator . Comp . Enabled )
TurnOn ( generator ) ;
else if ( generator . Comp . Enabled & & generator . Comp . IsConnected )
2022-06-23 00:27:49 -04:00
{
2022-12-19 10:41:47 +13:00
_popupSystem . PopupEntity ( Loc . GetString ( "comp-containment-toggle-warning" ) , args . User , args . User , PopupType . LargeCaution ) ;
2022-08-05 00:22:37 -04:00
return ;
2022-06-23 00:27:49 -04:00
}
2022-08-05 00:22:37 -04:00
else
2023-10-19 12:34:31 -07:00
TurnOff ( generator ) ;
2022-06-23 00:27:49 -04:00
}
2022-08-05 00:22:37 -04:00
args . Handled = true ;
}
2022-06-23 00:27:49 -04:00
2023-10-19 12:34:31 -07:00
private void OnAnchorChanged ( Entity < ContainmentFieldGeneratorComponent > generator , ref AnchorStateChangedEvent args )
2022-08-05 00:22:37 -04:00
{
if ( ! args . Anchored )
2023-10-19 12:34:31 -07:00
RemoveConnections ( generator ) ;
2022-08-05 00:22:37 -04:00
}
2022-06-23 00:27:49 -04:00
2023-10-19 12:34:31 -07:00
private void OnReanchorEvent ( Entity < ContainmentFieldGeneratorComponent > generator , ref ReAnchorEvent args )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
GridCheck ( generator ) ;
2022-08-05 00:22:37 -04:00
}
2022-06-16 14:46:21 +01:00
2022-08-05 00:22:37 -04:00
private void OnUnanchorAttempt ( EntityUid uid , ContainmentFieldGeneratorComponent component ,
UnanchorAttemptEvent args )
{
if ( component . Enabled )
2022-06-16 14:46:21 +01:00
{
2022-12-19 10:41:47 +13:00
_popupSystem . PopupEntity ( Loc . GetString ( "comp-containment-anchor-warning" ) , args . User , args . User , PopupType . LargeCaution ) ;
2022-08-05 00:22:37 -04:00
args . Cancel ( ) ;
2022-06-16 14:46:21 +01:00
}
2022-08-05 00:22:37 -04:00
}
2022-06-16 14:46:21 +01:00
2023-10-19 12:34:31 -07:00
private void TurnOn ( Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
generator . Comp . Enabled = true ;
ChangeFieldVisualizer ( generator ) ;
_popupSystem . PopupEntity ( Loc . GetString ( "comp-containment-turned-on" ) , generator ) ;
2022-08-05 00:22:37 -04:00
}
2023-10-19 12:34:31 -07:00
private void TurnOff ( Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
generator . Comp . Enabled = false ;
ChangeFieldVisualizer ( generator ) ;
_popupSystem . PopupEntity ( Loc . GetString ( "comp-containment-turned-off" ) , generator ) ;
2022-08-05 00:22:37 -04:00
}
2023-10-19 12:34:31 -07:00
private void OnComponentRemoved ( Entity < ContainmentFieldGeneratorComponent > generator , ref ComponentRemove args )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
RemoveConnections ( generator ) ;
2022-08-05 00:22:37 -04:00
}
/// <summary>
/// Deletes the fields and removes the respective connections for the generators.
/// </summary>
2023-10-19 12:34:31 -07:00
private void RemoveConnections ( Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
var ( uid , component ) = generator ;
2022-08-05 00:22:37 -04:00
foreach ( var ( direction , value ) in component . Connections )
2022-06-16 14:46:21 +01:00
{
2022-08-05 00:22:37 -04:00
foreach ( var field in value . Item2 )
2022-06-16 14:46:21 +01:00
{
2022-08-05 00:22:37 -04:00
QueueDel ( field ) ;
2022-06-16 14:46:21 +01:00
}
2023-10-19 12:34:31 -07:00
value . Item1 . Comp . Connections . Remove ( direction . GetOpposite ( ) ) ;
2021-07-21 22:26:18 +10:00
2023-10-19 12:34:31 -07:00
if ( value . Item1 . Comp . Connections . Count = = 0 ) //Change isconnected only if there's no more connections
2021-07-21 22:26:18 +10:00
{
2023-10-19 12:34:31 -07:00
value . Item1 . Comp . IsConnected = false ;
2022-08-05 00:22:37 -04:00
ChangeOnLightVisualizer ( value . Item1 ) ;
2021-07-21 22:26:18 +10:00
}
2022-08-05 00:22:37 -04:00
ChangeFieldVisualizer ( value . Item1 ) ;
2021-07-21 22:26:18 +10:00
}
2022-08-05 00:22:37 -04:00
component . Connections . Clear ( ) ;
component . IsConnected = false ;
2023-10-19 12:34:31 -07:00
ChangeOnLightVisualizer ( generator ) ;
ChangeFieldVisualizer ( generator ) ;
2023-05-28 05:25:54 -05:00
_adminLogger . Add ( LogType . FieldGeneration , LogImpact . Medium , $"{ToPrettyString(uid)} lost field connections" ) ; // Ideally LogImpact would depend on if there is a singulo nearby
2023-10-19 12:34:31 -07:00
_popupSystem . PopupEntity ( Loc . GetString ( "comp-containment-disconnected" ) , uid , PopupType . LargeCaution ) ;
2022-08-05 00:22:37 -04:00
}
#endregion
#region Connections
2021-07-21 22:26:18 +10:00
2022-08-05 00:22:37 -04:00
/// <summary>
/// Stores power in the generator. If it hits the threshold, it tries to establish a connection.
/// </summary>
/// <param name="power">The power that this generator received from the collision in <see cref="HandleGeneratorCollide"/></param>
2023-10-19 12:34:31 -07:00
public void ReceivePower ( int power , Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
var component = generator . Comp ;
2022-08-05 00:22:37 -04:00
component . PowerBuffer + = power ;
2023-10-19 12:34:31 -07:00
var genXForm = Transform ( generator ) ;
2022-08-05 00:22:37 -04:00
if ( component . PowerBuffer > = component . PowerMinimum )
2021-07-21 22:26:18 +10:00
{
2022-08-05 00:22:37 -04:00
var directions = Enum . GetValues < Direction > ( ) . Length ;
for ( int i = 0 ; i < directions - 1 ; i + = 2 )
2022-06-16 14:46:21 +01:00
{
2022-08-05 00:22:37 -04:00
var dir = ( Direction ) i ;
if ( component . Connections . ContainsKey ( dir ) )
continue ; // This direction already has an active connection
2023-10-19 12:34:31 -07:00
TryGenerateFieldConnection ( dir , generator , genXForm ) ;
2021-07-21 22:26:18 +10:00
}
}
2023-10-19 12:34:31 -07:00
ChangePowerVisualizer ( power , generator ) ;
2022-08-05 00:22:37 -04:00
}
2023-10-19 12:34:31 -07:00
public void LosePower ( Entity < ContainmentFieldGeneratorComponent > generator , int power )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
var component = generator . Comp ;
2022-08-05 00:22:37 -04:00
component . PowerBuffer - = power ;
if ( component . PowerBuffer < component . PowerMinimum & & component . Connections . Count ! = 0 )
2021-07-21 22:26:18 +10:00
{
2023-04-27 20:49:41 +06:00
_chatManager . SendAdminAnnouncement ( Loc . GetString ( "admin-chatalert-singularity-field-down" ,
( "fieldgenerator" , ToPrettyString ( generator ) ) ) ) ;
2023-10-19 12:34:31 -07:00
RemoveConnections ( generator ) ;
2021-05-13 02:05:46 +02:00
}
2023-10-19 12:34:31 -07:00
ChangePowerVisualizer ( power , generator ) ;
2022-08-05 00:22:37 -04:00
}
/// <summary>
/// This will attempt to establish a connection of fields between two generators.
/// If all the checks pass and fields spawn, it will store this connection on each respective generator.
/// </summary>
/// <param name="dir">The field generator establishes a connection in this direction.</param>
2023-10-19 12:34:31 -07:00
/// <param name="generator">The field generator component</param>
2022-08-05 00:22:37 -04:00
/// <param name="gen1XForm">The transform component for the first generator</param>
/// <returns></returns>
2023-10-19 12:34:31 -07:00
private bool TryGenerateFieldConnection ( Direction dir , Entity < ContainmentFieldGeneratorComponent > generator , TransformComponent gen1XForm )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
var component = generator . Comp ;
2022-08-05 00:22:37 -04:00
if ( ! component . Enabled )
return false ;
if ( ! gen1XForm . Anchored )
return false ;
2023-09-01 12:30:29 +10:00
var genWorldPosRot = gen1XForm . GetWorldPositionRotation ( ) ;
2022-08-05 00:22:37 -04:00
var dirRad = dir . ToAngle ( ) + genWorldPosRot . WorldRotation ; //needs to be like this for the raycast to work properly
var ray = new CollisionRay ( genWorldPosRot . WorldPosition , dirRad . ToVec ( ) , component . CollisionMask ) ;
2023-10-19 12:34:31 -07:00
var rayCastResults = _physics . IntersectRay ( gen1XForm . MapID , ray , component . MaxLength , generator , false ) ;
2022-08-05 00:22:37 -04:00
var genQuery = GetEntityQuery < ContainmentFieldGeneratorComponent > ( ) ;
RayCastResults ? closestResult = null ;
foreach ( var result in rayCastResults )
2022-06-16 14:46:21 +01:00
{
2022-08-05 00:22:37 -04:00
if ( genQuery . HasComponent ( result . HitEntity ) )
closestResult = result ;
2022-06-16 14:46:21 +01:00
2022-08-05 00:22:37 -04:00
break ;
2022-06-16 14:46:21 +01:00
}
2022-08-05 00:22:37 -04:00
if ( closestResult = = null )
return false ;
var ent = closestResult . Value . HitEntity ;
2022-06-16 14:46:21 +01:00
2023-09-20 10:12:48 +10:00
if ( ! TryComp < ContainmentFieldGeneratorComponent > ( ent , out var otherFieldGeneratorComponent ) | |
2022-08-05 00:22:37 -04:00
otherFieldGeneratorComponent = = component | |
! TryComp < PhysicsComponent > ( ent , out var collidableComponent ) | |
collidableComponent . BodyType ! = BodyType . Static | |
2023-10-19 12:34:31 -07:00
gen1XForm . ParentUid ! = Transform ( ent ) . ParentUid )
2022-06-16 14:46:21 +01:00
{
2022-08-05 00:22:37 -04:00
return false ;
2022-06-16 14:46:21 +01:00
}
2023-10-19 12:34:31 -07:00
var otherFieldGenerator = ( ent , otherFieldGeneratorComponent ) ;
var fields = GenerateFieldConnection ( generator , otherFieldGenerator ) ;
2022-08-05 00:22:37 -04:00
2023-10-19 12:34:31 -07:00
component . Connections [ dir ] = ( otherFieldGenerator , fields ) ;
otherFieldGeneratorComponent . Connections [ dir . GetOpposite ( ) ] = ( generator , fields ) ;
ChangeFieldVisualizer ( otherFieldGenerator ) ;
2022-08-05 00:22:37 -04:00
if ( ! component . IsConnected )
2021-05-13 02:05:46 +02:00
{
2022-08-05 00:22:37 -04:00
component . IsConnected = true ;
2023-10-19 12:34:31 -07:00
ChangeOnLightVisualizer ( generator ) ;
2022-08-05 00:22:37 -04:00
}
if ( ! otherFieldGeneratorComponent . IsConnected )
{
otherFieldGeneratorComponent . IsConnected = true ;
2023-10-19 12:34:31 -07:00
ChangeOnLightVisualizer ( otherFieldGenerator ) ;
2021-05-13 02:05:46 +02:00
}
2022-06-16 14:46:21 +01:00
2023-10-19 12:34:31 -07:00
ChangeFieldVisualizer ( generator ) ;
UpdateConnectionLights ( generator ) ;
_popupSystem . PopupEntity ( Loc . GetString ( "comp-containment-connected" ) , generator ) ;
2022-08-05 00:22:37 -04:00
return true ;
}
/// <summary>
/// Spawns fields between two generators if the <see cref="TryGenerateFieldConnection"/> finds two generators to connect.
/// </summary>
2023-10-19 12:34:31 -07:00
/// <param name="firstGen">The source field generator</param>
/// <param name="secondGen">The second generator that the source is connected to</param>
2022-08-05 00:22:37 -04:00
/// <returns></returns>
2023-10-19 12:34:31 -07:00
private List < EntityUid > GenerateFieldConnection ( Entity < ContainmentFieldGeneratorComponent > firstGen , Entity < ContainmentFieldGeneratorComponent > secondGen )
2022-08-05 00:22:37 -04:00
{
var fieldList = new List < EntityUid > ( ) ;
2023-10-19 12:34:31 -07:00
var gen1Coords = Transform ( firstGen ) . Coordinates ;
var gen2Coords = Transform ( secondGen ) . Coordinates ;
2022-08-05 00:22:37 -04:00
var delta = ( gen2Coords - gen1Coords ) . Position ;
2023-07-08 14:08:32 +10:00
var dirVec = delta . Normalized ( ) ;
var stopDist = delta . Length ( ) ;
2022-08-05 00:22:37 -04:00
var currentOffset = dirVec ;
2023-07-08 14:08:32 +10:00
while ( currentOffset . Length ( ) < stopDist )
2022-06-16 14:46:21 +01:00
{
2022-08-05 00:22:37 -04:00
var currentCoords = gen1Coords . Offset ( currentOffset ) ;
2023-10-19 12:34:31 -07:00
var newField = Spawn ( firstGen . Comp . CreatedField , currentCoords ) ;
2022-06-16 14:46:21 +01:00
2022-08-05 00:22:37 -04:00
var fieldXForm = Transform ( newField ) ;
2023-10-19 12:34:31 -07:00
fieldXForm . AttachParent ( firstGen ) ;
2022-08-05 00:22:37 -04:00
if ( dirVec . GetDir ( ) = = Direction . East | | dirVec . GetDir ( ) = = Direction . West )
2022-06-16 14:46:21 +01:00
{
2022-08-05 00:22:37 -04:00
var angle = fieldXForm . LocalPosition . ToAngle ( ) ;
var rotateBy90 = angle . Degrees + 90 ;
var rotatedAngle = Angle . FromDegrees ( rotateBy90 ) ;
fieldXForm . LocalRotation = rotatedAngle ;
2022-06-16 14:46:21 +01:00
}
2022-08-05 00:22:37 -04:00
fieldList . Add ( newField ) ;
currentOffset + = dirVec ;
2022-06-16 14:46:21 +01:00
}
2022-08-05 00:22:37 -04:00
return fieldList ;
}
2022-06-16 14:46:21 +01:00
2022-08-05 00:22:37 -04:00
/// <summary>
/// Creates a light component for the spawned fields.
/// </summary>
2023-10-19 12:34:31 -07:00
public void UpdateConnectionLights ( Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
if ( _light . TryGetLight ( generator , out var pointLightComponent ) )
2022-06-16 14:46:21 +01:00
{
2023-10-19 12:34:31 -07:00
_light . SetEnabled ( generator , generator . Comp . Connections . Count > 0 , pointLightComponent ) ;
2022-06-16 14:46:21 +01:00
}
2022-08-05 00:22:37 -04:00
}
/// <summary>
/// Checks to see if this or the other gens connected to a new grid. If they did, remove connection.
/// </summary>
2023-10-19 12:34:31 -07:00
public void GridCheck ( Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
var xFormQuery = GetEntityQuery < TransformComponent > ( ) ;
2022-06-16 14:46:21 +01:00
2023-10-19 12:34:31 -07:00
foreach ( var ( _ , generators ) in generator . Comp . Connections )
2022-06-16 14:46:21 +01:00
{
2023-10-19 12:34:31 -07:00
var gen1ParentGrid = xFormQuery . GetComponent ( generator ) . ParentUid ;
var gent2ParentGrid = xFormQuery . GetComponent ( generators . Item1 ) . ParentUid ;
2022-08-05 00:22:37 -04:00
if ( gen1ParentGrid ! = gent2ParentGrid )
2023-10-19 12:34:31 -07:00
RemoveConnections ( generator ) ;
2022-06-16 14:46:21 +01:00
}
2022-08-05 00:22:37 -04:00
}
#endregion
2022-06-16 14:46:21 +01:00
2022-08-05 00:22:37 -04:00
#region VisualizerHelpers
/// <summary>
/// Check if a fields power falls between certain ranges to update the field gen visual for power.
/// </summary>
/// <param name="power"></param>
2023-10-19 12:34:31 -07:00
/// <param name="generator"></param>
private void ChangePowerVisualizer ( int power , Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
var component = generator . Comp ;
_visualizer . SetData ( generator , ContainmentFieldGeneratorVisuals . PowerLight , component . PowerBuffer switch
{
< = 0 = > PowerLevelVisuals . NoPower ,
> = 25 = > PowerLevelVisuals . HighPower ,
_ = > ( component . PowerBuffer < component . PowerMinimum )
? PowerLevelVisuals . LowPower
: PowerLevelVisuals . MediumPower
2022-12-19 18:47:15 -08:00
} ) ;
2022-08-05 00:22:37 -04:00
}
2022-06-16 14:46:21 +01:00
2022-08-05 00:22:37 -04:00
/// <summary>
/// Check if a field has any or no connections and if it's enabled to toggle the field level light
/// </summary>
2023-10-19 12:34:31 -07:00
/// <param name="generator"></param>
private void ChangeFieldVisualizer ( Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
_visualizer . SetData ( generator , ContainmentFieldGeneratorVisuals . FieldLight , generator . Comp . Connections . Count switch
{
2022-12-19 18:47:15 -08:00
> 1 = > FieldLevelVisuals . MultipleFields ,
1 = > FieldLevelVisuals . OneField ,
2023-10-19 12:34:31 -07:00
_ = > generator . Comp . Enabled ? FieldLevelVisuals . On : FieldLevelVisuals . NoLevel
2022-12-19 18:47:15 -08:00
} ) ;
2022-08-05 00:22:37 -04:00
}
2023-10-19 12:34:31 -07:00
private void ChangeOnLightVisualizer ( Entity < ContainmentFieldGeneratorComponent > generator )
2022-08-05 00:22:37 -04:00
{
2023-10-19 12:34:31 -07:00
_visualizer . SetData ( generator , ContainmentFieldGeneratorVisuals . OnLight , generator . Comp . IsConnected ) ;
2021-05-13 02:05:46 +02:00
}
2022-08-05 00:22:37 -04:00
#endregion
2022-12-19 18:47:15 -08:00
/// <summary>
/// Prevents singularities from breaching containment if the containment field generator is connected.
/// </summary>
/// <param name="uid">The entity the singularity is trying to eat.</param>
/// <param name="comp">The containment field generator the singularity is trying to eat.</param>
/// <param name="args">The event arguments.</param>
2023-07-19 01:01:27 -07:00
private void PreventBreach ( EntityUid uid , ContainmentFieldGeneratorComponent comp , ref EventHorizonAttemptConsumeEntityEvent args )
2022-12-19 18:47:15 -08:00
{
if ( args . Cancelled )
return ;
if ( comp . IsConnected & & ! args . EventHorizon . CanBreachContainment )
2023-07-19 01:01:27 -07:00
args . Cancelled = true ;
2022-12-19 18:47:15 -08:00
}
2021-05-13 02:05:46 +02:00
}