2023-01-17 08:32:46 +00:00
using Content.Server.Administration ;
2022-12-11 21:06:11 +03:00
using Content.Server.Administration.Managers ;
using Content.Server.Chat.Managers ;
using Content.Server.DeviceNetwork ;
using Content.Server.DeviceNetwork.Components ;
using Content.Server.DeviceNetwork.Systems ;
using Content.Server.Paper ;
using Content.Server.Popups ;
using Content.Server.Power.Components ;
using Content.Server.Tools ;
2024-02-01 11:45:24 +03:00
using Content.Shared.UserInterface ;
2022-12-13 19:09:45 -06:00
using Content.Shared.Administration.Logs ;
2022-12-11 21:06:11 +03:00
using Content.Shared.Containers.ItemSlots ;
2022-12-13 19:09:45 -06:00
using Content.Shared.Database ;
2024-02-11 14:19:45 +11:00
using Content.Shared.DeviceNetwork ;
2023-02-19 01:03:06 +00:00
using Content.Shared.Emag.Components ;
2022-12-11 21:06:11 +03:00
using Content.Shared.Emag.Systems ;
using Content.Shared.Fax ;
using Content.Shared.Interaction ;
2023-08-13 19:28:10 +01:00
using Content.Shared.Paper ;
2022-12-11 21:06:11 +03:00
using Robust.Server.GameObjects ;
2023-04-16 23:20:57 -07:00
using Robust.Shared.Audio ;
2023-11-27 22:12:34 +11:00
using Robust.Shared.Audio.Systems ;
2022-12-11 21:06:11 +03:00
using Robust.Shared.Containers ;
using Robust.Shared.Player ;
2023-12-25 02:08:15 +01:00
using Robust.Shared.Prototypes ;
2022-12-11 21:06:11 +03:00
namespace Content.Server.Fax ;
public sealed class FaxSystem : EntitySystem
{
[Dependency] private readonly IChatManager _chat = default ! ;
[Dependency] private readonly IAdminManager _adminManager = default ! ;
[Dependency] private readonly ItemSlotsSystem _itemSlotsSystem = default ! ;
[Dependency] private readonly SharedAppearanceSystem _appearanceSystem = default ! ;
[Dependency] private readonly PopupSystem _popupSystem = default ! ;
[Dependency] private readonly DeviceNetworkSystem _deviceNetworkSystem = default ! ;
[Dependency] private readonly PaperSystem _paperSystem = default ! ;
[Dependency] private readonly SharedAudioSystem _audioSystem = default ! ;
[Dependency] private readonly ToolSystem _toolSystem = default ! ;
[Dependency] private readonly QuickDialogSystem _quickDialog = default ! ;
[Dependency] private readonly UserInterfaceSystem _userInterface = default ! ;
2022-12-13 19:09:45 -06:00
[Dependency] private readonly ISharedAdminLogManager _adminLogger = default ! ;
2023-08-28 11:20:31 +02:00
[Dependency] private readonly MetaDataSystem _metaData = default ! ;
2022-12-11 21:06:11 +03:00
2023-04-16 23:20:57 -07:00
private const string PaperSlotId = "Paper" ;
2022-12-11 21:06:11 +03:00
2023-12-25 02:08:15 +01:00
/// <summary>
/// The prototype ID to use for faxed or copied entities if we can't get one from
/// the paper entity for whatever reason.
/// </summary>
[ValidatePrototypeId<EntityPrototype>]
private const string DefaultPaperPrototypeId = "Paper" ;
2024-02-13 22:14:51 -03:00
[ValidatePrototypeId<EntityPrototype>]
private const string OfficePaperPrototypeId = "PaperOffice" ;
2023-12-25 02:08:15 +01:00
2022-12-11 21:06:11 +03:00
public override void Initialize ( )
{
base . Initialize ( ) ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
// Hooks
SubscribeLocalEvent < FaxMachineComponent , ComponentInit > ( OnComponentInit ) ;
SubscribeLocalEvent < FaxMachineComponent , MapInitEvent > ( OnMapInit ) ;
SubscribeLocalEvent < FaxMachineComponent , ComponentRemove > ( OnComponentRemove ) ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
SubscribeLocalEvent < FaxMachineComponent , EntInsertedIntoContainerMessage > ( OnItemSlotChanged ) ;
SubscribeLocalEvent < FaxMachineComponent , EntRemovedFromContainerMessage > ( OnItemSlotChanged ) ;
SubscribeLocalEvent < FaxMachineComponent , PowerChangedEvent > ( OnPowerChanged ) ;
SubscribeLocalEvent < FaxMachineComponent , DeviceNetworkPacketEvent > ( OnPacketReceived ) ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
// Interaction
SubscribeLocalEvent < FaxMachineComponent , InteractUsingEvent > ( OnInteractUsing ) ;
SubscribeLocalEvent < FaxMachineComponent , GotEmaggedEvent > ( OnEmagged ) ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
// UI
SubscribeLocalEvent < FaxMachineComponent , AfterActivatableUIOpenEvent > ( OnToggleInterface ) ;
2024-02-13 22:14:51 -03:00
SubscribeLocalEvent < FaxMachineComponent , FaxFileMessage > ( OnFileButtonPressed ) ;
2023-12-25 02:08:15 +01:00
SubscribeLocalEvent < FaxMachineComponent , FaxCopyMessage > ( OnCopyButtonPressed ) ;
2022-12-11 21:06:11 +03:00
SubscribeLocalEvent < FaxMachineComponent , FaxSendMessage > ( OnSendButtonPressed ) ;
SubscribeLocalEvent < FaxMachineComponent , FaxRefreshMessage > ( OnRefreshButtonPressed ) ;
SubscribeLocalEvent < FaxMachineComponent , FaxDestinationMessage > ( OnDestinationSelected ) ;
}
public override void Update ( float frameTime )
{
base . Update ( frameTime ) ;
2023-04-16 23:20:57 -07:00
var query = EntityQueryEnumerator < FaxMachineComponent , ApcPowerReceiverComponent > ( ) ;
while ( query . MoveNext ( out var uid , out var fax , out var receiver ) )
2022-12-11 21:06:11 +03:00
{
if ( ! receiver . Powered )
continue ;
2023-04-16 23:20:57 -07:00
ProcessPrintingAnimation ( uid , frameTime , fax ) ;
ProcessInsertingAnimation ( uid , frameTime , fax ) ;
ProcessSendingTimeout ( uid , frameTime , fax ) ;
2022-12-11 21:06:11 +03:00
}
}
2023-04-16 23:20:57 -07:00
private void ProcessPrintingAnimation ( EntityUid uid , float frameTime , FaxMachineComponent comp )
2022-12-11 21:06:11 +03:00
{
if ( comp . PrintingTimeRemaining > 0 )
{
comp . PrintingTimeRemaining - = frameTime ;
2023-04-16 23:20:57 -07:00
UpdateAppearance ( uid , comp ) ;
2022-12-11 21:06:11 +03:00
var isAnimationEnd = comp . PrintingTimeRemaining < = 0 ;
if ( isAnimationEnd )
{
2023-04-16 23:20:57 -07:00
SpawnPaperFromQueue ( uid , comp ) ;
UpdateUserInterface ( uid , comp ) ;
2022-12-11 21:06:11 +03:00
}
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
return ;
}
if ( comp . PrintingQueue . Count > 0 )
{
comp . PrintingTimeRemaining = comp . PrintingTime ;
2023-04-16 23:20:57 -07:00
_audioSystem . PlayPvs ( comp . PrintSound , uid ) ;
2022-12-11 21:06:11 +03:00
}
}
2023-04-16 23:20:57 -07:00
private void ProcessInsertingAnimation ( EntityUid uid , float frameTime , FaxMachineComponent comp )
2022-12-11 21:06:11 +03:00
{
if ( comp . InsertingTimeRemaining < = 0 )
return ;
comp . InsertingTimeRemaining - = frameTime ;
2023-04-16 23:20:57 -07:00
UpdateAppearance ( uid , comp ) ;
2022-12-11 21:06:11 +03:00
var isAnimationEnd = comp . InsertingTimeRemaining < = 0 ;
if ( isAnimationEnd )
{
2023-04-16 23:20:57 -07:00
_itemSlotsSystem . SetLock ( uid , comp . PaperSlot , false ) ;
UpdateUserInterface ( uid , comp ) ;
2022-12-11 21:06:11 +03:00
}
}
2023-04-16 23:20:57 -07:00
private void ProcessSendingTimeout ( EntityUid uid , float frameTime , FaxMachineComponent comp )
2022-12-11 21:06:11 +03:00
{
if ( comp . SendTimeoutRemaining > 0 )
{
comp . SendTimeoutRemaining - = frameTime ;
if ( comp . SendTimeoutRemaining < = 0 )
2023-04-16 23:20:57 -07:00
UpdateUserInterface ( uid , comp ) ;
2022-12-11 21:06:11 +03:00
}
}
private void OnComponentInit ( EntityUid uid , FaxMachineComponent component , ComponentInit args )
{
2023-04-16 23:20:57 -07:00
_itemSlotsSystem . AddItemSlot ( uid , PaperSlotId , component . PaperSlot ) ;
2022-12-11 21:06:11 +03:00
UpdateAppearance ( uid , component ) ;
}
private void OnComponentRemove ( EntityUid uid , FaxMachineComponent component , ComponentRemove args )
{
_itemSlotsSystem . RemoveItemSlot ( uid , component . PaperSlot ) ;
}
private void OnMapInit ( EntityUid uid , FaxMachineComponent component , MapInitEvent args )
{
// Load all faxes on map in cache each other to prevent taking same name by user created fax
Refresh ( uid , component ) ;
}
private void OnItemSlotChanged ( EntityUid uid , FaxMachineComponent component , ContainerModifiedMessage args )
{
if ( ! component . Initialized )
return ;
if ( args . Container . ID ! = component . PaperSlot . ID )
return ;
var isPaperInserted = component . PaperSlot . Item . HasValue ;
if ( isPaperInserted )
{
component . InsertingTimeRemaining = component . InsertionTime ;
_itemSlotsSystem . SetLock ( uid , component . PaperSlot , true ) ;
}
UpdateUserInterface ( uid , component ) ;
}
private void OnPowerChanged ( EntityUid uid , FaxMachineComponent component , ref PowerChangedEvent args )
{
var isInsertInterrupted = ! args . Powered & & component . InsertingTimeRemaining > 0 ;
if ( isInsertInterrupted )
{
component . InsertingTimeRemaining = 0f ; // Reset animation
// Drop from slot because animation did not play completely
_itemSlotsSystem . SetLock ( uid , component . PaperSlot , false ) ;
_itemSlotsSystem . TryEject ( uid , component . PaperSlot , null , out var _ , true ) ;
}
var isPrintInterrupted = ! args . Powered & & component . PrintingTimeRemaining > 0 ;
if ( isPrintInterrupted )
{
component . PrintingTimeRemaining = 0f ; // Reset animation
}
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
if ( isInsertInterrupted | | isPrintInterrupted )
2023-04-16 23:20:57 -07:00
UpdateAppearance ( uid , component ) ;
2022-12-11 21:06:11 +03:00
_itemSlotsSystem . SetLock ( uid , component . PaperSlot , ! args . Powered ) ; // Lock slot when power is off
}
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
private void OnInteractUsing ( EntityUid uid , FaxMachineComponent component , InteractUsingEvent args )
{
if ( args . Handled | |
! TryComp < ActorComponent > ( args . User , out var actor ) | |
! _toolSystem . HasQuality ( args . Used , "Screwing" ) ) // Screwing because Pulsing already used by device linking
return ;
_quickDialog . OpenDialog ( actor . PlayerSession ,
Loc . GetString ( "fax-machine-dialog-rename" ) ,
Loc . GetString ( "fax-machine-dialog-field-name" ) ,
( string newName ) = >
{
if ( component . FaxName = = newName )
return ;
if ( newName . Length > 20 )
{
2022-12-19 10:41:47 +13:00
_popupSystem . PopupEntity ( Loc . GetString ( "fax-machine-popup-name-long" ) , uid ) ;
2022-12-11 21:06:11 +03:00
return ;
}
2023-02-19 01:03:06 +00:00
if ( component . KnownFaxes . ContainsValue ( newName ) & & ! HasComp < EmaggedComponent > ( uid ) ) // Allow existing names if emagged for fun
2022-12-11 21:06:11 +03:00
{
2022-12-19 10:41:47 +13:00
_popupSystem . PopupEntity ( Loc . GetString ( "fax-machine-popup-name-exist" ) , uid ) ;
2022-12-11 21:06:11 +03:00
return ;
}
2022-12-13 19:09:45 -06:00
_adminLogger . Add ( LogType . Action , LogImpact . Low ,
$"{ToPrettyString(args.User):user} renamed {ToPrettyString(uid)} from \" { component . FaxName } \ " to \"{newName}\"" ) ;
2022-12-11 21:06:11 +03:00
component . FaxName = newName ;
2022-12-19 10:41:47 +13:00
_popupSystem . PopupEntity ( Loc . GetString ( "fax-machine-popup-name-set" ) , uid ) ;
2022-12-11 21:06:11 +03:00
UpdateUserInterface ( uid , component ) ;
} ) ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
args . Handled = true ;
}
2022-12-19 10:41:47 +13:00
2023-01-21 10:12:45 -05:00
private void OnEmagged ( EntityUid uid , FaxMachineComponent component , ref GotEmaggedEvent args )
2022-12-11 21:06:11 +03:00
{
_audioSystem . PlayPvs ( component . EmagSound , uid ) ;
args . Handled = true ;
}
private void OnPacketReceived ( EntityUid uid , FaxMachineComponent component , DeviceNetworkPacketEvent args )
{
if ( ! HasComp < DeviceNetworkComponent > ( uid ) | | string . IsNullOrEmpty ( args . SenderAddress ) )
return ;
if ( args . Data . TryGetValue ( DeviceNetworkConstants . Command , out string? command ) )
{
switch ( command )
{
case FaxConstants . FaxPingCommand :
2023-02-19 01:03:06 +00:00
var isForSyndie = HasComp < EmaggedComponent > ( uid ) & &
2022-12-11 21:06:11 +03:00
args . Data . ContainsKey ( FaxConstants . FaxSyndicateData ) ;
if ( ! isForSyndie & & ! component . ResponsePings )
return ;
var payload = new NetworkPayload ( )
{
{ DeviceNetworkConstants . Command , FaxConstants . FaxPongCommand } ,
{ FaxConstants . FaxNameData , component . FaxName }
} ;
_deviceNetworkSystem . QueuePacket ( uid , args . SenderAddress , payload ) ;
break ;
case FaxConstants . FaxPongCommand :
if ( ! args . Data . TryGetValue ( FaxConstants . FaxNameData , out string? faxName ) )
return ;
component . KnownFaxes [ args . SenderAddress ] = faxName ;
UpdateUserInterface ( uid , component ) ;
break ;
case FaxConstants . FaxPrintCommand :
if ( ! args . Data . TryGetValue ( FaxConstants . FaxPaperNameData , out string? name ) | |
! args . Data . TryGetValue ( FaxConstants . FaxPaperContentData , out string? content ) )
return ;
2022-12-20 06:44:15 +03:00
args . Data . TryGetValue ( FaxConstants . FaxPaperStampStateData , out string? stampState ) ;
2023-08-13 19:28:10 +01:00
args . Data . TryGetValue ( FaxConstants . FaxPaperStampedByData , out List < StampDisplayInfo > ? stampedBy ) ;
2023-01-17 08:32:46 +00:00
args . Data . TryGetValue ( FaxConstants . FaxPaperPrototypeData , out string? prototypeId ) ;
2022-12-20 06:44:15 +03:00
2023-01-17 08:32:46 +00:00
var printout = new FaxPrintout ( content , name , prototypeId , stampState , stampedBy ) ;
2022-12-11 21:06:11 +03:00
Receive ( uid , printout , args . SenderAddress ) ;
break ;
}
}
}
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
private void OnToggleInterface ( EntityUid uid , FaxMachineComponent component , AfterActivatableUIOpenEvent args )
{
UpdateUserInterface ( uid , component ) ;
}
2022-12-19 10:41:47 +13:00
2024-02-13 22:14:51 -03:00
private void OnFileButtonPressed ( EntityUid uid , FaxMachineComponent component , FaxFileMessage args )
{
args . Content = args . Content [ . . Math . Min ( args . Content . Length , FaxFileMessageValidation . MaxContentSize ) ] ;
PrintFile ( uid , component , args ) ;
}
2023-12-25 02:08:15 +01:00
private void OnCopyButtonPressed ( EntityUid uid , FaxMachineComponent component , FaxCopyMessage args )
{
2024-03-13 12:03:12 +03:00
Copy ( uid , component , args ) ;
2023-12-25 02:08:15 +01:00
}
2022-12-11 21:06:11 +03:00
private void OnSendButtonPressed ( EntityUid uid , FaxMachineComponent component , FaxSendMessage args )
{
2022-12-13 19:09:45 -06:00
Send ( uid , component , args . Session . AttachedEntity ) ;
2022-12-11 21:06:11 +03:00
}
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
private void OnRefreshButtonPressed ( EntityUid uid , FaxMachineComponent component , FaxRefreshMessage args )
{
Refresh ( uid , component ) ;
}
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
private void OnDestinationSelected ( EntityUid uid , FaxMachineComponent component , FaxDestinationMessage args )
{
SetDestination ( uid , args . Address , component ) ;
}
private void UpdateAppearance ( EntityUid uid , FaxMachineComponent ? component = null )
{
if ( ! Resolve ( uid , ref component ) )
return ;
if ( component . InsertingTimeRemaining > 0 )
_appearanceSystem . SetData ( uid , FaxMachineVisuals . VisualState , FaxMachineVisualState . Inserting ) ;
else if ( component . PrintingTimeRemaining > 0 )
_appearanceSystem . SetData ( uid , FaxMachineVisuals . VisualState , FaxMachineVisualState . Printing ) ;
else
_appearanceSystem . SetData ( uid , FaxMachineVisuals . VisualState , FaxMachineVisualState . Normal ) ;
}
private void UpdateUserInterface ( EntityUid uid , FaxMachineComponent ? component = null )
{
if ( ! Resolve ( uid , ref component ) )
return ;
var isPaperInserted = component . PaperSlot . Item ! = null ;
var canSend = isPaperInserted & &
component . DestinationFaxAddress ! = null & &
component . SendTimeoutRemaining < = 0 & &
component . InsertingTimeRemaining < = 0 ;
2023-12-25 02:08:15 +01:00
var canCopy = isPaperInserted & &
component . SendTimeoutRemaining < = 0 & &
component . InsertingTimeRemaining < = 0 ;
var state = new FaxUiState ( component . FaxName , component . KnownFaxes , canSend , canCopy , isPaperInserted , component . DestinationFaxAddress ) ;
2022-12-11 21:06:11 +03:00
_userInterface . TrySetUiState ( uid , FaxUiKey . Key , state ) ;
}
/// <summary>
/// Set fax destination address not checking if he knows it exists
/// </summary>
public void SetDestination ( EntityUid uid , string destAddress , FaxMachineComponent ? component = null )
{
if ( ! Resolve ( uid , ref component ) )
return ;
component . DestinationFaxAddress = destAddress ;
UpdateUserInterface ( uid , component ) ;
}
/// <summary>
/// Clears current known fax info and make network scan ping
/// Adds special data to payload if it was emagged to identify itself as a Syndicate
/// </summary>
public void Refresh ( EntityUid uid , FaxMachineComponent ? component = null )
{
if ( ! Resolve ( uid , ref component ) )
return ;
component . DestinationFaxAddress = null ;
component . KnownFaxes . Clear ( ) ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
var payload = new NetworkPayload ( )
{
{ DeviceNetworkConstants . Command , FaxConstants . FaxPingCommand }
} ;
2023-02-19 01:03:06 +00:00
if ( HasComp < EmaggedComponent > ( uid ) )
2022-12-11 21:06:11 +03:00
payload . Add ( FaxConstants . FaxSyndicateData , true ) ;
_deviceNetworkSystem . QueuePacket ( uid , null , payload ) ;
}
2024-02-13 22:14:51 -03:00
/// <summary>
/// Makes fax print from a file from the computer. A timeout is set after copying,
/// which is shared by the send button.
/// </summary>
public void PrintFile ( EntityUid uid , FaxMachineComponent component , FaxFileMessage args )
{
string prototype ;
if ( args . OfficePaper )
prototype = OfficePaperPrototypeId ;
else
prototype = DefaultPaperPrototypeId ;
var name = Loc . GetString ( "fax-machine-printed-paper-name" ) ;
var printout = new FaxPrintout ( args . Content , name , prototype ) ;
component . PrintingQueue . Enqueue ( printout ) ;
component . SendTimeoutRemaining + = component . SendTimeout ;
UpdateUserInterface ( uid , component ) ;
2024-03-13 12:03:12 +03:00
if ( args . Session . AttachedEntity ! = null )
_adminLogger . Add ( LogType . Action , LogImpact . Low ,
$"{ToPrettyString(args.Session.AttachedEntity.Value):actor} added print job to {ToPrettyString(uid):tool} with text: {args.Content}" ) ;
else
_adminLogger . Add ( LogType . Action , LogImpact . Low ,
$"Someone added print job to {ToPrettyString(uid):tool} with text: {args.Content}" ) ;
2024-02-13 22:14:51 -03:00
}
2023-12-25 02:08:15 +01:00
/// <summary>
/// Copies the paper in the fax. A timeout is set after copying,
/// which is shared by the send button.
/// </summary>
2024-03-13 12:03:12 +03:00
public void Copy ( EntityUid uid , FaxMachineComponent ? component , FaxCopyMessage args )
2023-12-25 02:08:15 +01:00
{
if ( ! Resolve ( uid , ref component ) )
return ;
var sendEntity = component . PaperSlot . Item ;
if ( sendEntity = = null )
return ;
if ( ! TryComp < MetaDataComponent > ( sendEntity , out var metadata ) | |
! TryComp < PaperComponent > ( sendEntity , out var paper ) )
return ;
// TODO: See comment in 'Send()' about not being able to copy whole entities
var printout = new FaxPrintout ( paper . Content ,
metadata . EntityName ,
metadata . EntityPrototype ? . ID ? ? DefaultPaperPrototypeId ,
paper . StampState ,
paper . StampedBy ) ;
component . PrintingQueue . Enqueue ( printout ) ;
component . SendTimeoutRemaining + = component . SendTimeout ;
// Don't play component.SendSound - it clashes with the printing sound, which
// will start immediately.
UpdateUserInterface ( uid , component ) ;
2024-03-13 12:03:12 +03:00
if ( args . Session . AttachedEntity ! = null )
_adminLogger . Add ( LogType . Action , LogImpact . Low ,
$"{ToPrettyString(args.Session.AttachedEntity.Value):actor} added copy job to {ToPrettyString(uid):tool} with text: {ToPrettyString(component.PaperSlot.Item):subject}" ) ;
2023-12-25 02:08:15 +01:00
}
2022-12-11 21:06:11 +03:00
/// <summary>
/// Sends message to addressee if paper is set and a known fax is selected
2023-12-25 02:08:15 +01:00
/// A timeout is set after sending, which is shared by the copy button.
2022-12-11 21:06:11 +03:00
/// </summary>
2022-12-13 19:09:45 -06:00
public void Send ( EntityUid uid , FaxMachineComponent ? component = null , EntityUid ? sender = null )
2022-12-11 21:06:11 +03:00
{
if ( ! Resolve ( uid , ref component ) )
return ;
var sendEntity = component . PaperSlot . Item ;
if ( sendEntity = = null )
return ;
if ( component . DestinationFaxAddress = = null )
return ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
if ( ! component . KnownFaxes . TryGetValue ( component . DestinationFaxAddress , out var faxName ) )
return ;
if ( ! TryComp < MetaDataComponent > ( sendEntity , out var metadata ) | |
! TryComp < PaperComponent > ( sendEntity , out var paper ) )
return ;
var payload = new NetworkPayload ( )
{
{ DeviceNetworkConstants . Command , FaxConstants . FaxPrintCommand } ,
{ FaxConstants . FaxPaperNameData , metadata . EntityName } ,
{ FaxConstants . FaxPaperContentData , paper . Content } ,
} ;
2022-12-20 06:44:15 +03:00
2023-01-17 08:32:46 +00:00
if ( metadata . EntityPrototype ! = null )
{
2023-01-19 03:56:45 +01:00
// TODO: Ideally, we could just make a copy of the whole entity when it's
// faxed, in order to preserve visuals, etc.. This functionality isn't
// available yet, so we'll pass along the originating prototypeId and fall
2023-12-25 02:08:15 +01:00
// back to DefaultPaperPrototypeId in SpawnPaperFromQueue if we can't find one here.
2023-01-17 08:32:46 +00:00
payload [ FaxConstants . FaxPaperPrototypeData ] = metadata . EntityPrototype . ID ;
}
2022-12-20 06:44:15 +03:00
if ( paper . StampState ! = null )
{
payload [ FaxConstants . FaxPaperStampStateData ] = paper . StampState ;
payload [ FaxConstants . FaxPaperStampedByData ] = paper . StampedBy ;
}
2023-01-17 08:32:46 +00:00
2022-12-11 21:06:11 +03:00
_deviceNetworkSystem . QueuePacket ( uid , component . DestinationFaxAddress , payload ) ;
2022-12-13 19:09:45 -06:00
_adminLogger . Add ( LogType . Action , LogImpact . Low , $"{(sender != null ? ToPrettyString(sender.Value) : " Unknown "):user} sent fax from \"{component.FaxName}\" {ToPrettyString(uid)} to {faxName} ({component.DestinationFaxAddress}): {paper.Content}" ) ;
2022-12-11 21:06:11 +03:00
component . SendTimeoutRemaining + = component . SendTimeout ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
_audioSystem . PlayPvs ( component . SendSound , uid ) ;
2022-12-19 10:41:47 +13:00
2022-12-11 21:06:11 +03:00
UpdateUserInterface ( uid , component ) ;
}
/// <summary>
/// Accepts a new message and adds it to the queue to print
/// If has parameter "notifyAdmins" also output a special message to admin chat.
/// </summary>
2023-04-16 23:20:57 -07:00
public void Receive ( EntityUid uid , FaxPrintout printout , string? fromAddress = null , FaxMachineComponent ? component = null )
2022-12-11 21:06:11 +03:00
{
if ( ! Resolve ( uid , ref component ) )
return ;
var faxName = Loc . GetString ( "fax-machine-popup-source-unknown" ) ;
2023-04-16 23:20:57 -07:00
if ( fromAddress ! = null & & component . KnownFaxes . TryGetValue ( fromAddress , out var fax ) ) // If message received from unknown fax address
faxName = fax ;
2022-12-11 21:06:11 +03:00
2022-12-19 10:41:47 +13:00
_popupSystem . PopupEntity ( Loc . GetString ( "fax-machine-popup-received" , ( "from" , faxName ) ) , uid ) ;
2022-12-11 21:06:11 +03:00
_appearanceSystem . SetData ( uid , FaxMachineVisuals . VisualState , FaxMachineVisualState . Printing ) ;
if ( component . NotifyAdmins )
NotifyAdmins ( faxName ) ;
component . PrintingQueue . Enqueue ( printout ) ;
}
private void SpawnPaperFromQueue ( EntityUid uid , FaxMachineComponent ? component = null )
{
if ( ! Resolve ( uid , ref component ) | | component . PrintingQueue . Count = = 0 )
return ;
var printout = component . PrintingQueue . Dequeue ( ) ;
2023-01-17 08:32:46 +00:00
2023-12-25 02:08:15 +01:00
var entityToSpawn = printout . PrototypeId . Length = = 0 ? DefaultPaperPrototypeId : printout . PrototypeId ;
2023-01-17 08:32:46 +00:00
var printed = EntityManager . SpawnEntity ( entityToSpawn , Transform ( uid ) . Coordinates ) ;
2022-12-11 21:06:11 +03:00
if ( TryComp < PaperComponent > ( printed , out var paper ) )
2022-12-20 06:44:15 +03:00
{
2022-12-11 21:06:11 +03:00
_paperSystem . SetContent ( printed , printout . Content ) ;
2022-12-20 06:44:15 +03:00
// Apply stamps
if ( printout . StampState ! = null )
{
2023-08-13 19:28:10 +01:00
foreach ( var stamp in printout . StampedBy )
2022-12-20 06:44:15 +03:00
{
2023-08-13 19:28:10 +01:00
_paperSystem . TryStamp ( printed , stamp , printout . StampState ) ;
2022-12-20 06:44:15 +03:00
}
}
}
2023-08-28 11:20:31 +02:00
_metaData . SetEntityName ( printed , printout . Name ) ;
2022-12-13 19:09:45 -06:00
_adminLogger . Add ( LogType . Action , LogImpact . Low , $"\" { component . FaxName } \ " {ToPrettyString(uid)} printed {ToPrettyString(printed)}: {printout.Content}" ) ;
2022-12-11 21:06:11 +03:00
}
private void NotifyAdmins ( string faxName )
{
_chat . SendAdminAnnouncement ( Loc . GetString ( "fax-machine-chat-notify" , ( "fax" , faxName ) ) ) ;
2023-04-16 23:20:57 -07:00
_audioSystem . PlayGlobal ( "/Audio/Machines/high_tech_confirm.ogg" , Filter . Empty ( ) . AddPlayers ( _adminManager . ActiveAdmins ) , false , AudioParams . Default . WithVolume ( - 8f ) ) ;
2022-12-11 21:06:11 +03:00
}
}