Artifact analyzer now pauses on power-loss (#22974)

* Artifact analyzer now pauses on power-loss

Instead of just cancelling the current scan, the artifact analyzer
will now pause in case of power-loss.

Scanning will automatically resume when power returns.

* Improve artifact scanning pausing

This builds upon the latest improvements in artifact scanning
regarding UI update.
This commit is contained in:
Guillaume E
2023-12-30 18:49:24 +01:00
committed by GitHub
parent 3d955677c5
commit 4fe93cf456
5 changed files with 89 additions and 9 deletions

View File

@@ -10,11 +10,24 @@ namespace Content.Server.Xenoarchaeology.Equipment.Components;
public sealed partial class ActiveArtifactAnalyzerComponent : Component
{
/// <summary>
/// When did the scanning start?
/// When did the scanning start or last resume?
/// </summary>
[DataField("startTime", customTypeSerializer: typeof(TimespanSerializer))]
public TimeSpan StartTime;
/// <summary>
/// When pausing, this will store the duration the scan has already been running for.
/// </summary>
[ViewVariables(VVAccess.ReadWrite)]
public TimeSpan AccumulatedRunTime;
/// <summary>
/// Is analysis paused?
/// It could be when the Artifact Analyzer has no power, for example.
/// </summary>
[ViewVariables(VVAccess.ReadWrite)]
public bool AnalysisPaused = false;
/// <summary>
/// What is being scanned?
/// </summary>

View File

@@ -79,7 +79,10 @@ public sealed class ArtifactAnalyzerSystem : EntitySystem
var query = EntityQueryEnumerator<ActiveArtifactAnalyzerComponent, ArtifactAnalyzerComponent>();
while (query.MoveNext(out var uid, out var active, out var scan))
{
if (_timing.CurTime - active.StartTime < scan.AnalysisDuration * scan.AnalysisDurationMulitplier)
if (active.AnalysisPaused)
continue;
if (_timing.CurTime - active.StartTime < scan.AnalysisDuration * scan.AnalysisDurationMulitplier - active.AccumulatedRunTime)
continue;
FinishScan(uid, scan, active);
@@ -209,9 +212,11 @@ public sealed class ArtifactAnalyzerSystem : EntitySystem
var serverConnected = TryComp<ResearchClientComponent>(uid, out var client) && client.ConnectedToServer;
var scanning = TryComp<ActiveArtifactAnalyzerComponent>(component.AnalyzerEntity, out var active);
var paused = active != null ? active.AnalysisPaused : false;
var state = new AnalysisConsoleScanUpdateState(GetNetEntity(artifact), analyzerConnected, serverConnected,
canScan, canPrint, msg, scanning, active?.StartTime, totalTime, points);
canScan, canPrint, msg, scanning, paused, active?.StartTime, active?.AccumulatedRunTime, totalTime, points);
var bui = _ui.GetUi(uid, ArtifactAnalzyerUiKey.Key);
_ui.SetUiState(bui, state);
@@ -248,8 +253,12 @@ public sealed class ArtifactAnalyzerSystem : EntitySystem
var activeComp = EnsureComp<ActiveArtifactAnalyzerComponent>(component.AnalyzerEntity.Value);
activeComp.StartTime = _timing.CurTime;
activeComp.AccumulatedRunTime = TimeSpan.Zero;
activeComp.Artifact = ent.Value;
if (TryComp<ApcPowerReceiverComponent>(component.AnalyzerEntity.Value, out var powa))
activeComp.AnalysisPaused = !powa.Powered;
var activeArtifact = EnsureComp<ActiveScannedArtifactComponent>(ent.Value);
activeArtifact.Scanner = component.AnalyzerEntity.Value;
UpdateUserInterface(uid, component);
@@ -415,6 +424,33 @@ public sealed class ArtifactAnalyzerSystem : EntitySystem
UpdateUserInterface(component.Console.Value);
}
[PublicAPI]
public void PauseScan(EntityUid uid, ArtifactAnalyzerComponent? component = null, ActiveArtifactAnalyzerComponent? active = null)
{
if (!Resolve(uid, ref component, ref active) || active.AnalysisPaused)
return;
active.AnalysisPaused = true;
// As we pause, we store what was already completed.
active.AccumulatedRunTime = (_timing.CurTime - active.StartTime) + active.AccumulatedRunTime;
if (Exists(component.Console))
UpdateUserInterface(component.Console.Value);
}
[PublicAPI]
public void ResumeScan(EntityUid uid, ArtifactAnalyzerComponent? component = null, ActiveArtifactAnalyzerComponent? active = null)
{
if (!Resolve(uid, ref component, ref active) || !active.AnalysisPaused)
return;
active.StartTime = _timing.CurTime;
active.AnalysisPaused = false;
if (Exists(component.Console))
UpdateUserInterface(component.Console.Value);
}
private void OnRefreshParts(EntityUid uid, ArtifactAnalyzerComponent component, RefreshPartsEvent args)
{
var analysisRating = args.PartRatings[component.MachinePartAnalysisDuration];
@@ -462,10 +498,16 @@ public sealed class ArtifactAnalyzerSystem : EntitySystem
_ambientSound.SetAmbience(uid, false);
}
private void OnPowerChanged(EntityUid uid, ActiveArtifactAnalyzerComponent component, ref PowerChangedEvent args)
private void OnPowerChanged(EntityUid uid, ActiveArtifactAnalyzerComponent active, ref PowerChangedEvent args)
{
if (!args.Powered)
CancelScan(component.Artifact);
{
PauseScan(uid, null, active);
}
else
{
ResumeScan(uid, null, active);
}
}
}