2020-04-09 00:28:56 +02:00
using System ;
using System.Threading ;
2020-09-23 11:53:31 +02:00
using Content.Server.Interfaces.Chat ;
2020-04-09 00:28:56 +02:00
using Content.Server.Interfaces.GameTicking ;
2020-11-26 17:07:46 +00:00
using Content.Shared.GameTicking ;
2021-01-01 16:34:54 +01:00
using Robust.Server.GameObjects.EntitySystems ;
2020-04-09 00:28:56 +02:00
using Robust.Shared.GameObjects.Systems ;
2020-04-09 20:28:22 +02:00
using Robust.Shared.Interfaces.Timing ;
2020-04-09 00:28:56 +02:00
using Robust.Shared.IoC ;
2020-09-23 11:53:31 +02:00
using Robust.Shared.Localization ;
2020-04-09 00:28:56 +02:00
using Timer = Robust . Shared . Timers . Timer ;
2020-08-13 14:40:27 +02:00
namespace Content.Server.GameObjects.EntitySystems
2020-04-09 00:28:56 +02:00
{
2020-11-26 17:07:46 +00:00
public class RoundEndSystem : EntitySystem , IResettingEntitySystem
2020-04-09 00:28:56 +02:00
{
2020-08-24 14:10:28 +02:00
[Dependency] private readonly IGameTicker _gameTicker = default ! ;
[Dependency] private readonly IGameTiming _gameTiming = default ! ;
2020-09-23 11:53:31 +02:00
[Dependency] private readonly IChatManager _chatManager = default ! ;
public const float RestartRoundTime = 20f ;
2020-04-09 00:28:56 +02:00
2020-11-27 11:00:49 +01:00
private CancellationTokenSource _roundEndCancellationTokenSource = new ( ) ;
2020-04-09 00:28:56 +02:00
public bool IsRoundEndCountdownStarted { get ; private set ; }
2020-04-10 13:37:13 +02:00
public TimeSpan RoundEndCountdownTime { get ; set ; } = TimeSpan . FromMinutes ( 4 ) ;
2020-04-09 20:28:22 +02:00
public TimeSpan ? ExpectedCountdownEnd = null ;
2020-04-09 00:28:56 +02:00
public delegate void RoundEndCountdownStarted ( ) ;
public event RoundEndCountdownStarted OnRoundEndCountdownStarted ;
public delegate void RoundEndCountdownCancelled ( ) ;
public event RoundEndCountdownCancelled OnRoundEndCountdownCancelled ;
public delegate void RoundEndCountdownFinished ( ) ;
public event RoundEndCountdownFinished OnRoundEndCountdownFinished ;
2020-11-26 17:07:46 +00:00
void IResettingEntitySystem . Reset ( )
{
IsRoundEndCountdownStarted = false ;
_roundEndCancellationTokenSource . Cancel ( ) ;
_roundEndCancellationTokenSource = new CancellationTokenSource ( ) ;
ExpectedCountdownEnd = null ;
}
2020-04-09 00:28:56 +02:00
public void RequestRoundEnd ( )
{
if ( IsRoundEndCountdownStarted )
return ;
IsRoundEndCountdownStarted = true ;
2021-01-01 16:34:54 +01:00
_chatManager . DispatchStationAnnouncement ( Loc . GetString ( "An emergency shuttle has been sent. ETA: {0} minutes." , RoundEndCountdownTime . Minutes ) , Loc . GetString ( "Station" ) ) ;
Get < AudioSystem > ( ) . PlayGlobal ( "/Audio/Announcements/shuttlecalled.ogg" ) ;
2020-04-10 13:37:13 +02:00
ExpectedCountdownEnd = _gameTiming . CurTime + RoundEndCountdownTime ;
2020-04-09 00:28:56 +02:00
Timer . Spawn ( RoundEndCountdownTime , EndRound , _roundEndCancellationTokenSource . Token ) ;
OnRoundEndCountdownStarted ? . Invoke ( ) ;
}
public void CancelRoundEndCountdown ( )
{
2020-04-09 01:43:28 +02:00
if ( ! IsRoundEndCountdownStarted )
return ;
IsRoundEndCountdownStarted = false ;
2021-01-01 16:34:54 +01:00
_chatManager . DispatchStationAnnouncement ( Loc . GetString ( "The emergency shuttle has been recalled." ) , Loc . GetString ( "Station" ) ) ;
Get < AudioSystem > ( ) . PlayGlobal ( "/Audio/Announcements/shuttlerecalled.ogg" ) ;
2020-04-09 00:28:56 +02:00
_roundEndCancellationTokenSource . Cancel ( ) ;
_roundEndCancellationTokenSource = new CancellationTokenSource ( ) ;
ExpectedCountdownEnd = null ;
OnRoundEndCountdownCancelled ? . Invoke ( ) ;
}
private void EndRound ( )
{
OnRoundEndCountdownFinished ? . Invoke ( ) ;
_gameTicker . EndRound ( ) ;
2020-09-23 11:53:31 +02:00
_chatManager . DispatchServerAnnouncement ( Loc . GetString ( "Restarting the round in {0} seconds..." , RestartRoundTime ) ) ;
Timer . Spawn ( TimeSpan . FromSeconds ( RestartRoundTime ) , ( ) = > _gameTicker . RestartRound ( ) , CancellationToken . None ) ;
2020-04-09 00:28:56 +02:00
}
}
}