]> git.smokeofanarchy.ru Git - space-station-14.git/commitdiff
``NarcolepsySystem`` refactor (#40305)
authorWinkarst-cpu <74284083+Winkarst-cpu@users.noreply.github.com>
Tue, 16 Sep 2025 18:29:48 +0000 (21:29 +0300)
committerGitHub <noreply@github.com>
Tue, 16 Sep 2025 18:29:48 +0000 (20:29 +0200)
* Refactor

* Update

* Update

Content.Server/EntityEffects/EntityEffectSystem.cs
Content.Server/Traits/Assorted/NarcolepsyComponent.cs [deleted file]
Content.Server/Traits/Assorted/NarcolepsySystem.cs [deleted file]
Content.Shared/EntityEffects/Effects/ResetNarcolepsy.cs
Content.Shared/Traits/Assorted/NarcolepsyComponent.cs [new file with mode: 0644]
Content.Shared/Traits/Assorted/NarcolepsySystem.cs [new file with mode: 0644]
Resources/Prototypes/Traits/disabilities.yml

index 4e447c7fab0444571890c82fea584b877cbc0580..3a86941a34165048704bc37cab47beda22c15df3 100644 (file)
@@ -18,7 +18,6 @@ using Content.Server.Speech.Components;
 using Content.Server.Spreader;
 using Content.Server.Temperature.Components;
 using Content.Server.Temperature.Systems;
-using Content.Server.Traits.Assorted;
 using Content.Server.Zombies;
 using Content.Shared.Atmos;
 using Content.Shared.Atmos.Components;
@@ -33,6 +32,7 @@ using Content.Shared.Maps;
 using Content.Shared.Mind.Components;
 using Content.Shared.Popups;
 using Content.Shared.Random;
+using Content.Shared.Traits.Assorted;
 using Content.Shared.Zombies;
 using Robust.Server.GameObjects;
 using Robust.Shared.Audio;
diff --git a/Content.Server/Traits/Assorted/NarcolepsyComponent.cs b/Content.Server/Traits/Assorted/NarcolepsyComponent.cs
deleted file mode 100644 (file)
index efa3458..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-using System.Numerics;
-
-namespace Content.Server.Traits.Assorted;
-
-/// <summary>
-/// This is used for the narcolepsy trait.
-/// </summary>
-[RegisterComponent, Access(typeof(NarcolepsySystem))]
-public sealed partial class NarcolepsyComponent : Component
-{
-    /// <summary>
-    /// The random time between incidents, (min, max).
-    /// </summary>
-    [DataField("timeBetweenIncidents", required: true)]
-    public Vector2 TimeBetweenIncidents { get; private set; }
-
-    /// <summary>
-    /// The duration of incidents, (min, max).
-    /// </summary>
-    [DataField("durationOfIncident", required: true)]
-    public Vector2 DurationOfIncident { get; private set; }
-
-    public float NextIncidentTime;
-}
diff --git a/Content.Server/Traits/Assorted/NarcolepsySystem.cs b/Content.Server/Traits/Assorted/NarcolepsySystem.cs
deleted file mode 100644 (file)
index 159e953..0000000
+++ /dev/null
@@ -1,59 +0,0 @@
-using Content.Shared.Bed.Sleep;
-using Content.Shared.StatusEffectNew;
-using Robust.Shared.Random;
-
-namespace Content.Server.Traits.Assorted;
-
-/// <summary>
-/// This handles narcolepsy, causing the affected to fall asleep uncontrollably at a random interval.
-/// </summary>
-public sealed class NarcolepsySystem : EntitySystem
-{
-    [Dependency] private readonly StatusEffectsSystem _statusEffects = default!;
-    [Dependency] private readonly IRobustRandom _random = default!;
-
-    /// <inheritdoc/>
-    public override void Initialize()
-    {
-        SubscribeLocalEvent<NarcolepsyComponent, ComponentStartup>(SetupNarcolepsy);
-    }
-
-    private void SetupNarcolepsy(EntityUid uid, NarcolepsyComponent component, ComponentStartup args)
-    {
-        component.NextIncidentTime =
-            _random.NextFloat(component.TimeBetweenIncidents.X, component.TimeBetweenIncidents.Y);
-    }
-
-    public void AdjustNarcolepsyTimer(EntityUid uid, int TimerReset, NarcolepsyComponent? narcolepsy = null)
-    {
-        if (!Resolve(uid, ref narcolepsy, false))
-            return;
-
-        narcolepsy.NextIncidentTime = TimerReset;
-    }
-
-    public override void Update(float frameTime)
-    {
-        base.Update(frameTime);
-
-        var query = EntityQueryEnumerator<NarcolepsyComponent>();
-        while (query.MoveNext(out var uid, out var narcolepsy))
-        {
-            narcolepsy.NextIncidentTime -= frameTime;
-
-            if (narcolepsy.NextIncidentTime >= 0)
-                continue;
-
-            // Set the new time.
-            narcolepsy.NextIncidentTime +=
-                _random.NextFloat(narcolepsy.TimeBetweenIncidents.X, narcolepsy.TimeBetweenIncidents.Y);
-
-            var duration = _random.NextFloat(narcolepsy.DurationOfIncident.X, narcolepsy.DurationOfIncident.Y);
-
-            // Make sure the sleep time doesn't cut into the time to next incident.
-            narcolepsy.NextIncidentTime += duration;
-
-            _statusEffects.TryAddStatusEffectDuration(uid, SleepingSystem.StatusEffectForcedSleeping, TimeSpan.FromSeconds(duration));
-        }
-    }
-}
index 71d228aece5c73f50f18d169df61519ed8e5b2c8..009cf914d5dae56ad4d5afb31f58733f5f126aeb 100644 (file)
@@ -12,7 +12,7 @@ public sealed partial class ResetNarcolepsy : EventEntityEffect<ResetNarcolepsy>
     /// The # of seconds the effect resets the narcolepsy timer to
     /// </summary>
     [DataField("TimerReset")]
-    public int TimerReset = 600;
+    public TimeSpan TimerReset = TimeSpan.FromSeconds(600);
 
     protected override string? ReagentEffectGuidebookText(IPrototypeManager prototype, IEntitySystemManager entSys)
         => Loc.GetString("reagent-effect-guidebook-reset-narcolepsy", ("chance", Probability));
diff --git a/Content.Shared/Traits/Assorted/NarcolepsyComponent.cs b/Content.Shared/Traits/Assorted/NarcolepsyComponent.cs
new file mode 100644 (file)
index 0000000..ae94908
--- /dev/null
@@ -0,0 +1,44 @@
+using Robust.Shared.GameStates;
+using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom;
+
+namespace Content.Shared.Traits.Assorted;
+
+/// <summary>
+/// This is used for the narcolepsy trait.
+/// </summary>
+[RegisterComponent, NetworkedComponent]
+[AutoGenerateComponentState(fieldDeltas: true), AutoGenerateComponentPause]
+[Access(typeof(NarcolepsySystem))]
+public sealed partial class NarcolepsyComponent : Component
+{
+    /// <summary>
+    /// The maximum time between incidents.
+    /// </summary>
+    [DataField(required: true), AutoNetworkedField]
+    public TimeSpan MaxTimeBetweenIncidents;
+
+    /// <summary>
+    /// The minimum time between incidents.
+    /// </summary>
+    [DataField(required: true), AutoNetworkedField]
+    public TimeSpan MinTimeBetweenIncidents;
+
+    /// <summary>
+    /// The maximum duration of incidents.
+    /// </summary>
+    [DataField(required: true), AutoNetworkedField]
+    public TimeSpan MaxDurationOfIncident;
+
+    /// <summary>
+    /// The minimum duration of incidents.
+    /// </summary>
+    [DataField(required: true), AutoNetworkedField]
+    public TimeSpan MinDurationOfIncident;
+
+    /// <summary>
+    /// Next time indcident happens.
+    /// </summary>
+    [DataField(customTypeSerializer: typeof(TimeOffsetSerializer))]
+    [AutoNetworkedField, AutoPausedField]
+    public TimeSpan NextIncidentTime = TimeSpan.Zero;
+}
diff --git a/Content.Shared/Traits/Assorted/NarcolepsySystem.cs b/Content.Shared/Traits/Assorted/NarcolepsySystem.cs
new file mode 100644 (file)
index 0000000..7bce80c
--- /dev/null
@@ -0,0 +1,69 @@
+using Content.Shared.Bed.Sleep;
+using Content.Shared.Random.Helpers;
+using Content.Shared.StatusEffectNew;
+using Robust.Shared.Random;
+using Robust.Shared.Timing;
+
+namespace Content.Shared.Traits.Assorted;
+
+/// <summary>
+/// This handles narcolepsy, causing the affected to fall asleep uncontrollably at a random interval.
+/// </summary>
+public sealed class NarcolepsySystem : EntitySystem
+{
+    [Dependency] private readonly StatusEffectsSystem _statusEffects = default!;
+    [Dependency] private readonly IRobustRandom _random = default!;
+    [Dependency] private readonly IGameTiming _timing = default!;
+
+    /// <inheritdoc/>
+    public override void Initialize()
+    {
+        base.Initialize();
+
+        SubscribeLocalEvent<NarcolepsyComponent, MapInitEvent>(OnMapInit);
+    }
+
+    private void OnMapInit(Entity<NarcolepsyComponent> ent, ref MapInitEvent args)
+    {
+        ent.Comp.NextIncidentTime = _timing.CurTime + _random.Next(ent.Comp.MinTimeBetweenIncidents, ent.Comp.MaxTimeBetweenIncidents);
+        DirtyField(ent, ent.Comp, nameof(ent.Comp.NextIncidentTime));
+    }
+
+    /// <summary>
+    /// Changes the time until the next incident.
+    /// </summary>
+    public void AdjustNarcolepsyTimer(Entity<NarcolepsyComponent?> ent, TimeSpan time)
+    {
+        if (!Resolve(ent, ref ent.Comp, false))
+            return;
+
+        ent.Comp.NextIncidentTime = _timing.CurTime + time;
+        DirtyField(ent, ent.Comp, nameof(ent.Comp.NextIncidentTime));
+    }
+
+    public override void Update(float frameTime)
+    {
+        base.Update(frameTime);
+
+        var query = EntityQueryEnumerator<NarcolepsyComponent>();
+
+        while (query.MoveNext(out var uid, out var narcolepsy))
+        {
+            if (narcolepsy.NextIncidentTime > _timing.CurTime)
+                continue;
+
+            // TODO: Replace with RandomPredicted once the engine PR is merged
+            var seed = SharedRandomExtensions.HashCodeCombine(new() { (int)_timing.CurTick.Value, GetNetEntity(uid).Id });
+            var rand = new System.Random(seed);
+
+            var duration = narcolepsy.MinDurationOfIncident + (narcolepsy.MaxDurationOfIncident - narcolepsy.MinDurationOfIncident) * rand.NextDouble();
+
+            // Set the new time.
+            narcolepsy.NextIncidentTime +=
+                narcolepsy.MinTimeBetweenIncidents + (narcolepsy.MaxTimeBetweenIncidents - narcolepsy.MinTimeBetweenIncidents) * rand.NextDouble() + duration;
+            DirtyField(uid, narcolepsy, nameof(narcolepsy.NextIncidentTime));
+
+            _statusEffects.TryAddStatusEffectDuration(uid, SleepingSystem.StatusEffectForcedSleeping, duration);
+        }
+    }
+}
index c5356149f2b2b90342b375515af8ab36ea193c12..51993d3dd117a645d6c16148af62879b3b5b7d68 100644 (file)
   category: Disabilities
   components:
     - type: Narcolepsy
-      timeBetweenIncidents: 300, 600
-      durationOfIncident: 10, 30
+      maxTimeBetweenIncidents: 600
+      minTimeBetweenIncidents: 300
+      maxDurationOfIncident: 30
+      minDurationOfIncident: 10
 
 - type: trait
   id: Unrevivable