From cdbe92d37d65b6adc89d45f66825ad502ad4549f Mon Sep 17 00:00:00 2001 From: Hannah Giovanna Dawson Date: Mon, 27 Oct 2025 19:53:04 +0000 Subject: [PATCH] Update DamageableSystem to modern standards (#39417) * Update DamageableSystem to modern standards * DamageContainerId -> DamageContainerID with lint flag * Replace strings with protoids * Make CVar subscription declarations all consistently whitespaced * ChangeDamage -> TryChangeDamage, cope with C# jank * Revert event signature changes * Restore a comment * Re-add two queries * Init the queries * Use appearanceQuery in DamageChanged * Use damageableQuery in TryChangeDamage * Use damageableQuery in SetDamageModifierSetId * Final cleanup, fix sandboxing * Rectify ExplosionSystem:::ProcessEntity's call to TryChangeDamage * Re-organize DamageableSystem * first big fuck you breaking change. * THATS A LOT OF DAMAGE!!! * Fix test fails * test fixes 2 * push it --------- Co-authored-by: Princess Cheeseballs <66055347+Pronana@users.noreply.github.com> --- Content.Benchmarks/DestructibleBenchmark.cs | 3 +- Content.Client/Damage/DamageVisualsSystem.cs | 1 + .../UI/HealthAnalyzerWindow.xaml.cs | 8 +- .../Overlays/EntityHealthBarOverlay.cs | 2 +- .../Overlays/ShowHealthIconsSystem.cs | 2 +- .../DamageOverlayUiController.cs | 2 +- .../Tests/Commands/RejuvenateTest.cs | 2 + .../Tests/Commands/SuicideCommandTests.cs | 6 +- .../Construction/Interaction/WindowRepair.cs | 4 +- .../Tests/Damageable/DamageableTest.cs | 12 +- .../DestructibleDamageGroupTest.cs | 6 +- .../DestructibleDamageTypeTest.cs | 2 + .../DestructibleDestructionTest.cs | 1 + .../DestructibleThresholdActivationTest.cs | 8 +- .../Tests/GameRules/NukeOpsTest.cs | 2 +- .../Tests/Minds/MindTests.cs | 4 +- .../Tests/Mousetrap/MousetrapTest.cs | 3 +- .../Tests/Storage/EntityStorageTests.cs | 1 + .../Tests/Vending/VendingInteractionTest.cs | 4 +- .../Tests/VendingMachineRestockTest.cs | 9 +- .../Tests/Weapons/WeaponTests.cs | 2 +- .../Access/Systems/IdCardConsoleSystem.cs | 1 + .../Systems/AdminVerbSystem.Smites.cs | 3 +- .../AtmosphereSystem.DeltaPressure.cs | 2 +- .../Atmos/EntitySystems/AtmosphereSystem.cs | 2 +- .../Atmos/EntitySystems/BarotraumaSystem.cs | 3 +- .../Atmos/EntitySystems/FlammableSystem.cs | 2 +- Content.Server/Atmos/Rotting/RottingSystem.cs | 2 +- Content.Server/Bed/BedSystem.cs | 2 +- Content.Server/Bible/BibleSystem.cs | 7 +- .../Body/Systems/RespiratorSystem.cs | 6 +- .../CardboardBox/CardboardBoxSystem.cs | 14 +- Content.Server/Chat/SuicideSystem.cs | 2 +- .../Chat/Systems/EmoteOnDamageSystem.cs | 2 + Content.Server/Cloning/CloningPodSystem.cs | 2 +- Content.Server/Cluwne/CluwneSystem.cs | 2 +- .../Construction/Conditions/MinHealth.cs | 7 +- Content.Server/Damage/Commands/HurtCommand.cs | 2 +- .../Damage/ForceSay/DamageForceSaySystem.cs | 1 + .../Damage/Systems/DamageOnHitSystem.cs | 3 +- .../Damage/Systems/DamageOnLandSystem.cs | 2 +- .../Systems/DamageOnToolInteractSystem.cs | 14 +- .../Damage/Systems/DamageOtherOnHitSystem.cs | 8 +- .../Damage/Systems/DamageRandomPopupSystem.cs | 1 + .../Damage/Systems/ExaminableDamageSystem.cs | 2 +- .../DestructibleSystem.BenchmarkHelpers.cs | 4 +- .../Destructible/DestructibleSystem.cs | 5 +- .../Disposal/Unit/DisposableSystem.cs | 2 +- Content.Server/Dragon/DragonRiftSystem.cs | 4 +- .../Electrocution/ElectrocutionSystem.cs | 14 +- .../EntitySystems/ExplosionSystem.Airtight.cs | 4 +- .../ExplosionSystem.Processing.cs | 37 +- .../EntitySystems/ExplosionSystem.cs | 3 +- Content.Server/Ghost/GhostSystem.cs | 5 +- Content.Server/Guardian/GuardianSystem.cs | 6 +- .../ImmovableRod/ImmovableRodSystem.cs | 3 +- .../KillTracking/KillTrackingSystem.cs | 1 + .../Kitchen/EntitySystems/MicrowaveSystem.cs | 4 +- .../Lightning/LightningTargetSystem.cs | 3 +- Content.Server/Mech/Systems/MechSystem.cs | 4 +- Content.Server/Medical/DefibrillatorSystem.cs | 3 +- .../Medical/HealthAnalyzerSystem.cs | 2 +- Content.Server/Mining/MeteorSystem.cs | 3 +- .../Specific/PickNearbyInjectableOperator.cs | 2 +- .../NPC/Systems/NPCRetaliationSystem.cs | 1 + .../NPC/Systems/NPCUtilitySystem.cs | 2 +- .../Ninja/Systems/StunProviderSystem.cs | 6 +- .../EntitySystems/SmokingSystem.Vape.cs | 2 +- .../Polymorph/Systems/PolymorphSystem.cs | 7 +- .../Projectiles/ProjectileSystem.cs | 72 +-- .../EntitySystems/RevenantSystem.Abilities.cs | 2 +- .../Revenant/EntitySystems/RevenantSystem.cs | 2 +- .../Shuttles/Systems/ShuttleSystem.Impact.cs | 3 +- .../Shuttles/Systems/ShuttleSystem.cs | 2 +- .../Shuttles/Systems/ThrusterSystem.cs | 4 +- .../Silicons/Borgs/BorgSystem.Transponder.cs | 2 +- .../Silicons/StationAi/StationAiSystem.cs | 8 +- .../DamagedSiliconAccentSystem.cs | 2 +- Content.Server/Spreader/KudzuSystem.cs | 3 +- .../Temperature/Systems/TemperatureSystem.cs | 3 +- .../VendingMachines/VendingMachineSystem.cs | 1 + .../Ranged/Systems/GunSystem.AutoFire.cs | 2 +- .../Zombies/ZombieSystem.Transform.cs | 6 +- Content.Server/Zombies/ZombieSystem.cs | 11 +- Content.Shared/Armor/SharedArmorSystem.cs | 1 + Content.Shared/Bed/Sleep/SleepingSystem.cs | 1 + .../Blocking/BlockingSystem.User.cs | 48 +- .../Body/Systems/SharedBloodstreamSystem.cs | 5 +- .../Body/Systems/SharedBodySystem.Parts.cs | 2 +- .../Body/Systems/SharedBodySystem.cs | 2 +- .../Systems/ChangelingDevourSystem.cs | 5 +- Content.Shared/Chat/SharedSuicideSystem.cs | 8 +- .../Climbing/Systems/ClimbSystem.cs | 2 +- .../Clothing/SharedCursedMaskSystem.cs | 1 + Content.Shared/Clumsy/ClumsySystem.cs | 8 +- .../ClothingSlowOnDamageModifierComponent.cs | 1 + .../Damage/Components/DamageableComponent.cs | 182 +++---- .../Components/IgnoreSlowOnDamageComponent.cs | 1 + .../RequireProjectileTargetComponent.cs | 1 + Content.Shared/Damage/DamageModifierSet.cs | 1 + Content.Shared/Damage/DamageSpecifier.cs | 1 + .../Prototypes/DamageContainerPrototype.cs | 2 +- .../Damage/Prototypes/DamageGroupPrototype.cs | 2 +- .../Damage/Systems/DamageOnAttackedSystem.cs | 4 +- .../Damage/Systems/DamageOnInteractSystem.cs | 6 +- .../Damage/Systems/DamageableSystem.API.cs | 235 ++++++++ .../DamageableSystem.BenchmarkHelpers.cs | 6 +- .../Damage/Systems/DamageableSystem.Events.cs | 290 ++++++++++ .../Damage/Systems/DamageableSystem.cs | 510 +++--------------- .../Damage/Systems/PassiveDamageSystem.cs | 6 +- .../Systems/RequireProjectileTargetSystem.cs | 7 +- .../Damage/Systems/SharedGodmodeSystem.cs | 4 +- .../Damage/Systems/SlowOnDamageSystem.cs | 183 ++++--- .../Destructible/Triggers/AndTrigger.cs | 2 +- .../Triggers/DamageGroupTrigger.cs | 2 +- .../Destructible/Triggers/DamageTrigger.cs | 2 +- .../Triggers/DamageTypeTrigger.cs | 2 +- .../Triggers/IThresholdTrigger.cs | 2 +- .../Destructible/Triggers/OrTrigger.cs | 2 +- Content.Shared/DoAfter/SharedDoAfterSystem.cs | 1 + .../Doors/Systems/SharedDoorSystem.cs | 2 +- .../DamageGroupEntityConditionSystem.cs | 2 +- .../DamageTypeEntityConditionSystem.cs | 1 + .../TotalDamageEntityConditionSystem.cs | 2 +- .../EvenHealthChangeEntityEffectSystem.cs | 7 +- .../Effects/HealthChangeEntityEffectSystem.cs | 11 +- .../Execution/SharedExecutionSystem.cs | 3 +- Content.Shared/Fax/Systems/FaxecuteSystem.cs | 4 +- .../Flash/DamagedByFlashingSystem.cs | 4 +- .../HealthExaminableSystem.cs | 2 +- .../Implants/SharedImplanterSystem.cs | 2 +- .../Inventory/InventorySystem.Relay.cs | 1 + .../Kitchen/SharedKitchenSpikeSystem.cs | 6 +- .../Medical/Healing/HealingSystem.cs | 9 +- .../Medical/Stethoscope/StethoscopeSystem.cs | 2 +- .../SuitSensors/SharedSuitSensorSystem.cs | 2 +- .../Mobs/Components/MobStateComponent.cs | 3 +- .../Systems/MobStateSystem.Subscribers.cs | 1 + Content.Shared/Mobs/Systems/MobStateSystem.cs | 3 +- .../Mobs/Systems/MobThresholdSystem.cs | 2 + .../Nutrition/EntitySystems/HungerSystem.cs | 4 +- .../Systems/SharedChameleonProjectorSystem.cs | 2 +- Content.Shared/Repairable/RepairableSystem.cs | 9 +- .../Silicons/Borgs/SharedBorgSystem.Relay.cs | 1 + Content.Shared/Silicons/Bots/MedibotSystem.cs | 8 +- .../EntitySystems/SecretStashSystem.cs | 2 +- .../Stunnable/SharedStunSystem.Knockdown.cs | 1 + .../Trigger/Systems/DamageOnTriggerSystem.cs | 4 +- .../Turrets/SharedDeployableTurretSystem.cs | 6 +- .../Systems/HitscanBasicDamageSystem.cs | 6 +- .../Marker/SharedDamageMarkerSystem.cs | 2 +- .../Weapons/Melee/SharedMeleeWeaponSystem.cs | 10 +- .../Weapons/Ranged/Systems/SharedGunSystem.cs | 1 + .../Artifact/SharedXenoArtifactSystem.XAT.cs | 1 + .../Artifact/XAE/XAEDamageInAreaSystem.cs | 1 + .../XAT/XATDamageThresholdReachedSystem.cs | 1 + .../Equipment/SharedArtifactCrusherSystem.cs | 2 +- 157 files changed, 1127 insertions(+), 967 deletions(-) create mode 100644 Content.Shared/Damage/Systems/DamageableSystem.API.cs create mode 100644 Content.Shared/Damage/Systems/DamageableSystem.Events.cs diff --git a/Content.Benchmarks/DestructibleBenchmark.cs b/Content.Benchmarks/DestructibleBenchmark.cs index b91837e7ca..1b54bacca0 100644 --- a/Content.Benchmarks/DestructibleBenchmark.cs +++ b/Content.Benchmarks/DestructibleBenchmark.cs @@ -1,12 +1,13 @@ using System.Collections.Generic; -using System.Diagnostics; using System.Threading.Tasks; using BenchmarkDotNet.Attributes; using Content.IntegrationTests; using Content.IntegrationTests.Pair; using Content.Server.Destructible; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.Maps; using Robust.Shared; diff --git a/Content.Client/Damage/DamageVisualsSystem.cs b/Content.Client/Damage/DamageVisualsSystem.cs index 065bf628bc..ac3ff819aa 100644 --- a/Content.Client/Damage/DamageVisualsSystem.cs +++ b/Content.Client/Damage/DamageVisualsSystem.cs @@ -1,5 +1,6 @@ using System.Linq; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; using Content.Shared.FixedPoint; using Robust.Client.GameObjects; diff --git a/Content.Client/HealthAnalyzer/UI/HealthAnalyzerWindow.xaml.cs b/Content.Client/HealthAnalyzer/UI/HealthAnalyzerWindow.xaml.cs index 225619b031..533a8b9f2c 100644 --- a/Content.Client/HealthAnalyzer/UI/HealthAnalyzerWindow.xaml.cs +++ b/Content.Client/HealthAnalyzer/UI/HealthAnalyzerWindow.xaml.cs @@ -1,28 +1,22 @@ using System.Linq; using System.Numerics; -using Content.Client.Message; using Content.Shared.Atmos; using Content.Client.UserInterface.Controls; -using Content.Shared.Alert; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; using Content.Shared.FixedPoint; using Content.Shared.Humanoid; using Content.Shared.Humanoid.Prototypes; using Content.Shared.IdentityManagement; -using Content.Shared.Inventory; using Content.Shared.MedicalScanner; using Content.Shared.Mobs; using Content.Shared.Mobs.Components; -using Content.Shared.Mobs.Systems; -using Content.Shared.Nutrition.Components; using Robust.Client.AutoGenerated; using Robust.Client.UserInterface.XAML; using Robust.Client.GameObjects; using Robust.Client.Graphics; using Robust.Client.UserInterface.Controls; using Robust.Client.ResourceManagement; -using Robust.Client.UserInterface; using Robust.Shared.Prototypes; using Robust.Shared.Utility; diff --git a/Content.Client/Overlays/EntityHealthBarOverlay.cs b/Content.Client/Overlays/EntityHealthBarOverlay.cs index cf9d879844..55fc1e0974 100644 --- a/Content.Client/Overlays/EntityHealthBarOverlay.cs +++ b/Content.Client/Overlays/EntityHealthBarOverlay.cs @@ -1,7 +1,7 @@ using System.Numerics; using Content.Client.StatusIcon; using Content.Client.UserInterface.Systems; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.FixedPoint; using Content.Shared.Mobs; using Content.Shared.Mobs.Components; diff --git a/Content.Client/Overlays/ShowHealthIconsSystem.cs b/Content.Client/Overlays/ShowHealthIconsSystem.cs index 0a875e79c5..7fbc0cd944 100644 --- a/Content.Client/Overlays/ShowHealthIconsSystem.cs +++ b/Content.Client/Overlays/ShowHealthIconsSystem.cs @@ -1,5 +1,4 @@ using Content.Shared.Atmos.Rotting; -using Content.Shared.Damage; using Content.Shared.Inventory.Events; using Content.Shared.Mobs.Components; using Content.Shared.Overlays; @@ -7,6 +6,7 @@ using Content.Shared.StatusIcon; using Content.Shared.StatusIcon.Components; using Robust.Shared.Prototypes; using System.Linq; +using Content.Shared.Damage.Components; namespace Content.Client.Overlays; diff --git a/Content.Client/UserInterface/Systems/DamageOverlays/DamageOverlayUiController.cs b/Content.Client/UserInterface/Systems/DamageOverlays/DamageOverlayUiController.cs index 55d00fec18..20db76554d 100644 --- a/Content.Client/UserInterface/Systems/DamageOverlays/DamageOverlayUiController.cs +++ b/Content.Client/UserInterface/Systems/DamageOverlays/DamageOverlayUiController.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.FixedPoint; using Content.Shared.Mobs; using Content.Shared.Mobs.Components; diff --git a/Content.IntegrationTests/Tests/Commands/RejuvenateTest.cs b/Content.IntegrationTests/Tests/Commands/RejuvenateTest.cs index 53604b2c1e..87ff00691a 100644 --- a/Content.IntegrationTests/Tests/Commands/RejuvenateTest.cs +++ b/Content.IntegrationTests/Tests/Commands/RejuvenateTest.cs @@ -1,6 +1,8 @@ using Content.Shared.Administration.Systems; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.Mobs.Components; using Content.Shared.Mobs.Systems; diff --git a/Content.IntegrationTests/Tests/Commands/SuicideCommandTests.cs b/Content.IntegrationTests/Tests/Commands/SuicideCommandTests.cs index c232ccf415..57e8bfd449 100644 --- a/Content.IntegrationTests/Tests/Commands/SuicideCommandTests.cs +++ b/Content.IntegrationTests/Tests/Commands/SuicideCommandTests.cs @@ -1,6 +1,8 @@ using System.Linq; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.Execution; using Content.Shared.FixedPoint; using Content.Shared.Ghost; @@ -280,7 +282,7 @@ public sealed class SuicideCommandTests await server.WaitAssertion(() => { // Heal all damage first (possible low pressure damage taken) - damageableSystem.SetAllDamage(player, damageableComp, 0); + damageableSystem.ClearAllDamage((player, damageableComp)); consoleHost.GetSessionShell(playerMan.Sessions.First()).ExecuteCommand("suicide"); var lethalDamageThreshold = mobThresholdsComp.Thresholds.Keys.Last(); @@ -355,7 +357,7 @@ public sealed class SuicideCommandTests await server.WaitAssertion(() => { // Heal all damage first (possible low pressure damage taken) - damageableSystem.SetAllDamage(player, damageableComp, 0); + damageableSystem.ClearAllDamage((player, damageableComp)); consoleHost.GetSessionShell(playerMan.Sessions.First()).ExecuteCommand("suicide"); var lethalDamageThreshold = mobThresholdsComp.Thresholds.Keys.Last(); diff --git a/Content.IntegrationTests/Tests/Construction/Interaction/WindowRepair.cs b/Content.IntegrationTests/Tests/Construction/Interaction/WindowRepair.cs index 192604edfd..5a4d284c0f 100644 --- a/Content.IntegrationTests/Tests/Construction/Interaction/WindowRepair.cs +++ b/Content.IntegrationTests/Tests/Construction/Interaction/WindowRepair.cs @@ -1,6 +1,8 @@ using Content.IntegrationTests.Tests.Interaction; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Robust.Shared.Prototypes; @@ -21,7 +23,7 @@ public sealed class WindowRepair : InteractionTest var damageType = Server.ProtoMan.Index(BluntDamageType); var damage = new DamageSpecifier(damageType, FixedPoint2.New(10)); Assert.That(comp.Damage.GetTotal(), Is.EqualTo(FixedPoint2.Zero)); - await Server.WaitPost(() => sys.TryChangeDamage(SEntMan.GetEntity(Target), damage, ignoreResistances: true)); + await Server.WaitPost(() => sys.TryChangeDamage(SEntMan.GetEntity(Target).Value, damage, ignoreResistances: true)); await RunTicks(5); Assert.That(comp.Damage.GetTotal(), Is.GreaterThan(FixedPoint2.Zero)); diff --git a/Content.IntegrationTests/Tests/Damageable/DamageableTest.cs b/Content.IntegrationTests/Tests/Damageable/DamageableTest.cs index f610ab732e..72e8901631 100644 --- a/Content.IntegrationTests/Tests/Damageable/DamageableTest.cs +++ b/Content.IntegrationTests/Tests/Damageable/DamageableTest.cs @@ -1,5 +1,7 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Robust.Shared.GameObjects; using Robust.Shared.Map; @@ -232,10 +234,14 @@ namespace Content.IntegrationTests.Tests.Damageable Assert.That(sDamageableComponent.TotalDamage, Is.EqualTo(FixedPoint2.Zero)); }); - // Test SetAll function - sDamageableSystem.SetAllDamage(sDamageableEntity, sDamageableComponent, 10); + // Test SetAll and ClearAll function + sDamageableSystem.SetAllDamage((sDamageableEntity, sDamageableComponent), 10); Assert.That(sDamageableComponent.TotalDamage, Is.EqualTo(FixedPoint2.New(10 * sDamageableComponent.Damage.DamageDict.Count))); - sDamageableSystem.SetAllDamage(sDamageableEntity, sDamageableComponent, 0); + sDamageableSystem.SetAllDamage((sDamageableEntity, sDamageableComponent), 0); + Assert.That(sDamageableComponent.TotalDamage, Is.EqualTo(FixedPoint2.Zero)); + sDamageableSystem.SetAllDamage((sDamageableEntity, sDamageableComponent), 10); + Assert.That(sDamageableComponent.TotalDamage, Is.EqualTo(FixedPoint2.New(10 * sDamageableComponent.Damage.DamageDict.Count))); + sDamageableSystem.ClearAllDamage((sDamageableEntity, sDamageableComponent)); Assert.That(sDamageableComponent.TotalDamage, Is.EqualTo(FixedPoint2.Zero)); // Test 'wasted' healing diff --git a/Content.IntegrationTests/Tests/Destructible/DestructibleDamageGroupTest.cs b/Content.IntegrationTests/Tests/Destructible/DestructibleDamageGroupTest.cs index 3650fd69d7..99f68b3fa3 100644 --- a/Content.IntegrationTests/Tests/Destructible/DestructibleDamageGroupTest.cs +++ b/Content.IntegrationTests/Tests/Destructible/DestructibleDamageGroupTest.cs @@ -1,5 +1,7 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.Destructible.Thresholds.Triggers; using Content.Shared.FixedPoint; using Robust.Shared.GameObjects; @@ -130,7 +132,7 @@ namespace Content.IntegrationTests.Tests.Destructible sTestThresholdListenerSystem.ThresholdsReached.Clear(); // Heal both classes of damage to 0 - sDamageableSystem.SetAllDamage(sDestructibleEntity, sDamageableComponent, 0); + sDamageableSystem.ClearAllDamage((sDestructibleEntity, sDamageableComponent)); // No new thresholds reached, healing should not trigger it Assert.That(sTestThresholdListenerSystem.ThresholdsReached, Is.Empty); @@ -174,7 +176,7 @@ namespace Content.IntegrationTests.Tests.Destructible threshold.TriggersOnce = true; // Heal brute and burn back to 0 - sDamageableSystem.SetAllDamage(sDestructibleEntity, sDamageableComponent, 0); + sDamageableSystem.ClearAllDamage((sDestructibleEntity, sDamageableComponent)); // No new thresholds reached from healing Assert.That(sTestThresholdListenerSystem.ThresholdsReached, Is.Empty); diff --git a/Content.IntegrationTests/Tests/Destructible/DestructibleDamageTypeTest.cs b/Content.IntegrationTests/Tests/Destructible/DestructibleDamageTypeTest.cs index 4b1dc1ab3b..70baaea95a 100644 --- a/Content.IntegrationTests/Tests/Destructible/DestructibleDamageTypeTest.cs +++ b/Content.IntegrationTests/Tests/Destructible/DestructibleDamageTypeTest.cs @@ -1,5 +1,7 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.Destructible.Thresholds.Triggers; using Robust.Shared.GameObjects; using Robust.Shared.Prototypes; diff --git a/Content.IntegrationTests/Tests/Destructible/DestructibleDestructionTest.cs b/Content.IntegrationTests/Tests/Destructible/DestructibleDestructionTest.cs index b1342eeafe..df98294ee9 100644 --- a/Content.IntegrationTests/Tests/Destructible/DestructibleDestructionTest.cs +++ b/Content.IntegrationTests/Tests/Destructible/DestructibleDestructionTest.cs @@ -2,6 +2,7 @@ using System.Linq; using Content.Server.Destructible.Thresholds.Behaviors; using Content.Shared.Damage; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.Destructible.Thresholds; using Robust.Shared.GameObjects; using Robust.Shared.Prototypes; diff --git a/Content.IntegrationTests/Tests/Destructible/DestructibleThresholdActivationTest.cs b/Content.IntegrationTests/Tests/Destructible/DestructibleThresholdActivationTest.cs index fb3c40ec3c..1736d3d7e3 100644 --- a/Content.IntegrationTests/Tests/Destructible/DestructibleThresholdActivationTest.cs +++ b/Content.IntegrationTests/Tests/Destructible/DestructibleThresholdActivationTest.cs @@ -3,7 +3,9 @@ using Content.Server.Destructible; using Content.Server.Destructible.Thresholds; using Content.Server.Destructible.Thresholds.Behaviors; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Robust.Shared.Audio.Systems; using Content.Shared.Destructible; @@ -124,7 +126,7 @@ namespace Content.IntegrationTests.Tests.Destructible Assert.That(sTestThresholdListenerSystem.ThresholdsReached, Is.Empty); // Set damage to 0 - sDamageableSystem.SetAllDamage(sDestructibleEntity, sDamageableComponent, 0); + sDamageableSystem.ClearAllDamage((sDestructibleEntity, sDamageableComponent)); // Damage for 100, up to 100 sDamageableSystem.TryChangeDamage(sDestructibleEntity, bluntDamage * 10, true); @@ -185,7 +187,7 @@ namespace Content.IntegrationTests.Tests.Destructible sTestThresholdListenerSystem.ThresholdsReached.Clear(); // Heal all damage - sDamageableSystem.SetAllDamage(sDestructibleEntity, sDamageableComponent, 0); + sDamageableSystem.ClearAllDamage((sDestructibleEntity, sDamageableComponent)); // Damage up to 50 sDamageableSystem.TryChangeDamage(sDestructibleEntity, bluntDamage * 5, true); @@ -247,7 +249,7 @@ namespace Content.IntegrationTests.Tests.Destructible sTestThresholdListenerSystem.ThresholdsReached.Clear(); // Heal the entity completely - sDamageableSystem.SetAllDamage(sDestructibleEntity, sDamageableComponent, 0); + sDamageableSystem.ClearAllDamage((sDestructibleEntity, sDamageableComponent)); // Check that the entity has 0 damage Assert.That(sDamageableComponent.TotalDamage, Is.EqualTo(FixedPoint2.Zero)); diff --git a/Content.IntegrationTests/Tests/GameRules/NukeOpsTest.cs b/Content.IntegrationTests/Tests/GameRules/NukeOpsTest.cs index 4f92fd4e55..246a770190 100644 --- a/Content.IntegrationTests/Tests/GameRules/NukeOpsTest.cs +++ b/Content.IntegrationTests/Tests/GameRules/NukeOpsTest.cs @@ -10,7 +10,7 @@ using Content.Server.Roles; using Content.Server.RoundEnd; using Content.Server.Shuttles.Components; using Content.Shared.CCVar; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.FixedPoint; using Content.Shared.GameTicking; using Content.Shared.Hands.Components; diff --git a/Content.IntegrationTests/Tests/Minds/MindTests.cs b/Content.IntegrationTests/Tests/Minds/MindTests.cs index 1bda6fd4db..35069339ba 100644 --- a/Content.IntegrationTests/Tests/Minds/MindTests.cs +++ b/Content.IntegrationTests/Tests/Minds/MindTests.cs @@ -4,7 +4,9 @@ using Content.Server.Ghost.Roles; using Content.Server.Ghost.Roles.Components; using Content.Server.Mind; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.Mind; using Content.Shared.Mind.Components; @@ -147,7 +149,7 @@ public sealed partial class MindTests var damageable = entMan.GetComponent(entity); var prototype = protoMan.Index(BluntDamageType); - damageableSystem.SetDamage(entity, damageable, new DamageSpecifier(prototype, FixedPoint2.New(401))); + damageableSystem.SetDamage((entity, damageable), new DamageSpecifier(prototype, FixedPoint2.New(401))); Assert.That(mindSystem.GetMind(entity, mindContainerComp), Is.EqualTo(mindId)); }); diff --git a/Content.IntegrationTests/Tests/Mousetrap/MousetrapTest.cs b/Content.IntegrationTests/Tests/Mousetrap/MousetrapTest.cs index 422d58cdcf..5f1b9172dd 100644 --- a/Content.IntegrationTests/Tests/Mousetrap/MousetrapTest.cs +++ b/Content.IntegrationTests/Tests/Mousetrap/MousetrapTest.cs @@ -1,7 +1,6 @@ using Content.IntegrationTests.Tests.Movement; using Content.Server.NPC.HTN; -using Content.Shared.Damage; -using Content.Shared.FixedPoint; +using Content.Shared.Damage.Components; using Content.Shared.Item.ItemToggle; using Content.Shared.Item.ItemToggle.Components; using Content.Shared.Mobs; diff --git a/Content.IntegrationTests/Tests/Storage/EntityStorageTests.cs b/Content.IntegrationTests/Tests/Storage/EntityStorageTests.cs index 45ee69a9ef..f80cc089de 100644 --- a/Content.IntegrationTests/Tests/Storage/EntityStorageTests.cs +++ b/Content.IntegrationTests/Tests/Storage/EntityStorageTests.cs @@ -1,5 +1,6 @@ using Content.Server.Storage.EntitySystems; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Robust.Shared.Containers; using Robust.Shared.GameObjects; diff --git a/Content.IntegrationTests/Tests/Vending/VendingInteractionTest.cs b/Content.IntegrationTests/Tests/Vending/VendingInteractionTest.cs index 3645667737..af16f1278a 100644 --- a/Content.IntegrationTests/Tests/Vending/VendingInteractionTest.cs +++ b/Content.IntegrationTests/Tests/Vending/VendingInteractionTest.cs @@ -2,7 +2,9 @@ using System.Linq; using Content.IntegrationTests.Tests.Interaction; using Content.Server.VendingMachines; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.VendingMachines; using Robust.Shared.Prototypes; @@ -200,7 +202,7 @@ public sealed class VendingInteractionTest : InteractionTest // Damage the vending machine to the point that it breaks var damageType = ProtoMan.Index(TestDamageType); var damage = new DamageSpecifier(damageType, FixedPoint2.New(100)); - await Server.WaitPost(() => damageableSys.TryChangeDamage(SEntMan.GetEntity(Target), damage, ignoreResistances: true)); + await Server.WaitPost(() => damageableSys.TryChangeDamage(SEntMan.GetEntity(Target).Value, damage, ignoreResistances: true)); await RunTicks(5); Assert.That(damageableComp.Damage.GetTotal(), Is.GreaterThan(FixedPoint2.Zero), $"{VendingMachineProtoId} did not take damage."); } diff --git a/Content.IntegrationTests/Tests/VendingMachineRestockTest.cs b/Content.IntegrationTests/Tests/VendingMachineRestockTest.cs index f30eed0651..01770fe107 100644 --- a/Content.IntegrationTests/Tests/VendingMachineRestockTest.cs +++ b/Content.IntegrationTests/Tests/VendingMachineRestockTest.cs @@ -5,6 +5,7 @@ using Content.Server.Wires; using Content.Shared.Cargo.Prototypes; using Content.Shared.Damage; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.Prototypes; using Content.Shared.Storage.Components; using Content.Shared.VendingMachines; @@ -296,14 +297,12 @@ namespace Content.IntegrationTests.Tests restock = entityManager.SpawnEntity("TestRestockExplode", coordinates); var damageSpec = new DamageSpecifier(prototypeManager.Index(TestDamageType), 100); - var damageResult = damageableSystem.TryChangeDamage(restock, damageSpec); + var damageResult = damageableSystem.ChangeDamage(restock, damageSpec); #pragma warning disable NUnit2045 - Assert.That(damageResult, Is.Not.Null, - "Received null damageResult when attempting to damage restock box."); + Assert.That(!damageResult.Empty, "Received empty damageResult when attempting to damage restock box."); - Assert.That((int) damageResult!.GetTotal(), Is.GreaterThan(0), - "Box damage result was not greater than 0."); + Assert.That((int) damageResult.GetTotal(), Is.GreaterThan(0), "Box damage result was not greater than 0."); #pragma warning restore NUnit2045 }); await server.WaitRunTicks(15); diff --git a/Content.IntegrationTests/Tests/Weapons/WeaponTests.cs b/Content.IntegrationTests/Tests/Weapons/WeaponTests.cs index bf240ba9e2..135e75f8be 100644 --- a/Content.IntegrationTests/Tests/Weapons/WeaponTests.cs +++ b/Content.IntegrationTests/Tests/Weapons/WeaponTests.cs @@ -1,5 +1,5 @@ using Content.IntegrationTests.Tests.Interaction; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Weapons.Ranged.Components; using Content.Shared.Weapons.Ranged.Systems; using Content.Shared.Wieldable.Components; diff --git a/Content.Server/Access/Systems/IdCardConsoleSystem.cs b/Content.Server/Access/Systems/IdCardConsoleSystem.cs index 7c772830ba..9f21fd68d8 100644 --- a/Content.Server/Access/Systems/IdCardConsoleSystem.cs +++ b/Content.Server/Access/Systems/IdCardConsoleSystem.cs @@ -12,6 +12,7 @@ using Content.Shared.Chat; using Content.Shared.Construction; using Content.Shared.Containers.ItemSlots; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Roles; using Content.Shared.StationRecords; diff --git a/Content.Server/Administration/Systems/AdminVerbSystem.Smites.cs b/Content.Server/Administration/Systems/AdminVerbSystem.Smites.cs index d03b799ff2..617451f955 100644 --- a/Content.Server/Administration/Systems/AdminVerbSystem.Smites.cs +++ b/Content.Server/Administration/Systems/AdminVerbSystem.Smites.cs @@ -1,6 +1,5 @@ using Content.Server.Administration.Components; using Content.Server.Atmos.EntitySystems; -using Content.Server.Body.Components; using Content.Server.Body.Systems; using Content.Server.Electrocution; using Content.Server.Explosion.EntitySystems; @@ -24,7 +23,6 @@ using Content.Shared.Body.Part; using Content.Shared.Clothing.Components; using Content.Shared.Clumsy; using Content.Shared.Cluwne; -using Content.Shared.Damage; using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Electrocution; @@ -58,6 +56,7 @@ using Robust.Shared.Spawners; using Robust.Shared.Utility; using System.Numerics; using System.Threading; +using Content.Shared.Damage.Components; using Timer = Robust.Shared.Timing.Timer; namespace Content.Server.Administration.Systems; diff --git a/Content.Server/Atmos/EntitySystems/AtmosphereSystem.DeltaPressure.cs b/Content.Server/Atmos/EntitySystems/AtmosphereSystem.DeltaPressure.cs index 255e58dcbf..d6ab2a0087 100644 --- a/Content.Server/Atmos/EntitySystems/AtmosphereSystem.DeltaPressure.cs +++ b/Content.Server/Atmos/EntitySystems/AtmosphereSystem.DeltaPressure.cs @@ -251,7 +251,7 @@ public sealed partial class AtmosphereSystem var maxPressureCapped = Math.Min(maxPressure, ent.Comp.MaxEffectivePressure); var appliedDamage = ScaleDamage(ent, ent.Comp.BaseDamage, maxPressureCapped); - _damage.TryChangeDamage(ent, appliedDamage, ignoreResistances: true, interruptsDoAfters: false); + _damage.ChangeDamage(ent.Owner, appliedDamage, ignoreResistances: true, interruptsDoAfters: false); SetIsTakingDamageState(ent, true); } diff --git a/Content.Server/Atmos/EntitySystems/AtmosphereSystem.cs b/Content.Server/Atmos/EntitySystems/AtmosphereSystem.cs index 00b7e16913..8120caca4e 100644 --- a/Content.Server/Atmos/EntitySystems/AtmosphereSystem.cs +++ b/Content.Server/Atmos/EntitySystems/AtmosphereSystem.cs @@ -14,7 +14,7 @@ using Robust.Shared.Map; using Robust.Shared.Physics.Systems; using Robust.Shared.Prototypes; using System.Linq; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Robust.Shared.Threading; namespace Content.Server.Atmos.EntitySystems; diff --git a/Content.Server/Atmos/EntitySystems/BarotraumaSystem.cs b/Content.Server/Atmos/EntitySystems/BarotraumaSystem.cs index ec508790ba..c23f58637d 100644 --- a/Content.Server/Atmos/EntitySystems/BarotraumaSystem.cs +++ b/Content.Server/Atmos/EntitySystems/BarotraumaSystem.cs @@ -3,7 +3,8 @@ using Content.Server.Administration.Logs; using Content.Server.Atmos.Components; using Content.Shared.Alert; using Content.Shared.Atmos; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.FixedPoint; using Content.Shared.Inventory; diff --git a/Content.Server/Atmos/EntitySystems/FlammableSystem.cs b/Content.Server/Atmos/EntitySystems/FlammableSystem.cs index 81bd4e5c6c..071c63c500 100644 --- a/Content.Server/Atmos/EntitySystems/FlammableSystem.cs +++ b/Content.Server/Atmos/EntitySystems/FlammableSystem.cs @@ -7,7 +7,7 @@ using Content.Shared.ActionBlocker; using Content.Shared.Alert; using Content.Shared.Atmos; using Content.Shared.Atmos.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.IgnitionSource; using Content.Shared.Interaction; diff --git a/Content.Server/Atmos/Rotting/RottingSystem.cs b/Content.Server/Atmos/Rotting/RottingSystem.cs index 57c1504b16..5feb95e3c4 100644 --- a/Content.Server/Atmos/Rotting/RottingSystem.cs +++ b/Content.Server/Atmos/Rotting/RottingSystem.cs @@ -2,7 +2,7 @@ using Content.Server.Atmos.EntitySystems; using Content.Shared.Atmos; using Content.Shared.Atmos.Rotting; using Content.Shared.Body.Events; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Temperature.Components; using Robust.Server.Containers; using Robust.Shared.Physics.Components; diff --git a/Content.Server/Bed/BedSystem.cs b/Content.Server/Bed/BedSystem.cs index 8cfb28acb6..f6c2862a84 100644 --- a/Content.Server/Bed/BedSystem.cs +++ b/Content.Server/Bed/BedSystem.cs @@ -2,7 +2,7 @@ using Content.Shared.Bed; using Content.Shared.Bed.Components; using Content.Shared.Bed.Sleep; using Content.Shared.Buckle.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Mobs.Systems; namespace Content.Server.Bed diff --git a/Content.Server/Bible/BibleSystem.cs b/Content.Server/Bible/BibleSystem.cs index 2aabb5eb27..eb11a465bd 100644 --- a/Content.Server/Bible/BibleSystem.cs +++ b/Content.Server/Bible/BibleSystem.cs @@ -4,7 +4,7 @@ using Content.Server.Popups; using Content.Shared.ActionBlocker; using Content.Shared.Actions; using Content.Shared.Bible; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Ghost.Roles.Components; using Content.Shared.IdentityManagement; using Content.Shared.Interaction; @@ -14,7 +14,6 @@ using Content.Shared.Mobs.Systems; using Content.Shared.Popups; using Content.Shared.Timing; using Content.Shared.Verbs; -using Robust.Shared.Audio; using Robust.Shared.Audio.Systems; using Robust.Shared.Player; using Robust.Shared.Random; @@ -133,9 +132,7 @@ namespace Content.Server.Bible } } - var damage = _damageableSystem.TryChangeDamage(args.Target.Value, component.Damage, true, origin: uid); - - if (damage == null || damage.Empty) + if (_damageableSystem.TryChangeDamage(args.Target.Value, component.Damage, true, origin: uid)) { var othersMessage = Loc.GetString(component.LocPrefix + "-heal-success-none-others", ("user", Identity.Entity(args.User, EntityManager)), ("target", Identity.Entity(args.Target.Value, EntityManager)), ("bible", uid)); _popupSystem.PopupEntity(othersMessage, args.User, Filter.PvsExcept(args.User), true, PopupType.Medium); diff --git a/Content.Server/Body/Systems/RespiratorSystem.cs b/Content.Server/Body/Systems/RespiratorSystem.cs index ca3ee2c9e1..79457cb036 100644 --- a/Content.Server/Body/Systems/RespiratorSystem.cs +++ b/Content.Server/Body/Systems/RespiratorSystem.cs @@ -12,7 +12,7 @@ using Content.Shared.Chat; using Content.Shared.Chemistry.Components; using Content.Shared.Chemistry.EntitySystems; using Content.Shared.Chemistry.Reagent; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.EntityConditions; using Content.Shared.EntityConditions.Conditions.Body; @@ -367,7 +367,7 @@ public sealed class RespiratorSystem : EntitySystem if (ent.Comp.SuffocationCycles == 2) _adminLogger.Add(LogType.Asphyxiation, $"{ToPrettyString(ent):entity} started suffocating"); - _damageableSys.TryChangeDamage(ent, ent.Comp.Damage, interruptsDoAfters: false); + _damageableSys.ChangeDamage(ent.Owner, ent.Comp.Damage, interruptsDoAfters: false); if (ent.Comp.SuffocationCycles < ent.Comp.SuffocationCycleThreshold) return; @@ -381,7 +381,7 @@ public sealed class RespiratorSystem : EntitySystem if (ent.Comp.SuffocationCycles >= 2) _adminLogger.Add(LogType.Asphyxiation, $"{ToPrettyString(ent):entity} stopped suffocating"); - _damageableSys.TryChangeDamage(ent, ent.Comp.DamageRecovery); + _damageableSys.ChangeDamage(ent.Owner, ent.Comp.DamageRecovery); var ev = new StopSuffocatingEvent(); RaiseLocalEvent(ent, ref ev); diff --git a/Content.Server/CardboardBox/CardboardBoxSystem.cs b/Content.Server/CardboardBox/CardboardBoxSystem.cs index 836dc485d9..9fdd23e780 100644 --- a/Content.Server/CardboardBox/CardboardBoxSystem.cs +++ b/Content.Server/CardboardBox/CardboardBoxSystem.cs @@ -1,20 +1,16 @@ -using Content.Server.Storage.Components; using Content.Server.Storage.EntitySystems; using Content.Shared.Access.Components; using Content.Shared.CardboardBox; using Content.Shared.CardboardBox.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Interaction; using Content.Shared.Movement.Components; using Content.Shared.Movement.Systems; using Content.Shared.Stealth; using Content.Shared.Stealth.Components; using Content.Shared.Storage.Components; -using Robust.Server.GameObjects; -using Robust.Shared.Audio; using Robust.Shared.Audio.Systems; using Robust.Shared.Containers; -using Robust.Shared.Player; using Robust.Shared.Timing; namespace Content.Server.CardboardBox; @@ -109,10 +105,10 @@ public sealed class CardboardBoxSystem : SharedCardboardBoxSystem //Relay damage to the mover private void OnDamage(EntityUid uid, CardboardBoxComponent component, DamageChangedEvent args) { - if (args.DamageDelta != null && args.DamageIncreased) - { - _damageable.TryChangeDamage(component.Mover, args.DamageDelta, origin: args.Origin); - } + if (args.DamageDelta == null || !args.DamageIncreased || component.Mover is not { } mover) + return; + + _damageable.ChangeDamage(mover, args.DamageDelta, origin: args.Origin); } private void OnEntInserted(EntityUid uid, CardboardBoxComponent component, EntInsertedIntoContainerMessage args) diff --git a/Content.Server/Chat/SuicideSystem.cs b/Content.Server/Chat/SuicideSystem.cs index dca2959f98..9f901b2ad8 100644 --- a/Content.Server/Chat/SuicideSystem.cs +++ b/Content.Server/Chat/SuicideSystem.cs @@ -2,7 +2,7 @@ using Content.Server.Ghost; using Content.Server.Hands.Systems; using Content.Shared.Administration.Logs; using Content.Shared.Chat; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Database; using Content.Shared.IdentityManagement; using Content.Shared.Interaction.Events; diff --git a/Content.Server/Chat/Systems/EmoteOnDamageSystem.cs b/Content.Server/Chat/Systems/EmoteOnDamageSystem.cs index 4afb885c4c..2b2be1e869 100644 --- a/Content.Server/Chat/Systems/EmoteOnDamageSystem.cs +++ b/Content.Server/Chat/Systems/EmoteOnDamageSystem.cs @@ -1,3 +1,5 @@ +using Content.Shared.Damage.Systems; + namespace Content.Server.Chat.Systems; using Content.Shared.Chat; diff --git a/Content.Server/Cloning/CloningPodSystem.cs b/Content.Server/Cloning/CloningPodSystem.cs index f413a1863f..2f113bee57 100644 --- a/Content.Server/Cloning/CloningPodSystem.cs +++ b/Content.Server/Cloning/CloningPodSystem.cs @@ -12,7 +12,7 @@ using Content.Shared.CCVar; using Content.Shared.Chemistry.Components; using Content.Shared.Cloning; using Content.Shared.Chat; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.DeviceLinking.Events; using Content.Shared.Emag.Components; using Content.Shared.Emag.Systems; diff --git a/Content.Server/Cluwne/CluwneSystem.cs b/Content.Server/Cluwne/CluwneSystem.cs index ab13548e04..97d7005279 100644 --- a/Content.Server/Cluwne/CluwneSystem.cs +++ b/Content.Server/Cluwne/CluwneSystem.cs @@ -8,7 +8,7 @@ using Content.Shared.Chat; using Content.Shared.Chat.Prototypes; using Content.Shared.Clumsy; using Content.Shared.Cluwne; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Mobs; using Content.Shared.NameModifier.EntitySystems; using Content.Shared.Popups; diff --git a/Content.Server/Construction/Conditions/MinHealth.cs b/Content.Server/Construction/Conditions/MinHealth.cs index 980f6a49ca..cef30db71f 100644 --- a/Content.Server/Construction/Conditions/MinHealth.cs +++ b/Content.Server/Construction/Conditions/MinHealth.cs @@ -1,13 +1,8 @@ using Content.Server.Destructible; using Content.Shared.Construction; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Examine; using Content.Shared.FixedPoint; -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; namespace Content.Server.Construction.Conditions; diff --git a/Content.Server/Damage/Commands/HurtCommand.cs b/Content.Server/Damage/Commands/HurtCommand.cs index af9c1ee8fc..849f6e543e 100644 --- a/Content.Server/Damage/Commands/HurtCommand.cs +++ b/Content.Server/Damage/Commands/HurtCommand.cs @@ -4,7 +4,7 @@ using Content.Server.Administration; using Content.Shared.Administration; using Content.Shared.Damage; using Content.Shared.Damage.Prototypes; -using Content.Shared.FixedPoint; +using Content.Shared.Damage.Systems; using Robust.Shared.Console; using Robust.Shared.Prototypes; diff --git a/Content.Server/Damage/ForceSay/DamageForceSaySystem.cs b/Content.Server/Damage/ForceSay/DamageForceSaySystem.cs index a46d42f3e3..5597c47fdb 100644 --- a/Content.Server/Damage/ForceSay/DamageForceSaySystem.cs +++ b/Content.Server/Damage/ForceSay/DamageForceSaySystem.cs @@ -2,6 +2,7 @@ using Content.Shared.Bed.Sleep; using Content.Shared.Damage; using Content.Shared.Damage.Events; using Content.Shared.Damage.ForceSay; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.Mobs; using Content.Shared.Mobs.Systems; diff --git a/Content.Server/Damage/Systems/DamageOnHitSystem.cs b/Content.Server/Damage/Systems/DamageOnHitSystem.cs index f129a14f79..4b13106cc8 100644 --- a/Content.Server/Damage/Systems/DamageOnHitSystem.cs +++ b/Content.Server/Damage/Systems/DamageOnHitSystem.cs @@ -1,8 +1,7 @@ using Content.Server.Damage.Components; -using Content.Shared.Damage; -using Robust.Shared.Player; using Content.Shared.Weapons.Melee.Events; using System.Linq; +using Content.Shared.Damage.Systems; namespace Content.Server.Damage.Systems; diff --git a/Content.Server/Damage/Systems/DamageOnLandSystem.cs b/Content.Server/Damage/Systems/DamageOnLandSystem.cs index 3cf103e6ee..8dede48dee 100644 --- a/Content.Server/Damage/Systems/DamageOnLandSystem.cs +++ b/Content.Server/Damage/Systems/DamageOnLandSystem.cs @@ -9,7 +9,7 @@ namespace Content.Server.Damage.Systems /// public sealed class DamageOnLandSystem : EntitySystem { - [Dependency] private readonly DamageableSystem _damageableSystem = default!; + [Dependency] private readonly Shared.Damage.Systems.DamageableSystem _damageableSystem = default!; public override void Initialize() { diff --git a/Content.Server/Damage/Systems/DamageOnToolInteractSystem.cs b/Content.Server/Damage/Systems/DamageOnToolInteractSystem.cs index 8c0e0a1382..88fe02510f 100644 --- a/Content.Server/Damage/Systems/DamageOnToolInteractSystem.cs +++ b/Content.Server/Damage/Systems/DamageOnToolInteractSystem.cs @@ -11,7 +11,7 @@ namespace Content.Server.Damage.Systems { public sealed class DamageOnToolInteractSystem : EntitySystem { - [Dependency] private readonly DamageableSystem _damageableSystem = default!; + [Dependency] private readonly Shared.Damage.Systems.DamageableSystem _damageableSystem = default!; [Dependency] private readonly IAdminLogManager _adminLogger = default!; [Dependency] private readonly SharedToolSystem _toolSystem = default!; @@ -35,22 +35,22 @@ namespace Content.Server.Damage.Systems && itemToggle.Activated && !welder.TankSafe) { - var dmg = _damageableSystem.TryChangeDamage(args.Target, weldingDamage, origin: args.User); - - if (dmg != null) + if (_damageableSystem.TryChangeDamage(args.Target, weldingDamage, out var dmg, origin: args.User)) + { _adminLogger.Add(LogType.Damaged, $"{ToPrettyString(args.User):user} used {ToPrettyString(args.Used):used} as a welder to deal {dmg.GetTotal():damage} damage to {ToPrettyString(args.Target):target}"); + } args.Handled = true; } else if (component.DefaultDamage is {} damage && _toolSystem.HasQuality(args.Used, component.Tools)) { - var dmg = _damageableSystem.TryChangeDamage(args.Target, damage, origin: args.User); - - if (dmg != null) + if (_damageableSystem.TryChangeDamage(args.Target, damage, out var dmg, origin: args.User)) + { _adminLogger.Add(LogType.Damaged, $"{ToPrettyString(args.User):user} used {ToPrettyString(args.Used):used} as a tool to deal {dmg.GetTotal():damage} damage to {ToPrettyString(args.Target):target}"); + } args.Handled = true; } diff --git a/Content.Server/Damage/Systems/DamageOtherOnHitSystem.cs b/Content.Server/Damage/Systems/DamageOtherOnHitSystem.cs index 10930ca5c9..02bc7334a6 100644 --- a/Content.Server/Damage/Systems/DamageOtherOnHitSystem.cs +++ b/Content.Server/Damage/Systems/DamageOtherOnHitSystem.cs @@ -17,7 +17,7 @@ public sealed class DamageOtherOnHitSystem : SharedDamageOtherOnHitSystem { [Dependency] private readonly IAdminLogManager _adminLogger = default!; [Dependency] private readonly GunSystem _guns = default!; - [Dependency] private readonly DamageableSystem _damageable = default!; + [Dependency] private readonly Shared.Damage.Systems.DamageableSystem _damageable = default!; [Dependency] private readonly SharedCameraRecoilSystem _sharedCameraRecoil = default!; [Dependency] private readonly SharedColorFlashEffectSystem _color = default!; @@ -33,13 +33,13 @@ public sealed class DamageOtherOnHitSystem : SharedDamageOtherOnHitSystem if (TerminatingOrDeleted(args.Target)) return; - var dmg = _damageable.TryChangeDamage(args.Target, component.Damage * _damageable.UniversalThrownDamageModifier, component.IgnoreResistances, origin: args.Component.Thrower); + var dmg = _damageable.ChangeDamage(args.Target, component.Damage * _damageable.UniversalThrownDamageModifier, component.IgnoreResistances, origin: args.Component.Thrower); // Log damage only for mobs. Useful for when people throw spears at each other, but also avoids log-spam when explosions send glass shards flying. - if (dmg != null && HasComp(args.Target)) + if (HasComp(args.Target)) _adminLogger.Add(LogType.ThrowHit, $"{ToPrettyString(args.Target):target} received {dmg.GetTotal():damage} damage from collision"); - if (dmg is { Empty: false }) + if (!dmg.Empty) { _color.RaiseEffect(Color.Red, [args.Target], Filter.Pvs(args.Target, entityManager: EntityManager)); } diff --git a/Content.Server/Damage/Systems/DamageRandomPopupSystem.cs b/Content.Server/Damage/Systems/DamageRandomPopupSystem.cs index 8bdbf84147..25e7bc1644 100644 --- a/Content.Server/Damage/Systems/DamageRandomPopupSystem.cs +++ b/Content.Server/Damage/Systems/DamageRandomPopupSystem.cs @@ -1,6 +1,7 @@ using Content.Server.Damage.Components; using Content.Server.Popups; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Robust.Shared.Player; using Robust.Shared.Random; diff --git a/Content.Server/Damage/Systems/ExaminableDamageSystem.cs b/Content.Server/Damage/Systems/ExaminableDamageSystem.cs index b0dfae71b7..a2a9f234f5 100644 --- a/Content.Server/Damage/Systems/ExaminableDamageSystem.cs +++ b/Content.Server/Damage/Systems/ExaminableDamageSystem.cs @@ -1,6 +1,6 @@ using Content.Server.Damage.Components; using Content.Server.Destructible; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Examine; using Content.Shared.Rounding; using Robust.Shared.Prototypes; diff --git a/Content.Server/Destructible/DestructibleSystem.BenchmarkHelpers.cs b/Content.Server/Destructible/DestructibleSystem.BenchmarkHelpers.cs index ac5e3704fe..a00194c911 100644 --- a/Content.Server/Destructible/DestructibleSystem.BenchmarkHelpers.cs +++ b/Content.Server/Destructible/DestructibleSystem.BenchmarkHelpers.cs @@ -7,7 +7,7 @@ public sealed partial class DestructibleSystem /// /// Tests all triggers in a DestructibleComponent to see how expensive it is to query them. /// - public void TestAllTriggers(List> destructibles) + public void TestAllTriggers(List> destructibles) { foreach (var (uid, damageable, destructible) in destructibles) { @@ -22,7 +22,7 @@ public sealed partial class DestructibleSystem /// /// Tests all behaviours in a DestructibleComponent to see how expensive it is to query them. /// - public void TestAllBehaviors(List> destructibles) + public void TestAllBehaviors(List> destructibles) { foreach (var (uid, damageable, destructible) in destructibles) { diff --git a/Content.Server/Destructible/DestructibleSystem.cs b/Content.Server/Destructible/DestructibleSystem.cs index 847229278c..7ed736fffd 100644 --- a/Content.Server/Destructible/DestructibleSystem.cs +++ b/Content.Server/Destructible/DestructibleSystem.cs @@ -11,6 +11,7 @@ using Content.Server.Fluids.EntitySystems; using Content.Server.Stack; using Content.Shared.Chemistry.EntitySystems; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Destructible; using Content.Shared.Destructible.Thresholds.Triggers; @@ -111,7 +112,7 @@ namespace Content.Server.Destructible /// /// Check if the given threshold should trigger. /// - public bool Triggered(DamageThreshold threshold, Entity owner) + public bool Triggered(DamageThreshold threshold, Entity owner) { if (threshold.Trigger == null) return false; @@ -135,7 +136,7 @@ namespace Content.Server.Destructible /// /// Check if the conditions for the given threshold are currently true. /// - public bool Reached(DamageThreshold threshold, Entity owner) + public bool Reached(DamageThreshold threshold, Entity owner) { if (threshold.Trigger == null) return false; diff --git a/Content.Server/Disposal/Unit/DisposableSystem.cs b/Content.Server/Disposal/Unit/DisposableSystem.cs index d307488110..73365c4f62 100644 --- a/Content.Server/Disposal/Unit/DisposableSystem.cs +++ b/Content.Server/Disposal/Unit/DisposableSystem.cs @@ -1,7 +1,7 @@ using Content.Server.Atmos.EntitySystems; using Content.Server.Disposal.Tube; using Content.Shared.Body.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Disposal.Components; using Content.Shared.Item; using Content.Shared.Throwing; diff --git a/Content.Server/Dragon/DragonRiftSystem.cs b/Content.Server/Dragon/DragonRiftSystem.cs index 9cab018fd7..842b27ec86 100644 --- a/Content.Server/Dragon/DragonRiftSystem.cs +++ b/Content.Server/Dragon/DragonRiftSystem.cs @@ -2,16 +2,14 @@ using Content.Server.Chat.Systems; using Content.Server.NPC; using Content.Server.NPC.Systems; using Content.Server.Pinpointer; -using Content.Shared.Damage; using Content.Shared.Dragon; using Content.Shared.Examine; using Content.Shared.Sprite; -using Robust.Shared.GameObjects; using Robust.Shared.Map; using Robust.Shared.Player; using Robust.Shared.Serialization.Manager; using System.Numerics; -using Robust.Shared.Audio; +using Content.Shared.Damage.Components; using Robust.Shared.Audio.Systems; using Robust.Shared.GameStates; using Robust.Shared.Utility; diff --git a/Content.Server/Electrocution/ElectrocutionSystem.cs b/Content.Server/Electrocution/ElectrocutionSystem.cs index a162b29e19..fe9fe44571 100644 --- a/Content.Server/Electrocution/ElectrocutionSystem.cs +++ b/Content.Server/Electrocution/ElectrocutionSystem.cs @@ -1,14 +1,12 @@ using Content.Server.Administration.Logs; -using Content.Server.NodeContainer; using Content.Server.NodeContainer.EntitySystems; -using Content.Server.NodeContainer.NodeGroups; -using Content.Server.NodeContainer.Nodes; using Content.Server.Power.Components; using Content.Server.Power.EntitySystems; using Content.Server.Power.NodeGroups; using Content.Server.Weapons.Melee; using Content.Shared.Damage; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Electrocution; using Content.Shared.IdentityManagement; @@ -27,7 +25,6 @@ using Content.Shared.Tag; using Content.Shared.Weapons.Melee.Events; using Robust.Shared.Audio; using Robust.Shared.Audio.Systems; -using Robust.Shared.Map; using Robust.Shared.Physics.Events; using Robust.Shared.Player; using Robust.Shared.Prototypes; @@ -402,19 +399,16 @@ public sealed class ElectrocutionSystem : SharedElectrocutionSystem ? _stun.TryUpdateParalyzeDuration(uid, time * ParalyzeTimeMultiplier) : _stun.TryAddParalyzeDuration(uid, time * ParalyzeTimeMultiplier); } - + // TODO: Sparks here. if (shockDamage is { } dmg) { - var actual = _damageable.TryChangeDamage(uid, - new DamageSpecifier(_prototypeManager.Index(DamageType), dmg), origin: sourceUid); - - if (actual != null) + if (_damageable.TryChangeDamage(uid, new DamageSpecifier(_prototypeManager.Index(DamageType), dmg), out var damage, origin: sourceUid)) { _adminLogger.Add(LogType.Electrocution, - $"{ToPrettyString(uid):entity} received {actual.GetTotal():damage} powered electrocution damage{(sourceUid != null ? " from " + ToPrettyString(sourceUid.Value) : ""):source}"); + $"{ToPrettyString(uid):entity} received {damage:damage} powered electrocution damage{(sourceUid != null ? " from " + ToPrettyString(sourceUid.Value) : ""):source}"); } } diff --git a/Content.Server/Explosion/EntitySystems/ExplosionSystem.Airtight.cs b/Content.Server/Explosion/EntitySystems/ExplosionSystem.Airtight.cs index 3d55a7e823..303c4e8cab 100644 --- a/Content.Server/Explosion/EntitySystems/ExplosionSystem.Airtight.cs +++ b/Content.Server/Explosion/EntitySystems/ExplosionSystem.Airtight.cs @@ -1,9 +1,7 @@ using Content.Server.Atmos.Components; -using Content.Server.Destructible; using Content.Shared.Atmos; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Explosion; -using Content.Shared.Explosion.EntitySystems; using Content.Shared.FixedPoint; using Robust.Shared.Map.Components; diff --git a/Content.Server/Explosion/EntitySystems/ExplosionSystem.Processing.cs b/Content.Server/Explosion/EntitySystems/ExplosionSystem.Processing.cs index 263fdabf98..c6528b0142 100644 --- a/Content.Server/Explosion/EntitySystems/ExplosionSystem.Processing.cs +++ b/Content.Server/Explosion/EntitySystems/ExplosionSystem.Processing.cs @@ -1,13 +1,10 @@ -using System.Linq; using System.Numerics; -using Content.Server.Atmos.EntitySystems; -using Content.Server.Explosion.Components; using Content.Shared.CCVar; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Database; using Content.Shared.Explosion; using Content.Shared.Explosion.Components; -using Content.Shared.Explosion.EntitySystems; using Content.Shared.Maps; using Content.Shared.Physics; using Content.Shared.Projectiles; @@ -17,7 +14,6 @@ using Robust.Shared.Map.Components; using Robust.Shared.Physics; using Robust.Shared.Physics.Components; using Robust.Shared.Physics.Dynamics; -using Robust.Shared.Player; using Robust.Shared.Random; using Robust.Shared.Timing; using Robust.Shared.Utility; @@ -439,28 +435,25 @@ public sealed partial class ExplosionSystem float? fireStacksOnIgnite, EntityUid? cause) { - if (originalDamage != null) + if (originalDamage is not null) { GetEntitiesToDamage(uid, originalDamage, id); foreach (var (entity, damage) in _toDamage) { - if (_actorQuery.HasComp(entity)) - { - // Log damage to player entities only, cause this will create a massive amount of log spam otherwise. - if (cause != null) - { - _adminLogger.Add(LogType.ExplosionHit, LogImpact.Medium, $"Explosion of {ToPrettyString(cause):actor} dealt {damage.GetTotal()} damage to {ToPrettyString(entity):subject}"); - } - else - { - _adminLogger.Add(LogType.ExplosionHit, LogImpact.Medium, $"Explosion at {epicenter:epicenter} dealt {damage.GetTotal()} damage to {ToPrettyString(entity):subject}"); - } - - } + if (!_damageableQuery.TryComp(entity, out var damageable)) + continue; // TODO EXPLOSIONS turn explosions into entities, and pass the the entity in as the damage origin. - _damageableSystem.TryChangeDamage(entity, damage, ignoreResistances: true, ignoreGlobalModifiers: true); + _damageableSystem.TryChangeDamage((entity, damageable), damage, ignoreResistances: true, ignoreGlobalModifiers: true); + if (_actorQuery.HasComp(entity)) + { + // Log damage to player entities only; this will create a massive amount of log spam otherwise. + if (cause is not null) + _adminLogger.Add(LogType.ExplosionHit, LogImpact.Medium, $"Explosion of {ToPrettyString(cause):actor} dealt {damage.GetTotal()} damage to {ToPrettyString(entity):subject}"); + else + _adminLogger.Add(LogType.ExplosionHit, LogImpact.Medium, $"Explosion at {epicenter:epicenter} dealt {damage.GetTotal()} damage to {ToPrettyString(entity):subject}"); + } } } @@ -666,7 +659,7 @@ sealed class Explosion private readonly IEntityManager _entMan; private readonly ExplosionSystem _system; private readonly SharedMapSystem _mapSystem; - private readonly DamageableSystem _damageable; + private readonly Shared.Damage.Systems.DamageableSystem _damageable; public readonly EntityUid VisualEnt; @@ -690,7 +683,7 @@ sealed class Explosion EntityUid visualEnt, EntityUid? cause, SharedMapSystem mapSystem, - DamageableSystem damageable) + Shared.Damage.Systems.DamageableSystem damageable) { VisualEnt = visualEnt; Cause = cause; diff --git a/Content.Server/Explosion/EntitySystems/ExplosionSystem.cs b/Content.Server/Explosion/EntitySystems/ExplosionSystem.cs index 198db3eca1..70863d6f54 100644 --- a/Content.Server/Explosion/EntitySystems/ExplosionSystem.cs +++ b/Content.Server/Explosion/EntitySystems/ExplosionSystem.cs @@ -9,7 +9,8 @@ using Content.Server.NPC.Pathfinding; using Content.Shared.Atmos.Components; using Content.Shared.Camera; using Content.Shared.CCVar; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Explosion; using Content.Shared.Explosion.Components; diff --git a/Content.Server/Ghost/GhostSystem.cs b/Content.Server/Ghost/GhostSystem.cs index 1a3c9031fe..af1a433d1a 100644 --- a/Content.Server/Ghost/GhostSystem.cs +++ b/Content.Server/Ghost/GhostSystem.cs @@ -3,13 +3,14 @@ using System.Numerics; using Content.Server.Administration.Logs; using Content.Server.Chat.Managers; using Content.Server.GameTicking; -using Content.Server.Ghost.Components; using Content.Server.Mind; using Content.Server.Roles.Jobs; using Content.Shared.Actions; using Content.Shared.CCVar; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Examine; using Content.Shared.Eye; @@ -586,7 +587,7 @@ namespace Content.Server.Ghost DamageSpecifier damage = new(_prototypeManager.Index(AsphyxiationDamageType), dealtDamage); - _damageable.TryChangeDamage(playerEntity, damage, true); + _damageable.ChangeDamage(playerEntity.Value, damage, true); } } diff --git a/Content.Server/Guardian/GuardianSystem.cs b/Content.Server/Guardian/GuardianSystem.cs index ea1a6f4f4f..5f2597afef 100644 --- a/Content.Server/Guardian/GuardianSystem.cs +++ b/Content.Server/Guardian/GuardianSystem.cs @@ -1,7 +1,7 @@ using Content.Server.Body.Systems; using Content.Server.Popups; using Content.Shared.Actions; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.DoAfter; using Content.Shared.Examine; using Content.Shared.Guardian; @@ -285,8 +285,8 @@ namespace Content.Server.Guardian if (args.DamageDelta == null || component.Host == null || component.DamageShare == 0) return; - _damageSystem.TryChangeDamage( - component.Host, + _damageSystem.ChangeDamage( + component.Host.Value, args.DamageDelta * component.DamageShare, origin: args.Origin, ignoreResistances: true, diff --git a/Content.Server/ImmovableRod/ImmovableRodSystem.cs b/Content.Server/ImmovableRod/ImmovableRodSystem.cs index bcbcfda9af..646b5c97bb 100644 --- a/Content.Server/ImmovableRod/ImmovableRodSystem.cs +++ b/Content.Server/ImmovableRod/ImmovableRodSystem.cs @@ -1,10 +1,9 @@ using Content.Server.Body.Systems; using Content.Server.Destructible; -using Content.Server.Examine; using Content.Server.Polymorph.Components; using Content.Server.Popups; using Content.Shared.Body.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Examine; using Content.Shared.Popups; using Robust.Shared.Audio.Systems; diff --git a/Content.Server/KillTracking/KillTrackingSystem.cs b/Content.Server/KillTracking/KillTrackingSystem.cs index ba27ea5d9e..d40e0e13dd 100644 --- a/Content.Server/KillTracking/KillTrackingSystem.cs +++ b/Content.Server/KillTracking/KillTrackingSystem.cs @@ -1,5 +1,6 @@ using Content.Server.NPC.HTN; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.Mobs; using Content.Shared.Mobs.Systems; diff --git a/Content.Server/Kitchen/EntitySystems/MicrowaveSystem.cs b/Content.Server/Kitchen/EntitySystems/MicrowaveSystem.cs index e23bea7bb4..1c6ed26d48 100644 --- a/Content.Server/Kitchen/EntitySystems/MicrowaveSystem.cs +++ b/Content.Server/Kitchen/EntitySystems/MicrowaveSystem.cs @@ -7,7 +7,6 @@ using Content.Server.Hands.Systems; using Content.Server.Kitchen.Components; using Content.Server.Power.Components; using Content.Server.Power.EntitySystems; -using Content.Server.Temperature.Components; using Content.Server.Temperature.Systems; using Content.Shared.Body.Components; using Content.Shared.Body.Part; @@ -40,9 +39,8 @@ using Robust.Shared.Timing; using Content.Shared.Stacks; using Content.Server.Construction.Components; using Content.Shared.Chat; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Temperature.Components; -using Robust.Shared.Utility; namespace Content.Server.Kitchen.EntitySystems { diff --git a/Content.Server/Lightning/LightningTargetSystem.cs b/Content.Server/Lightning/LightningTargetSystem.cs index 4a0ee23c5b..eac23c3016 100644 --- a/Content.Server/Lightning/LightningTargetSystem.cs +++ b/Content.Server/Lightning/LightningTargetSystem.cs @@ -2,6 +2,7 @@ using Content.Server.Explosion.EntitySystems; using Content.Server.Lightning; using Content.Server.Lightning.Components; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Robust.Server.GameObjects; namespace Content.Server.Tesla.EntitySystems; @@ -26,7 +27,7 @@ public sealed class LightningTargetSystem : EntitySystem { DamageSpecifier damage = new(); damage.DamageDict.Add("Structural", uid.Comp.DamageFromLightning); - _damageable.TryChangeDamage(uid, damage, true); + _damageable.ChangeDamage(uid.Owner, damage, true); if (uid.Comp.LightningExplode) { diff --git a/Content.Server/Mech/Systems/MechSystem.cs b/Content.Server/Mech/Systems/MechSystem.cs index 917f4f5035..923c701868 100644 --- a/Content.Server/Mech/Systems/MechSystem.cs +++ b/Content.Server/Mech/Systems/MechSystem.cs @@ -4,7 +4,7 @@ using Content.Server.Body.Systems; using Content.Server.Mech.Components; using Content.Server.Power.EntitySystems; using Content.Shared.ActionBlocker; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.DoAfter; using Content.Shared.FixedPoint; using Content.Shared.Interaction; @@ -265,7 +265,7 @@ public sealed partial class MechSystem : SharedMechSystem component.PilotSlot.ContainedEntity != null) { var damage = args.DamageDelta * component.MechToPilotDamageMultiplier; - _damageable.TryChangeDamage(component.PilotSlot.ContainedEntity, damage); + _damageable.ChangeDamage(component.PilotSlot.ContainedEntity.Value, damage); } } diff --git a/Content.Server/Medical/DefibrillatorSystem.cs b/Content.Server/Medical/DefibrillatorSystem.cs index 1578f11629..f0dfceb14e 100644 --- a/Content.Server/Medical/DefibrillatorSystem.cs +++ b/Content.Server/Medical/DefibrillatorSystem.cs @@ -8,7 +8,8 @@ using Content.Server.Popups; using Content.Server.PowerCell; using Content.Shared.Traits.Assorted; using Content.Shared.Chat; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.DoAfter; using Content.Shared.Interaction; using Content.Shared.Item.ItemToggle; diff --git a/Content.Server/Medical/HealthAnalyzerSystem.cs b/Content.Server/Medical/HealthAnalyzerSystem.cs index 657ac3e636..f022dff5e3 100644 --- a/Content.Server/Medical/HealthAnalyzerSystem.cs +++ b/Content.Server/Medical/HealthAnalyzerSystem.cs @@ -2,7 +2,7 @@ using Content.Server.Medical.Components; using Content.Server.PowerCell; using Content.Shared.Body.Components; using Content.Shared.Chemistry.EntitySystems; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.DoAfter; using Content.Shared.IdentityManagement; using Content.Shared.Interaction; diff --git a/Content.Server/Mining/MeteorSystem.cs b/Content.Server/Mining/MeteorSystem.cs index 3b0c6920b3..361844ba25 100644 --- a/Content.Server/Mining/MeteorSystem.cs +++ b/Content.Server/Mining/MeteorSystem.cs @@ -1,6 +1,7 @@ using Content.Server.Administration.Logs; using Content.Server.Destructible; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.FixedPoint; using Content.Shared.Mobs.Systems; diff --git a/Content.Server/NPC/HTN/PrimitiveTasks/Operators/Specific/PickNearbyInjectableOperator.cs b/Content.Server/NPC/HTN/PrimitiveTasks/Operators/Specific/PickNearbyInjectableOperator.cs index f351d582c6..67a8198c38 100644 --- a/Content.Server/NPC/HTN/PrimitiveTasks/Operators/Specific/PickNearbyInjectableOperator.cs +++ b/Content.Server/NPC/HTN/PrimitiveTasks/Operators/Specific/PickNearbyInjectableOperator.cs @@ -3,7 +3,7 @@ using System.Threading.Tasks; using Content.Shared.NPC.Components; using Content.Server.NPC.Pathfinding; using Content.Shared.Chemistry.Components.SolutionManager; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Interaction; using Content.Shared.Mobs.Components; using Content.Shared.Silicons.Bots; diff --git a/Content.Server/NPC/Systems/NPCRetaliationSystem.cs b/Content.Server/NPC/Systems/NPCRetaliationSystem.cs index d6b2000f32..a970d34bda 100644 --- a/Content.Server/NPC/Systems/NPCRetaliationSystem.cs +++ b/Content.Server/NPC/Systems/NPCRetaliationSystem.cs @@ -1,6 +1,7 @@ using Content.Server.NPC.Components; using Content.Shared.CombatMode; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Mobs.Components; using Content.Shared.NPC.Components; using Content.Shared.NPC.Systems; diff --git a/Content.Server/NPC/Systems/NPCUtilitySystem.cs b/Content.Server/NPC/Systems/NPCUtilitySystem.cs index bc82e72692..9605b62847 100644 --- a/Content.Server/NPC/Systems/NPCUtilitySystem.cs +++ b/Content.Server/NPC/Systems/NPCUtilitySystem.cs @@ -6,7 +6,6 @@ using Content.Server.NPC.Queries.Curves; using Content.Server.NPC.Queries.Queries; using Content.Server.Nutrition.Components; using Content.Shared.Chemistry.EntitySystems; -using Content.Shared.Damage; using Content.Shared.Examine; using Content.Shared.Fluids.Components; using Content.Shared.Inventory; @@ -29,6 +28,7 @@ using Robust.Shared.Prototypes; using Robust.Shared.Utility; using Content.Shared.Atmos.Components; using System.Linq; +using Content.Shared.Damage.Components; using Content.Shared.Temperature.Components; namespace Content.Server.NPC.Systems; diff --git a/Content.Server/Ninja/Systems/StunProviderSystem.cs b/Content.Server/Ninja/Systems/StunProviderSystem.cs index 8697692e5e..98df8a039a 100644 --- a/Content.Server/Ninja/Systems/StunProviderSystem.cs +++ b/Content.Server/Ninja/Systems/StunProviderSystem.cs @@ -1,6 +1,6 @@ using Content.Server.Ninja.Events; using Content.Server.Power.EntitySystems; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Interaction; using Content.Shared.Ninja.Components; using Content.Shared.Ninja.Systems; @@ -9,8 +9,6 @@ using Content.Shared.Stunnable; using Content.Shared.Timing; using Content.Shared.Whitelist; using Robust.Shared.Audio.Systems; -using Robust.Shared.Timing; -using Robust.Shared.Prototypes; namespace Content.Server.Ninja.Systems; @@ -62,7 +60,7 @@ public sealed class StunProviderSystem : SharedStunProviderSystem _audio.PlayPvs(comp.Sound, target); - _damageable.TryChangeDamage(target, comp.StunDamage, false, true, null, origin: uid); + _damageable.ChangeDamage(target, comp.StunDamage, origin: uid); _stun.TryAddParalyzeDuration(target, comp.StunTime); // short cooldown to prevent instant stunlocking diff --git a/Content.Server/Nutrition/EntitySystems/SmokingSystem.Vape.cs b/Content.Server/Nutrition/EntitySystems/SmokingSystem.Vape.cs index 6905979a5f..871a15ee73 100644 --- a/Content.Server/Nutrition/EntitySystems/SmokingSystem.Vape.cs +++ b/Content.Server/Nutrition/EntitySystems/SmokingSystem.Vape.cs @@ -4,7 +4,7 @@ using Content.Server.Nutrition.Components; using Content.Server.Popups; using Content.Shared.Body.Components; using Content.Shared.Atmos; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.DoAfter; using Content.Shared.Emag.Systems; using Content.Shared.IdentityManagement; diff --git a/Content.Server/Polymorph/Systems/PolymorphSystem.cs b/Content.Server/Polymorph/Systems/PolymorphSystem.cs index db7fb6a92f..897ad72047 100644 --- a/Content.Server/Polymorph/Systems/PolymorphSystem.cs +++ b/Content.Server/Polymorph/Systems/PolymorphSystem.cs @@ -4,7 +4,8 @@ using Content.Server.Inventory; using Content.Server.Polymorph.Components; using Content.Shared.Buckle; using Content.Shared.Coordinates; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Destructible; using Content.Shared.Hands.EntitySystems; using Content.Shared.IdentityManagement; @@ -228,7 +229,7 @@ public sealed partial class PolymorphSystem : EntitySystem _mobThreshold.GetScaledDamage(uid, child, out var damage) && damage != null) { - _damageable.SetDamage(child, damageParent, damage); + _damageable.SetDamage((child, damageParent), damage); } if (configuration.Inventory == PolymorphInventoryChange.Transfer) @@ -323,7 +324,7 @@ public sealed partial class PolymorphSystem : EntitySystem _mobThreshold.GetScaledDamage(uid, parent, out var damage) && damage != null) { - _damageable.SetDamage(parent, damageParent, damage); + _damageable.SetDamage((parent, damageParent), damage); } if (component.Configuration.Inventory == PolymorphInventoryChange.Transfer) diff --git a/Content.Server/Projectiles/ProjectileSystem.cs b/Content.Server/Projectiles/ProjectileSystem.cs index 4c054a4561..28df1eb42d 100644 --- a/Content.Server/Projectiles/ProjectileSystem.cs +++ b/Content.Server/Projectiles/ProjectileSystem.cs @@ -3,7 +3,8 @@ using Content.Server.Destructible; using Content.Server.Effects; using Content.Server.Weapons.Ranged.Systems; using Content.Shared.Camera; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.FixedPoint; using Content.Shared.Projectiles; @@ -54,64 +55,63 @@ public sealed class ProjectileSystem : SharedProjectileSystem damageRequired -= damageableComponent.TotalDamage; damageRequired = FixedPoint2.Max(damageRequired, FixedPoint2.Zero); } - var modifiedDamage = _damageableSystem.TryChangeDamage(target, ev.Damage, component.IgnoreResistances, damageable: damageableComponent, origin: component.Shooter); var deleted = Deleted(target); - if (modifiedDamage is not null && Exists(component.Shooter)) + if (_damageableSystem.TryChangeDamage((target, damageableComponent), ev.Damage, out var damage, component.IgnoreResistances, origin: component.Shooter) && Exists(component.Shooter)) { - if (modifiedDamage.AnyPositive() && !deleted) + if (!deleted) { _color.RaiseEffect(Color.Red, new List { target }, Filter.Pvs(target, entityManager: EntityManager)); } _adminLogger.Add(LogType.BulletHit, LogImpact.Medium, - $"Projectile {ToPrettyString(uid):projectile} shot by {ToPrettyString(component.Shooter!.Value):user} hit {otherName:target} and dealt {modifiedDamage.GetTotal():damage} damage"); - } + $"Projectile {ToPrettyString(uid):projectile} shot by {ToPrettyString(component.Shooter!.Value):user} hit {otherName:target} and dealt {damage:damage} damage"); - // If penetration is to be considered, we need to do some checks to see if the projectile should stop. - if (modifiedDamage is not null && component.PenetrationThreshold != 0) - { - // If a damage type is required, stop the bullet if the hit entity doesn't have that type. - if (component.PenetrationDamageTypeRequirement != null) + // If penetration is to be considered, we need to do some checks to see if the projectile should stop. + if (component.PenetrationThreshold != 0) { - var stopPenetration = false; - foreach (var requiredDamageType in component.PenetrationDamageTypeRequirement) + // If a damage type is required, stop the bullet if the hit entity doesn't have that type. + if (component.PenetrationDamageTypeRequirement != null) { - if (!modifiedDamage.DamageDict.Keys.Contains(requiredDamageType)) + var stopPenetration = false; + foreach (var requiredDamageType in component.PenetrationDamageTypeRequirement) { - stopPenetration = true; - break; + if (!damage.DamageDict.Keys.Contains(requiredDamageType)) + { + stopPenetration = true; + break; + } + } + if (stopPenetration) + component.ProjectileSpent = true; + } + + // If the object won't be destroyed, it "tanks" the penetration hit. + if (damage.GetTotal() < damageRequired) + { + component.ProjectileSpent = true; + } + + if (!component.ProjectileSpent) + { + component.PenetrationAmount += damageRequired; + // The projectile has dealt enough damage to be spent. + if (component.PenetrationAmount >= component.PenetrationThreshold) + { + component.ProjectileSpent = true; } } - if (stopPenetration) - component.ProjectileSpent = true; } - - // If the object won't be destroyed, it "tanks" the penetration hit. - if (modifiedDamage.GetTotal() < damageRequired) + else { component.ProjectileSpent = true; } - - if (!component.ProjectileSpent) - { - component.PenetrationAmount += damageRequired; - // The projectile has dealt enough damage to be spent. - if (component.PenetrationAmount >= component.PenetrationThreshold) - { - component.ProjectileSpent = true; - } - } - } - else - { - component.ProjectileSpent = true; } if (!deleted) { - _guns.PlayImpactSound(target, modifiedDamage, component.SoundHit, component.ForceSound); + _guns.PlayImpactSound(target, damage, component.SoundHit, component.ForceSound); if (!args.OurBody.LinearVelocity.IsLengthZero()) _sharedCameraRecoil.KickCamera(target, args.OurBody.LinearVelocity.Normalized()); diff --git a/Content.Server/Revenant/EntitySystems/RevenantSystem.Abilities.cs b/Content.Server/Revenant/EntitySystems/RevenantSystem.Abilities.cs index 38c3480078..8089cba61b 100644 --- a/Content.Server/Revenant/EntitySystems/RevenantSystem.Abilities.cs +++ b/Content.Server/Revenant/EntitySystems/RevenantSystem.Abilities.cs @@ -213,7 +213,7 @@ public sealed partial class RevenantSystem return; DamageSpecifier dspec = new(); dspec.DamageDict.Add("Cold", damage.Value); - _damage.TryChangeDamage(args.Args.Target, dspec, true, origin: uid); + _damage.ChangeDamage(args.Args.Target.Value, dspec, true, origin: uid); args.Handled = true; } diff --git a/Content.Server/Revenant/EntitySystems/RevenantSystem.cs b/Content.Server/Revenant/EntitySystems/RevenantSystem.cs index 6c8972be58..34966d9c22 100644 --- a/Content.Server/Revenant/EntitySystems/RevenantSystem.cs +++ b/Content.Server/Revenant/EntitySystems/RevenantSystem.cs @@ -3,7 +3,7 @@ using Content.Server.Actions; using Content.Server.GameTicking; using Content.Server.Store.Systems; using Content.Shared.Alert; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.DoAfter; using Content.Shared.Examine; using Content.Shared.Eye; diff --git a/Content.Server/Shuttles/Systems/ShuttleSystem.Impact.cs b/Content.Server/Shuttles/Systems/ShuttleSystem.Impact.cs index b5adeb04db..6126234451 100644 --- a/Content.Server/Shuttles/Systems/ShuttleSystem.Impact.cs +++ b/Content.Server/Shuttles/Systems/ShuttleSystem.Impact.cs @@ -20,6 +20,7 @@ using Robust.Shared.Physics.Events; using Robust.Shared.Prototypes; using Robust.Shared.Random; using System.Numerics; +using Content.Shared.Damage.Components; namespace Content.Server.Shuttles.Systems; @@ -372,7 +373,7 @@ public sealed partial class ShuttleSystem damageSpec.DamageDict["Blunt"] = scaledDamage; damageSpec.DamageDict["Structural"] = scaledDamage * _structuralDamage; - _damageSys.TryChangeDamage(localEnt, damageSpec, damageable: damageable); + _damageSys.ChangeDamage((localEnt, damageable), damageSpec); } // might've been destroyed if (TerminatingOrDeleted(localEnt) || EntityManager.IsQueuedForDeletion(localEnt)) diff --git a/Content.Server/Shuttles/Systems/ShuttleSystem.cs b/Content.Server/Shuttles/Systems/ShuttleSystem.cs index e96ceffd16..86b97c40a6 100644 --- a/Content.Server/Shuttles/Systems/ShuttleSystem.cs +++ b/Content.Server/Shuttles/Systems/ShuttleSystem.cs @@ -8,7 +8,7 @@ using Content.Server.Shuttles.Events; using Content.Server.Station.Systems; using Content.Server.Stunnable; using Content.Shared.Buckle.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Light.Components; using Content.Shared.Movement.Events; using Content.Shared.Salvage; diff --git a/Content.Server/Shuttles/Systems/ThrusterSystem.cs b/Content.Server/Shuttles/Systems/ThrusterSystem.cs index f7f0a8b251..20040ab40a 100644 --- a/Content.Server/Shuttles/Systems/ThrusterSystem.cs +++ b/Content.Server/Shuttles/Systems/ThrusterSystem.cs @@ -1,16 +1,14 @@ using System.Numerics; using Content.Server.Audio; -using Content.Server.Power.Components; using Content.Server.Power.EntitySystems; using Content.Server.Shuttles.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Examine; using Content.Shared.Interaction; using Content.Shared.Maps; using Content.Shared.Physics; using Content.Shared.Shuttles.Components; using Content.Shared.Temperature; -using Robust.Shared.Map; using Robust.Shared.Map.Components; using Robust.Shared.Physics.Collision.Shapes; using Robust.Shared.Physics.Components; diff --git a/Content.Server/Silicons/Borgs/BorgSystem.Transponder.cs b/Content.Server/Silicons/Borgs/BorgSystem.Transponder.cs index 082e6776f0..fd3b910753 100644 --- a/Content.Server/Silicons/Borgs/BorgSystem.Transponder.cs +++ b/Content.Server/Silicons/Borgs/BorgSystem.Transponder.cs @@ -1,6 +1,6 @@ using Content.Shared.Containers.ItemSlots; using Content.Shared.DeviceNetwork; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.FixedPoint; using Content.Shared.Mobs; using Content.Shared.Mobs.Systems; diff --git a/Content.Server/Silicons/StationAi/StationAiSystem.cs b/Content.Server/Silicons/StationAi/StationAiSystem.cs index 4ee2a07d72..a9198d5816 100644 --- a/Content.Server/Silicons/StationAi/StationAiSystem.cs +++ b/Content.Server/Silicons/StationAi/StationAiSystem.cs @@ -12,7 +12,8 @@ using Content.Server.Station.Systems; using Content.Shared.Alert; using Content.Shared.Chat.Prototypes; using Content.Shared.Containers.ItemSlots; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Destructible; using Content.Shared.DeviceNetwork.Components; using Content.Shared.DoAfter; @@ -127,10 +128,7 @@ public sealed class StationAiSystem : SharedStationAiSystem _battery.SetCharge(ent, battery.MaxCharge); } - if (TryComp(ent, out var damageable)) - { - _damageable.SetAllDamage(ent, damageable, 0); - } + _damageable.ClearAllDamage(ent.Owner); } protected override void OnAiInsert(Entity ent, ref EntInsertedIntoContainerMessage args) diff --git a/Content.Server/Speech/EntitySystems/DamagedSiliconAccentSystem.cs b/Content.Server/Speech/EntitySystems/DamagedSiliconAccentSystem.cs index d4a37a07cd..a5e30346bd 100644 --- a/Content.Server/Speech/EntitySystems/DamagedSiliconAccentSystem.cs +++ b/Content.Server/Speech/EntitySystems/DamagedSiliconAccentSystem.cs @@ -2,7 +2,7 @@ using Content.Server.Destructible; using Content.Server.PowerCell; using Content.Shared.Speech.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.FixedPoint; using Content.Shared.Speech; using Robust.Shared.Random; diff --git a/Content.Server/Spreader/KudzuSystem.cs b/Content.Server/Spreader/KudzuSystem.cs index fbc809c15b..e8470ebd57 100644 --- a/Content.Server/Spreader/KudzuSystem.cs +++ b/Content.Server/Spreader/KudzuSystem.cs @@ -1,4 +1,5 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Spreader; using Robust.Shared.Prototypes; using Robust.Shared.Random; diff --git a/Content.Server/Temperature/Systems/TemperatureSystem.cs b/Content.Server/Temperature/Systems/TemperatureSystem.cs index f6a7536994..3bbde482c4 100644 --- a/Content.Server/Temperature/Systems/TemperatureSystem.cs +++ b/Content.Server/Temperature/Systems/TemperatureSystem.cs @@ -5,7 +5,8 @@ using Content.Server.Body.Components; using Content.Server.Temperature.Components; using Content.Shared.Alert; using Content.Shared.Atmos; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Inventory; using Content.Shared.Rejuvenate; diff --git a/Content.Server/VendingMachines/VendingMachineSystem.cs b/Content.Server/VendingMachines/VendingMachineSystem.cs index 86a7b512b6..1fb695ae61 100644 --- a/Content.Server/VendingMachines/VendingMachineSystem.cs +++ b/Content.Server/VendingMachines/VendingMachineSystem.cs @@ -5,6 +5,7 @@ using Content.Server.Power.Components; using Content.Server.Vocalization.Systems; using Content.Shared.Cargo; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Destructible; using Content.Shared.Emp; using Content.Shared.Power; diff --git a/Content.Server/Weapons/Ranged/Systems/GunSystem.AutoFire.cs b/Content.Server/Weapons/Ranged/Systems/GunSystem.AutoFire.cs index 47b0d5f3c6..995e29727b 100644 --- a/Content.Server/Weapons/Ranged/Systems/GunSystem.AutoFire.cs +++ b/Content.Server/Weapons/Ranged/Systems/GunSystem.AutoFire.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Weapons.Ranged.Components; using Robust.Shared.Map; diff --git a/Content.Server/Zombies/ZombieSystem.Transform.cs b/Content.Server/Zombies/ZombieSystem.Transform.cs index c44c2e7aa0..43a06f2614 100644 --- a/Content.Server/Zombies/ZombieSystem.Transform.cs +++ b/Content.Server/Zombies/ZombieSystem.Transform.cs @@ -14,10 +14,9 @@ using Content.Server.NPC.Systems; using Content.Server.StationEvents.Components; using Content.Server.Speech.Components; using Content.Shared.Body.Components; -using Content.Shared.Chat; using Content.Shared.CombatMode; using Content.Shared.CombatMode.Pacification; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Hands.Components; using Content.Shared.Hands.EntitySystems; using Content.Shared.Humanoid; @@ -248,8 +247,7 @@ public sealed partial class ZombieSystem tempComp.ColdDamage.ClampMax(0); //Heals the zombie from all the damage it took while human - if (TryComp(target, out var damageablecomp)) - _damageable.SetAllDamage(target, damageablecomp, 0); + _damageable.ClearAllDamage(target); _mobState.ChangeMobState(target, MobState.Alive); _faction.ClearFactions(target, dirty: false); diff --git a/Content.Server/Zombies/ZombieSystem.cs b/Content.Server/Zombies/ZombieSystem.cs index d4f86fa96c..72c5236930 100644 --- a/Content.Server/Zombies/ZombieSystem.cs +++ b/Content.Server/Zombies/ZombieSystem.cs @@ -1,4 +1,3 @@ -using System.Linq; using Content.Shared.NPC.Prototypes; using Content.Server.Actions; using Content.Server.Body.Systems; @@ -11,7 +10,7 @@ using Content.Shared.Armor; using Content.Shared.Bed.Sleep; using Content.Shared.Cloning.Events; using Content.Shared.Chat; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Humanoid; using Content.Shared.Inventory; using Content.Shared.Mind; @@ -118,7 +117,7 @@ namespace Content.Server.Zombies var curTime = _timing.CurTime; // Hurt the living infected - var query = EntityQueryEnumerator(); + var query = EntityQueryEnumerator(); while (query.MoveNext(out var uid, out var comp, out var damage, out var mobState)) { // Process only once per second @@ -138,11 +137,11 @@ namespace Content.Server.Zombies ? comp.CritDamageMultiplier : 1f; - _damageable.TryChangeDamage(uid, comp.Damage * multiplier, true, false, damage); + _damageable.ChangeDamage((uid, damage), comp.Damage * multiplier, true, false); } // Heal the zombified - var zombQuery = EntityQueryEnumerator(); + var zombQuery = EntityQueryEnumerator(); while (zombQuery.MoveNext(out var uid, out var comp, out var damage, out var mobState)) { // Process only once per second @@ -159,7 +158,7 @@ namespace Content.Server.Zombies : 1f; // Gradual healing for living zombies. - _damageable.TryChangeDamage(uid, comp.PassiveHealing * multiplier, true, false, damage); + _damageable.ChangeDamage((uid, damage), comp.PassiveHealing * multiplier, true, false); } } diff --git a/Content.Shared/Armor/SharedArmorSystem.cs b/Content.Shared/Armor/SharedArmorSystem.cs index 972289460f..6a3db3184d 100644 --- a/Content.Shared/Armor/SharedArmorSystem.cs +++ b/Content.Shared/Armor/SharedArmorSystem.cs @@ -1,5 +1,6 @@ using Content.Shared.Clothing.Components; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Examine; using Content.Shared.Inventory; using Content.Shared.Silicons.Borgs; diff --git a/Content.Shared/Bed/Sleep/SleepingSystem.cs b/Content.Shared/Bed/Sleep/SleepingSystem.cs index 27e11bc878..661c8399a1 100644 --- a/Content.Shared/Bed/Sleep/SleepingSystem.cs +++ b/Content.Shared/Bed/Sleep/SleepingSystem.cs @@ -4,6 +4,7 @@ using Content.Shared.Buckle.Components; using Content.Shared.Damage; using Content.Shared.Damage.Events; using Content.Shared.Damage.ForceSay; +using Content.Shared.Damage.Systems; using Content.Shared.Emoting; using Content.Shared.Examine; using Content.Shared.Eye.Blinding.Systems; diff --git a/Content.Shared/Blocking/BlockingSystem.User.cs b/Content.Shared/Blocking/BlockingSystem.User.cs index 2cd1db7f1f..db59a8d5f6 100644 --- a/Content.Shared/Blocking/BlockingSystem.User.cs +++ b/Content.Shared/Blocking/BlockingSystem.User.cs @@ -1,6 +1,6 @@ using Content.Shared.Damage; -using Content.Shared.Damage.Prototypes; -using Robust.Shared.Audio; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Robust.Shared.Audio.Systems; using Robust.Shared.Containers; @@ -42,31 +42,31 @@ public sealed partial class BlockingSystem private void OnUserDamageModified(EntityUid uid, BlockingUserComponent component, DamageModifyEvent args) { - if (TryComp(component.BlockingItem, out var blocking)) + if (component.BlockingItem is not { } item || !TryComp(item, out var blocking)) + return; + + if (args.Damage.GetTotal() <= 0) + return; + + // A shield should only block damage it can itself absorb. To determine that we need the Damageable component on it. + if (!TryComp(item, out var dmgComp)) + return; + + var blockFraction = blocking.IsBlocking ? blocking.ActiveBlockFraction : blocking.PassiveBlockFraction; + blockFraction = Math.Clamp(blockFraction, 0, 1); + _damageable.TryChangeDamage((item, dmgComp), blockFraction * args.OriginalDamage); + + var modify = new DamageModifierSet(); + foreach (var key in dmgComp.Damage.DamageDict.Keys) { - if (args.Damage.GetTotal() <= 0) - return; + modify.Coefficients.TryAdd(key, 1 - blockFraction); + } - // A shield should only block damage it can itself absorb. To determine that we need the Damageable component on it. - if (!TryComp(component.BlockingItem, out var dmgComp)) - return; + args.Damage = DamageSpecifier.ApplyModifierSet(args.Damage, modify); - var blockFraction = blocking.IsBlocking ? blocking.ActiveBlockFraction : blocking.PassiveBlockFraction; - blockFraction = Math.Clamp(blockFraction, 0, 1); - _damageable.TryChangeDamage(component.BlockingItem, blockFraction * args.OriginalDamage); - - var modify = new DamageModifierSet(); - foreach (var key in dmgComp.Damage.DamageDict.Keys) - { - modify.Coefficients.TryAdd(key, 1 - blockFraction); - } - - args.Damage = DamageSpecifier.ApplyModifierSet(args.Damage, modify); - - if (blocking.IsBlocking && !args.Damage.Equals(args.OriginalDamage)) - { - _audio.PlayPvs(blocking.BlockSound, uid); - } + if (blocking.IsBlocking && !args.Damage.Equals(args.OriginalDamage)) + { + _audio.PlayPvs(blocking.BlockSound, uid); } } diff --git a/Content.Shared/Body/Systems/SharedBloodstreamSystem.cs b/Content.Shared/Body/Systems/SharedBloodstreamSystem.cs index 693eede7d8..688e3ccb92 100644 --- a/Content.Shared/Body/Systems/SharedBloodstreamSystem.cs +++ b/Content.Shared/Body/Systems/SharedBloodstreamSystem.cs @@ -6,8 +6,8 @@ using Content.Shared.Chemistry.EntitySystems; using Content.Shared.Chemistry.Reaction; using Content.Shared.Chemistry.Reagent; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.EntityEffects.Effects.Solution; -using Content.Shared.EntityEffects.Effects.Transform; using Content.Shared.FixedPoint; using Content.Shared.Fluids; using Content.Shared.Forensics.Components; @@ -99,8 +99,7 @@ public abstract class SharedBloodstreamSystem : EntitySystem // bloodloss damage is based on the base value, and modified by how low your blood level is. var amt = bloodstream.BloodlossDamage / (0.1f + bloodPercentage); - _damageableSystem.TryChangeDamage(uid, amt, - ignoreResistances: false, interruptsDoAfters: false); + _damageableSystem.TryChangeDamage(uid, amt, ignoreResistances: false, interruptsDoAfters: false); // Apply dizziness as a symptom of bloodloss. // The effect is applied in a way that it will never be cleared without being healthy. diff --git a/Content.Shared/Body/Systems/SharedBodySystem.Parts.cs b/Content.Shared/Body/Systems/SharedBodySystem.Parts.cs index 78d270ddc9..0b2efdce59 100644 --- a/Content.Shared/Body/Systems/SharedBodySystem.Parts.cs +++ b/Content.Shared/Body/Systems/SharedBodySystem.Parts.cs @@ -181,7 +181,7 @@ public partial class SharedBodySystem { // TODO BODY SYSTEM KILL : remove this when wounding and required parts are implemented properly var damage = new DamageSpecifier(Prototypes.Index(BloodlossDamageType), 300); - Damageable.TryChangeDamage(bodyEnt, damage); + Damageable.ChangeDamage(bodyEnt.Owner, damage); } } diff --git a/Content.Shared/Body/Systems/SharedBodySystem.cs b/Content.Shared/Body/Systems/SharedBodySystem.cs index a45966fcc3..f359ebc632 100644 --- a/Content.Shared/Body/Systems/SharedBodySystem.cs +++ b/Content.Shared/Body/Systems/SharedBodySystem.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Movement.Systems; using Content.Shared.Standing; using Robust.Shared.Containers; diff --git a/Content.Shared/Changeling/Systems/ChangelingDevourSystem.cs b/Content.Shared/Changeling/Systems/ChangelingDevourSystem.cs index 500ee06b22..a30387a807 100644 --- a/Content.Shared/Changeling/Systems/ChangelingDevourSystem.cs +++ b/Content.Shared/Changeling/Systems/ChangelingDevourSystem.cs @@ -4,7 +4,8 @@ using Content.Shared.Armor; using Content.Shared.Atmos.Rotting; using Content.Shared.Body.Components; using Content.Shared.Changeling.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.DoAfter; using Content.Shared.Humanoid; @@ -92,7 +93,7 @@ public sealed class ChangelingDevourSystem : EntitySystem if (damage.Damage.DamageDict.TryGetValue(damagePoints.Key, out var val) && val > comp.DevourConsumeDamageCap) return; } - _damageable.TryChangeDamage(target, comp.DamagePerTick, true, true, damage, user); + _damageable.ChangeDamage((target.Value, damage), comp.DamagePerTick, true, true, user); } /// diff --git a/Content.Shared/Chat/SharedSuicideSystem.cs b/Content.Shared/Chat/SharedSuicideSystem.cs index 4b9eaf24b7..0484e51ab2 100644 --- a/Content.Shared/Chat/SharedSuicideSystem.cs +++ b/Content.Shared/Chat/SharedSuicideSystem.cs @@ -1,8 +1,10 @@ +using System.Linq; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.Mobs.Components; using Robust.Shared.Prototypes; -using System.Linq; namespace Content.Shared.Chat; @@ -40,7 +42,7 @@ public sealed class SharedSuicideSystem : EntitySystem appliedDamageSpecifier.DamageDict[key] = Math.Ceiling((double) (value * lethalAmountOfDamage / totalDamage)); } - _damageableSystem.TryChangeDamage(target, appliedDamageSpecifier, true, origin: target); + _damageableSystem.ChangeDamage(target.AsNullable(), appliedDamageSpecifier, true, origin: target); } /// @@ -64,6 +66,6 @@ public sealed class SharedSuicideSystem : EntitySystem } var damage = new DamageSpecifier(damagePrototype, lethalAmountOfDamage); - _damageableSystem.TryChangeDamage(target, damage, true, origin: target); + _damageableSystem.ChangeDamage(target.AsNullable(), damage, true, origin: target); } } diff --git a/Content.Shared/Climbing/Systems/ClimbSystem.cs b/Content.Shared/Climbing/Systems/ClimbSystem.cs index 45055ebbcc..9cc0a55ce1 100644 --- a/Content.Shared/Climbing/Systems/ClimbSystem.cs +++ b/Content.Shared/Climbing/Systems/ClimbSystem.cs @@ -2,7 +2,7 @@ using Content.Shared.ActionBlocker; using Content.Shared.Buckle.Components; using Content.Shared.Climbing.Components; using Content.Shared.Climbing.Events; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.DoAfter; using Content.Shared.DragDrop; using Content.Shared.Hands.Components; diff --git a/Content.Shared/Clothing/SharedCursedMaskSystem.cs b/Content.Shared/Clothing/SharedCursedMaskSystem.cs index 8ba83be151..359e8ef769 100644 --- a/Content.Shared/Clothing/SharedCursedMaskSystem.cs +++ b/Content.Shared/Clothing/SharedCursedMaskSystem.cs @@ -1,5 +1,6 @@ using Content.Shared.Clothing.Components; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Examine; using Content.Shared.Inventory; using Content.Shared.Movement.Systems; diff --git a/Content.Shared/Clumsy/ClumsySystem.cs b/Content.Shared/Clumsy/ClumsySystem.cs index d7b4019eb8..35866b155a 100644 --- a/Content.Shared/Clumsy/ClumsySystem.cs +++ b/Content.Shared/Clumsy/ClumsySystem.cs @@ -2,7 +2,7 @@ using Content.Shared.CCVar; using Content.Shared.Chemistry.Hypospray.Events; using Content.Shared.Climbing.Components; using Content.Shared.Climbing.Events; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.IdentityManagement; using Content.Shared.Medical; using Content.Shared.Popups; @@ -95,7 +95,7 @@ public sealed class ClumsySystem : EntitySystem args.Cancelled = true; // fail to catch if (ent.Comp.CatchingFailDamage != null) - _damageable.TryChangeDamage(ent, ent.Comp.CatchingFailDamage, origin: args.Item); + _damageable.ChangeDamage(ent.Owner, ent.Comp.CatchingFailDamage, origin: args.Item); // Collisions don't work properly with PopupPredicted or PlayPredicted. // So we make this server only. @@ -127,7 +127,7 @@ public sealed class ClumsySystem : EntitySystem return; if (ent.Comp.GunShootFailDamage != null) - _damageable.TryChangeDamage(ent, ent.Comp.GunShootFailDamage, origin: ent); + _damageable.ChangeDamage(ent.Owner, ent.Comp.GunShootFailDamage, origin: ent); _stun.TryUpdateParalyzeDuration(ent, ent.Comp.GunShootFailStunTime); @@ -199,7 +199,7 @@ public sealed class ClumsySystem : EntitySystem { stunTime = bonkComp.BonkTime; if (bonkComp.BonkDamage != null) - _damageable.TryChangeDamage(target, bonkComp.BonkDamage, true); + _damageable.ChangeDamage(target.Owner, bonkComp.BonkDamage, true); } _stun.TryUpdateParalyzeDuration(target, stunTime); diff --git a/Content.Shared/Damage/Components/ClothingSlowOnDamageModifierComponent.cs b/Content.Shared/Damage/Components/ClothingSlowOnDamageModifierComponent.cs index 3d4bdd597c..faf8a1bb57 100644 --- a/Content.Shared/Damage/Components/ClothingSlowOnDamageModifierComponent.cs +++ b/Content.Shared/Damage/Components/ClothingSlowOnDamageModifierComponent.cs @@ -1,3 +1,4 @@ +using Content.Shared.Damage.Systems; using Robust.Shared.GameStates; namespace Content.Shared.Damage.Components; diff --git a/Content.Shared/Damage/Components/DamageableComponent.cs b/Content.Shared/Damage/Components/DamageableComponent.cs index 1d290181ec..cef27d4d2f 100644 --- a/Content.Shared/Damage/Components/DamageableComponent.cs +++ b/Content.Shared/Damage/Components/DamageableComponent.cs @@ -1,4 +1,5 @@ using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.Mobs; using Content.Shared.StatusIcon; @@ -6,105 +7,100 @@ using Robust.Shared.GameStates; using Robust.Shared.Prototypes; using Robust.Shared.Serialization; -namespace Content.Shared.Damage +namespace Content.Shared.Damage.Components; + +/// +/// Component that allows entities to take damage. +/// +/// +/// The supported damage types are specified using a s. DamageContainers +/// may also have resistances to certain damage types, defined via a . +/// +[RegisterComponent] +[NetworkedComponent] +[Access(typeof(DamageableSystem), Other = AccessPermissions.ReadExecute)] +public sealed partial class DamageableComponent : Component { /// - /// Component that allows entities to take damage. + /// This specifies what damage types are supported by this component. + /// If null, all damage types will be supported. + /// + [DataField("damageContainer")] + // ReSharper disable once InconsistentNaming - This is wrong but fixing it is potentially annoying for downstreams. + public ProtoId? DamageContainerID; + + /// + /// This will be applied to any damage that is dealt to this container, + /// unless the damage explicitly ignores resistances. /// /// - /// The supported damage types are specified using a s. DamageContainers - /// may also have resistances to certain damage types, defined via a . + /// Though DamageModifierSets can be deserialized directly, we only want to use the prototype version here + /// to reduce duplication. /// - [RegisterComponent] - [NetworkedComponent] - [Access(typeof(DamageableSystem), Other = AccessPermissions.ReadExecute)] - public sealed partial class DamageableComponent : Component + [DataField("damageModifierSet")] + public ProtoId? DamageModifierSetId; + + /// + /// All the damage information is stored in this . + /// + /// + /// If this data-field is specified, this allows damageable components to be initialized with non-zero damage. + /// + [DataField(readOnly: true)] //TODO FULL GAME SAVE + public DamageSpecifier Damage = new(); + + /// + /// Damage, indexed by ID keys. + /// + /// + /// Groups which have no members that are supported by this component will not be present in this + /// dictionary. + /// + [ViewVariables] public Dictionary DamagePerGroup = new(); + + /// + /// The sum of all damages in the DamageableComponent. + /// + [ViewVariables] + public FixedPoint2 TotalDamage; + + [DataField("radiationDamageTypes")] + // ReSharper disable once UseCollectionExpression - Cannot refactor this as it's a potential sandbox violation. + public List> RadiationDamageTypeIDs = new() { "Radiation" }; + + /// + /// Group types that affect the pain overlay. + /// + /// TODO: Add support for adding damage types specifically rather than whole damage groups + [DataField] + // ReSharper disable once UseCollectionExpression - Cannot refactor this as it's a potential sandbox volation. + public List> PainDamageGroups = new() { "Brute", "Burn" }; + + [DataField] + public Dictionary> HealthIcons = new() { - /// - /// This specifies what damage types are supported by this component. - /// If null, all damage types will be supported. - /// - [DataField("damageContainer")] - public ProtoId? DamageContainerID; + { MobState.Alive, "HealthIconFine" }, + { MobState.Critical, "HealthIconCritical" }, + { MobState.Dead, "HealthIconDead" }, + }; - /// - /// This will be applied to any damage that is dealt to this container, - /// unless the damage explicitly ignores resistances. - /// - /// - /// Though DamageModifierSets can be deserialized directly, we only want to use the prototype version here - /// to reduce duplication. - /// - [DataField("damageModifierSet")] - public ProtoId? DamageModifierSetId; + [DataField] + public ProtoId RottingIcon = "HealthIconRotting"; - /// - /// All the damage information is stored in this . - /// - /// - /// If this data-field is specified, this allows damageable components to be initialized with non-zero damage. - /// - [DataField(readOnly: true)] // TODO FULL GAME SAVE - public DamageSpecifier Damage = new(); - - /// - /// Damage, indexed by ID keys. - /// - /// - /// Groups which have no members that are supported by this component will not be present in this - /// dictionary. - /// - [ViewVariables] public Dictionary DamagePerGroup = new(); - - /// - /// The sum of all damages in the DamageableComponent. - /// - [ViewVariables] - public FixedPoint2 TotalDamage; - - [DataField("radiationDamageTypes")] - public List> RadiationDamageTypeIDs = new() { "Radiation" }; - - /// - /// Group types that affect the pain overlay. - /// - /// TODO: Add support for adding damage types specifically rather than whole damage groups - [DataField] - public List> PainDamageGroups = new() { "Brute", "Burn" }; - - [DataField] - public Dictionary> HealthIcons = new() - { - { MobState.Alive, "HealthIconFine" }, - { MobState.Critical, "HealthIconCritical" }, - { MobState.Dead, "HealthIconDead" }, - }; - - [DataField] - public ProtoId RottingIcon = "HealthIconRotting"; - - [DataField] - public FixedPoint2? HealthBarThreshold; - } - - [Serializable, NetSerializable] - public sealed class DamageableComponentState : ComponentState - { - public readonly Dictionary DamageDict; - public readonly string? DamageContainerId; - public readonly string? ModifierSetId; - public readonly FixedPoint2? HealthBarThreshold; - - public DamageableComponentState( - Dictionary damageDict, - string? damageContainerId, - string? modifierSetId, - FixedPoint2? healthBarThreshold) - { - DamageDict = damageDict; - DamageContainerId = damageContainerId; - ModifierSetId = modifierSetId; - HealthBarThreshold = healthBarThreshold; - } - } + [DataField] + public FixedPoint2? HealthBarThreshold; +} + +[Serializable, NetSerializable] +public sealed class DamageableComponentState( + Dictionary damageDict, + ProtoId? damageContainerId, + ProtoId? modifierSetId, + FixedPoint2? healthBarThreshold) + : ComponentState +{ + public readonly Dictionary DamageDict = damageDict; + public readonly ProtoId? DamageContainerId = damageContainerId; + public readonly ProtoId? ModifierSetId = modifierSetId; + public readonly FixedPoint2? HealthBarThreshold = healthBarThreshold; } diff --git a/Content.Shared/Damage/Components/IgnoreSlowOnDamageComponent.cs b/Content.Shared/Damage/Components/IgnoreSlowOnDamageComponent.cs index e933eb1a79..101a494bc9 100644 --- a/Content.Shared/Damage/Components/IgnoreSlowOnDamageComponent.cs +++ b/Content.Shared/Damage/Components/IgnoreSlowOnDamageComponent.cs @@ -1,3 +1,4 @@ +using Content.Shared.Damage.Systems; using Robust.Shared.GameStates; namespace Content.Shared.Damage.Components; diff --git a/Content.Shared/Damage/Components/RequireProjectileTargetComponent.cs b/Content.Shared/Damage/Components/RequireProjectileTargetComponent.cs index 5bd8292daa..3c94dcbc38 100644 --- a/Content.Shared/Damage/Components/RequireProjectileTargetComponent.cs +++ b/Content.Shared/Damage/Components/RequireProjectileTargetComponent.cs @@ -1,3 +1,4 @@ +using Content.Shared.Damage.Systems; using Robust.Shared.GameStates; namespace Content.Shared.Damage.Components; diff --git a/Content.Shared/Damage/DamageModifierSet.cs b/Content.Shared/Damage/DamageModifierSet.cs index eaa6e93da4..d8b00ad1f2 100644 --- a/Content.Shared/Damage/DamageModifierSet.cs +++ b/Content.Shared/Damage/DamageModifierSet.cs @@ -1,3 +1,4 @@ +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; using Robust.Shared.Serialization; using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom.Prototype.Dictionary; diff --git a/Content.Shared/Damage/DamageSpecifier.cs b/Content.Shared/Damage/DamageSpecifier.cs index 7bf921baa2..6c11f88b1e 100644 --- a/Content.Shared/Damage/DamageSpecifier.cs +++ b/Content.Shared/Damage/DamageSpecifier.cs @@ -1,5 +1,6 @@ using System.Linq; using System.Text.Json.Serialization; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; using Content.Shared.FixedPoint; using JetBrains.Annotations; diff --git a/Content.Shared/Damage/Prototypes/DamageContainerPrototype.cs b/Content.Shared/Damage/Prototypes/DamageContainerPrototype.cs index 00322f0884..1643a5469d 100644 --- a/Content.Shared/Damage/Prototypes/DamageContainerPrototype.cs +++ b/Content.Shared/Damage/Prototypes/DamageContainerPrototype.cs @@ -1,5 +1,5 @@ +using Content.Shared.Damage.Components; using Robust.Shared.Prototypes; -using Robust.Shared.Serialization; namespace Content.Shared.Damage.Prototypes { diff --git a/Content.Shared/Damage/Prototypes/DamageGroupPrototype.cs b/Content.Shared/Damage/Prototypes/DamageGroupPrototype.cs index a33064f934..facdcce0e8 100644 --- a/Content.Shared/Damage/Prototypes/DamageGroupPrototype.cs +++ b/Content.Shared/Damage/Prototypes/DamageGroupPrototype.cs @@ -1,5 +1,5 @@ +using Content.Shared.Damage.Components; using Robust.Shared.Prototypes; -using Robust.Shared.Serialization; namespace Content.Shared.Damage.Prototypes { diff --git a/Content.Shared/Damage/Systems/DamageOnAttackedSystem.cs b/Content.Shared/Damage/Systems/DamageOnAttackedSystem.cs index 29de43fba4..d628f40b76 100644 --- a/Content.Shared/Damage/Systems/DamageOnAttackedSystem.cs +++ b/Content.Shared/Damage/Systems/DamageOnAttackedSystem.cs @@ -73,9 +73,9 @@ public sealed class DamageOnAttackedSystem : EntitySystem } } - totalDamage = _damageableSystem.TryChangeDamage(args.User, totalDamage, entity.Comp.IgnoreResistances, origin: entity); + totalDamage = _damageableSystem.ChangeDamage(args.User, totalDamage, entity.Comp.IgnoreResistances, origin: entity); - if (totalDamage != null && totalDamage.AnyPositive()) + if (totalDamage.AnyPositive()) { _adminLogger.Add(LogType.Damaged, $"{ToPrettyString(args.User):user} injured themselves by attacking {ToPrettyString(entity):target} and received {totalDamage.GetTotal():damage} damage"); _audioSystem.PlayPredicted(entity.Comp.InteractSound, entity, args.User); diff --git a/Content.Shared/Damage/Systems/DamageOnInteractSystem.cs b/Content.Shared/Damage/Systems/DamageOnInteractSystem.cs index bd3b6979f7..401c94f33e 100644 --- a/Content.Shared/Damage/Systems/DamageOnInteractSystem.cs +++ b/Content.Shared/Damage/Systems/DamageOnInteractSystem.cs @@ -65,7 +65,7 @@ public sealed class DamageOnInteractSystem : EntitySystem // or checking the entity for the comp itself if the inventory didn't work if (protectiveEntity.Comp == null && TryComp(args.User, out var protectiveComp)) protectiveEntity = (args.User, protectiveComp); - + // if protectiveComp isn't null after all that, it means the user has protection, // so let's calculate how much they resist @@ -75,9 +75,9 @@ public sealed class DamageOnInteractSystem : EntitySystem } } - totalDamage = _damageableSystem.TryChangeDamage(args.User, totalDamage, origin: args.Target); + totalDamage = _damageableSystem.ChangeDamage(args.User, totalDamage, origin: args.Target); - if (totalDamage != null && totalDamage.AnyPositive()) + if (totalDamage.AnyPositive()) { // Record this interaction and determine when a user is allowed to interact with this entity again entity.Comp.LastInteraction = _gameTiming.CurTime; diff --git a/Content.Shared/Damage/Systems/DamageableSystem.API.cs b/Content.Shared/Damage/Systems/DamageableSystem.API.cs new file mode 100644 index 0000000000..c2a1374901 --- /dev/null +++ b/Content.Shared/Damage/Systems/DamageableSystem.API.cs @@ -0,0 +1,235 @@ +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Prototypes; +using Content.Shared.FixedPoint; +using Robust.Shared.Prototypes; + +namespace Content.Shared.Damage.Systems; + +public sealed partial class DamageableSystem +{ + /// + /// Directly sets the damage specifier of a damageable component. + /// + /// + /// Useful for some unfriendly folk. Also ensures that cached values are updated and that a damage changed + /// event is raised. + /// + public void SetDamage(Entity ent, DamageSpecifier damage) + { + if (!_damageableQuery.Resolve(ent, ref ent.Comp, false)) + return; + + ent.Comp.Damage = damage; + + OnEntityDamageChanged((ent, ent.Comp)); + } + + /// + /// Applies damage specified via a . + /// + /// + /// is effectively just a dictionary of damage types and damage values. This + /// function just applies the container's resistances (unless otherwise specified) and then changes the + /// stored damage data. Division of group damage into types is managed by . + /// + /// + /// If the attempt was successful or not. + /// + public bool TryChangeDamage( + Entity ent, + DamageSpecifier damage, + bool ignoreResistances = false, + bool interruptsDoAfters = true, + EntityUid? origin = null, + bool ignoreGlobalModifiers = false + ) + { + //! Empty just checks if the DamageSpecifier is _literally_ empty, as in, is internal dictionary of damage types is empty. + // If you deal 0.0 of some damage type, Empty will be false! + return !TryChangeDamage(ent, damage, out _, ignoreResistances, interruptsDoAfters, origin, ignoreGlobalModifiers); + } + + /// + /// Applies damage specified via a . + /// + /// + /// is effectively just a dictionary of damage types and damage values. This + /// function just applies the container's resistances (unless otherwise specified) and then changes the + /// stored damage data. Division of group damage into types is managed by . + /// + /// + /// If the attempt was successful or not. + /// + public bool TryChangeDamage( + Entity ent, + DamageSpecifier damage, + out DamageSpecifier newDamage, + bool ignoreResistances = false, + bool interruptsDoAfters = true, + EntityUid? origin = null, + bool ignoreGlobalModifiers = false + ) + { + //! Empty just checks if the DamageSpecifier is _literally_ empty, as in, is internal dictionary of damage types is empty. + // If you deal 0.0 of some damage type, Empty will be false! + newDamage = ChangeDamage(ent, damage, ignoreResistances, interruptsDoAfters, origin, ignoreGlobalModifiers); + return !damage.Empty; + } + + /// + /// Applies damage specified via a . + /// + /// + /// is effectively just a dictionary of damage types and damage values. This + /// function just applies the container's resistances (unless otherwise specified) and then changes the + /// stored damage data. Division of group damage into types is managed by . + /// + /// + /// The actual amount of damage taken, as a DamageSpecifier. + /// + public DamageSpecifier ChangeDamage( + Entity ent, + DamageSpecifier damage, + bool ignoreResistances = false, + bool interruptsDoAfters = true, + EntityUid? origin = null, + bool ignoreGlobalModifiers = false + ) + { + var damageDone = new DamageSpecifier(); + + if (!_damageableQuery.Resolve(ent, ref ent.Comp, false)) + return damageDone; + + if (damage.Empty) + return damageDone; + + var before = new BeforeDamageChangedEvent(damage, origin); + RaiseLocalEvent(ent, ref before); + + if (before.Cancelled) + return damageDone; + + // Apply resistances + if (!ignoreResistances) + { + if ( + ent.Comp.DamageModifierSetId != null && + _prototypeManager.Resolve(ent.Comp.DamageModifierSetId, out var modifierSet) + ) + damage = DamageSpecifier.ApplyModifierSet(damage, modifierSet); + + // TODO DAMAGE + // byref struct event. + var ev = new DamageModifyEvent(damage, origin); + RaiseLocalEvent(ent, ev); + damage = ev.Damage; + + if (damage.Empty) + return damageDone; + } + + if (!ignoreGlobalModifiers) + damage = ApplyUniversalAllModifiers(damage); + + + damageDone.DamageDict.EnsureCapacity(damage.DamageDict.Count); + + var dict = ent.Comp.Damage.DamageDict; + foreach (var (type, value) in damage.DamageDict) + { + // CollectionsMarshal my beloved. + if (!dict.TryGetValue(type, out var oldValue)) + continue; + + var newValue = FixedPoint2.Max(FixedPoint2.Zero, oldValue + value); + if (newValue == oldValue) + continue; + + dict[type] = newValue; + damageDone.DamageDict[type] = newValue - oldValue; + } + + if (!damageDone.Empty) + OnEntityDamageChanged((ent, ent.Comp), damageDone, interruptsDoAfters, origin); + + return damageDone; + } + + /// + /// Applies the two universal "All" modifiers, if set. + /// Individual damage source modifiers are set in their respective code. + /// + /// The damage to be changed. + public DamageSpecifier ApplyUniversalAllModifiers(DamageSpecifier damage) + { + // Checks for changes first since they're unlikely in normal play. + if ( + MathHelper.CloseToPercent(UniversalAllDamageModifier, 1f) && + MathHelper.CloseToPercent(UniversalAllHealModifier, 1f) + ) + return damage; + + foreach (var (key, value) in damage.DamageDict) + { + if (value == 0) + continue; + + if (value > 0) + { + damage.DamageDict[key] *= UniversalAllDamageModifier; + + continue; + } + + if (value < 0) + damage.DamageDict[key] *= UniversalAllHealModifier; + } + + return damage; + } + + public void ClearAllDamage(Entity ent) + { + SetAllDamage(ent, FixedPoint2.Zero); + } + + /// + /// Sets all damage types supported by a to the specified value. + /// + /// + /// Does nothing If the given damage value is negative. + /// + public void SetAllDamage(Entity ent, FixedPoint2 newValue) + { + if (!_damageableQuery.Resolve(ent, ref ent.Comp, false)) + return; + + if (newValue < 0) + return; + + foreach (var type in ent.Comp.Damage.DamageDict.Keys) + { + ent.Comp.Damage.DamageDict[type] = newValue; + } + + // Setting damage does not count as 'dealing' damage, even if it is set to a larger value, so we pass an + // empty damage delta. + OnEntityDamageChanged((ent, ent.Comp), new DamageSpecifier()); + } + + /// + /// Set's the damage modifier set prototype for this entity. + /// + /// The entity we're setting the modifier set of. + /// The prototype we're setting. + public void SetDamageModifierSetId(Entity ent, ProtoId? damageModifierSetId) + { + if (!_damageableQuery.Resolve(ent, ref ent.Comp, false)) + return; + + ent.Comp.DamageModifierSetId = damageModifierSetId; + + Dirty(ent); + } +} diff --git a/Content.Shared/Damage/Systems/DamageableSystem.BenchmarkHelpers.cs b/Content.Shared/Damage/Systems/DamageableSystem.BenchmarkHelpers.cs index d248d717b8..5ca7fe1992 100644 --- a/Content.Shared/Damage/Systems/DamageableSystem.BenchmarkHelpers.cs +++ b/Content.Shared/Damage/Systems/DamageableSystem.BenchmarkHelpers.cs @@ -1,4 +1,6 @@ -namespace Content.Shared.Damage; +using Content.Shared.Damage.Components; + +namespace Content.Shared.Damage.Systems; public sealed partial class DamageableSystem { @@ -9,7 +11,7 @@ public sealed partial class DamageableSystem { foreach (var (uid, damageable) in damageables) { - TryChangeDamage(uid, damage, damageable: damageable); + TryChangeDamage((uid, damageable), damage); } } } diff --git a/Content.Shared/Damage/Systems/DamageableSystem.Events.cs b/Content.Shared/Damage/Systems/DamageableSystem.Events.cs new file mode 100644 index 0000000000..3e985ba204 --- /dev/null +++ b/Content.Shared/Damage/Systems/DamageableSystem.Events.cs @@ -0,0 +1,290 @@ +using Content.Shared.CCVar; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Prototypes; +using Content.Shared.FixedPoint; +using Content.Shared.Inventory; +using Content.Shared.Radiation.Events; +using Content.Shared.Rejuvenate; +using Robust.Shared.GameStates; + +namespace Content.Shared.Damage.Systems; + +public sealed partial class DamageableSystem +{ + public override void Initialize() + { + SubscribeLocalEvent(DamageableInit); + SubscribeLocalEvent(DamageableHandleState); + SubscribeLocalEvent(DamageableGetState); + SubscribeLocalEvent(OnIrradiated); + SubscribeLocalEvent(OnRejuvenate); + + _appearanceQuery = GetEntityQuery(); + _damageableQuery = GetEntityQuery(); + + // Damage modifier CVars are updated and stored here to be queried in other systems. + // Note that certain modifiers requires reloading the guidebook. + Subs.CVar( + _config, + CCVars.PlaytestAllDamageModifier, + value => + { + UniversalAllDamageModifier = value; + _chemistryGuideData.ReloadAllReagentPrototypes(); + _explosion.ReloadMap(); + }, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestAllHealModifier, + value => + { + UniversalAllHealModifier = value; + _chemistryGuideData.ReloadAllReagentPrototypes(); + }, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestProjectileDamageModifier, + value => UniversalProjectileDamageModifier = value, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestMeleeDamageModifier, + value => UniversalMeleeDamageModifier = value, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestProjectileDamageModifier, + value => UniversalProjectileDamageModifier = value, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestHitscanDamageModifier, + value => UniversalHitscanDamageModifier = value, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestReagentDamageModifier, + value => + { + UniversalReagentDamageModifier = value; + _chemistryGuideData.ReloadAllReagentPrototypes(); + }, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestReagentHealModifier, + value => + { + UniversalReagentHealModifier = value; + _chemistryGuideData.ReloadAllReagentPrototypes(); + }, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestExplosionDamageModifier, + value => + { + UniversalExplosionDamageModifier = value; + _explosion.ReloadMap(); + }, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestThrownDamageModifier, + value => UniversalThrownDamageModifier = value, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestTopicalsHealModifier, + value => UniversalTopicalsHealModifier = value, + true + ); + Subs.CVar( + _config, + CCVars.PlaytestMobDamageModifier, + value => UniversalMobDamageModifier = value, + true + ); + } + + /// + /// Initialize a damageable component + /// + private void DamageableInit(Entity ent, ref ComponentInit _) + { + if ( + ent.Comp.DamageContainerID is null || + !_prototypeManager.Resolve(ent.Comp.DamageContainerID, out var damageContainerPrototype) + ) + { + // No DamageContainerPrototype was given. So we will allow the container to support all damage types + foreach (var type in _prototypeManager.EnumeratePrototypes()) + { + ent.Comp.Damage.DamageDict.TryAdd(type.ID, FixedPoint2.Zero); + } + } + else + { + // Initialize damage dictionary, using the types and groups from the damage + // container prototype + foreach (var type in damageContainerPrototype.SupportedTypes) + { + ent.Comp.Damage.DamageDict.TryAdd(type, FixedPoint2.Zero); + } + + foreach (var groupId in damageContainerPrototype.SupportedGroups) + { + var group = _prototypeManager.Index(groupId); + foreach (var type in group.DamageTypes) + { + ent.Comp.Damage.DamageDict.TryAdd(type, FixedPoint2.Zero); + } + } + } + + ent.Comp.Damage.GetDamagePerGroup(_prototypeManager, ent.Comp.DamagePerGroup); + ent.Comp.TotalDamage = ent.Comp.Damage.GetTotal(); + } + + private void OnIrradiated(Entity ent, ref OnIrradiatedEvent args) + { + var damageValue = FixedPoint2.New(args.TotalRads); + + // Radiation should really just be a damage group instead of a list of types. + DamageSpecifier damage = new(); + foreach (var typeId in ent.Comp.RadiationDamageTypeIDs) + { + damage.DamageDict.Add(typeId, damageValue); + } + + ChangeDamage(ent.Owner, damage, interruptsDoAfters: false, origin: args.Origin); + } + + private void OnRejuvenate(Entity ent, ref RejuvenateEvent args) + { + // Do this so that the state changes when we set the damage + _mobThreshold.SetAllowRevives(ent, true); + ClearAllDamage(ent.AsNullable()); + _mobThreshold.SetAllowRevives(ent, false); + } + + private void DamageableHandleState(Entity ent, ref ComponentHandleState args) + { + if (args.Current is not DamageableComponentState state) + return; + + ent.Comp.DamageContainerID = state.DamageContainerId; + ent.Comp.DamageModifierSetId = state.ModifierSetId; + ent.Comp.HealthBarThreshold = state.HealthBarThreshold; + + // Has the damage actually changed? + DamageSpecifier newDamage = new() { DamageDict = new Dictionary(state.DamageDict) }; + var delta = newDamage - ent.Comp.Damage; + delta.TrimZeros(); + + if (delta.Empty) + return; + + ent.Comp.Damage = newDamage; + + OnEntityDamageChanged(ent, delta); + } +} + +/// +/// Raised before damage is done, so stuff can cancel it if necessary. +/// +[ByRefEvent] +public record struct BeforeDamageChangedEvent(DamageSpecifier Damage, EntityUid? Origin = null, bool Cancelled = false); + +/// +/// Raised on an entity when damage is about to be dealt, +/// in case anything else needs to modify it other than the base +/// damageable component. +/// +/// For example, armor. +/// +public sealed class DamageModifyEvent(DamageSpecifier damage, EntityUid? origin = null) + : EntityEventArgs, IInventoryRelayEvent +{ + // Whenever locational damage is a thing, this should just check only that bit of armour. + public SlotFlags TargetSlots => ~SlotFlags.POCKET; + + public readonly DamageSpecifier OriginalDamage = damage; + public DamageSpecifier Damage = damage; +} + +public sealed class DamageChangedEvent : EntityEventArgs +{ + /// + /// This is the component whose damage was changed. + /// + /// + /// Given that nearly every component that cares about a change in the damage, needs to know the + /// current damage values, directly passing this information prevents a lot of duplicate + /// Owner.TryGetComponent() calls. + /// + public readonly DamageableComponent Damageable; + + /// + /// The amount by which the damage has changed. If the damage was set directly to some number, this will be + /// null. + /// + public readonly DamageSpecifier? DamageDelta; + + /// + /// Was any of the damage change dealing damage, or was it all healing? + /// + public readonly bool DamageIncreased; + + /// + /// Does this event interrupt DoAfters? + /// Note: As provided in the constructor, this *does not* account for DamageIncreased. + /// As written into the event, this *does* account for DamageIncreased. + /// + public readonly bool InterruptsDoAfters; + + /// + /// Contains the entity which caused the change in damage, if any was responsible. + /// + public readonly EntityUid? Origin; + + public DamageChangedEvent( + DamageableComponent damageable, + DamageSpecifier? damageDelta, + bool interruptsDoAfters, + EntityUid? origin + ) + { + Damageable = damageable; + DamageDelta = damageDelta; + Origin = origin; + + if (DamageDelta is null) + return; + + foreach (var damageChange in DamageDelta.DamageDict.Values) + { + if (damageChange <= 0) + continue; + + DamageIncreased = true; + + break; + } + + InterruptsDoAfters = interruptsDoAfters && DamageIncreased; + } +} diff --git a/Content.Shared/Damage/Systems/DamageableSystem.cs b/Content.Shared/Damage/Systems/DamageableSystem.cs index f1e259001c..2b4c5ad360 100644 --- a/Content.Shared/Damage/Systems/DamageableSystem.cs +++ b/Content.Shared/Damage/Systems/DamageableSystem.cs @@ -1,469 +1,97 @@ using System.Linq; -using Content.Shared.CCVar; using Content.Shared.Chemistry; -using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Components; using Content.Shared.Explosion.EntitySystems; -using Content.Shared.FixedPoint; -using Content.Shared.Inventory; -using Content.Shared.Mobs.Components; using Content.Shared.Mobs.Systems; -using Content.Shared.Radiation.Events; -using Content.Shared.Rejuvenate; using Robust.Shared.Configuration; using Robust.Shared.GameStates; using Robust.Shared.Network; using Robust.Shared.Prototypes; using Robust.Shared.Utility; -namespace Content.Shared.Damage +namespace Content.Shared.Damage.Systems; + +public sealed partial class DamageableSystem : EntitySystem { - public sealed partial class DamageableSystem : EntitySystem - { - [Dependency] private readonly IPrototypeManager _prototypeManager = default!; - [Dependency] private readonly SharedAppearanceSystem _appearance = default!; - [Dependency] private readonly INetManager _netMan = default!; - [Dependency] private readonly MobThresholdSystem _mobThreshold = default!; - [Dependency] private readonly IConfigurationManager _config = default!; - [Dependency] private readonly SharedChemistryGuideDataSystem _chemistryGuideData = default!; - [Dependency] private readonly SharedExplosionSystem _explosion = default!; + [Dependency] private readonly IPrototypeManager _prototypeManager = default!; + [Dependency] private readonly SharedAppearanceSystem _appearance = default!; + [Dependency] private readonly INetManager _netMan = default!; + [Dependency] private readonly MobThresholdSystem _mobThreshold = default!; + [Dependency] private readonly IConfigurationManager _config = default!; + [Dependency] private readonly SharedChemistryGuideDataSystem _chemistryGuideData = default!; + [Dependency] private readonly SharedExplosionSystem _explosion = default!; - private EntityQuery _appearanceQuery; - private EntityQuery _damageableQuery; + private EntityQuery _appearanceQuery; + private EntityQuery _damageableQuery; - public float UniversalAllDamageModifier { get; private set; } = 1f; - public float UniversalAllHealModifier { get; private set; } = 1f; - public float UniversalMeleeDamageModifier { get; private set; } = 1f; - public float UniversalProjectileDamageModifier { get; private set; } = 1f; - public float UniversalHitscanDamageModifier { get; private set; } = 1f; - public float UniversalReagentDamageModifier { get; private set; } = 1f; - public float UniversalReagentHealModifier { get; private set; } = 1f; - public float UniversalExplosionDamageModifier { get; private set; } = 1f; - public float UniversalThrownDamageModifier { get; private set; } = 1f; - public float UniversalTopicalsHealModifier { get; private set; } = 1f; - public float UniversalMobDamageModifier { get; private set; } = 1f; - - public override void Initialize() - { - SubscribeLocalEvent(DamageableInit); - SubscribeLocalEvent(DamageableHandleState); - SubscribeLocalEvent(DamageableGetState); - SubscribeLocalEvent(OnIrradiated); - SubscribeLocalEvent(OnRejuvenate); - - _appearanceQuery = GetEntityQuery(); - _damageableQuery = GetEntityQuery(); - - // Damage modifier CVars are updated and stored here to be queried in other systems. - // Note that certain modifiers requires reloading the guidebook. - Subs.CVar(_config, CCVars.PlaytestAllDamageModifier, value => - { - UniversalAllDamageModifier = value; - _chemistryGuideData.ReloadAllReagentPrototypes(); - _explosion.ReloadMap(); - }, true); - Subs.CVar(_config, CCVars.PlaytestAllHealModifier, value => - { - UniversalAllHealModifier = value; - _chemistryGuideData.ReloadAllReagentPrototypes(); - }, true); - Subs.CVar(_config, CCVars.PlaytestProjectileDamageModifier, value => UniversalProjectileDamageModifier = value, true); - Subs.CVar(_config, CCVars.PlaytestMeleeDamageModifier, value => UniversalMeleeDamageModifier = value, true); - Subs.CVar(_config, CCVars.PlaytestProjectileDamageModifier, value => UniversalProjectileDamageModifier = value, true); - Subs.CVar(_config, CCVars.PlaytestHitscanDamageModifier, value => UniversalHitscanDamageModifier = value, true); - Subs.CVar(_config, CCVars.PlaytestReagentDamageModifier, value => - { - UniversalReagentDamageModifier = value; - _chemistryGuideData.ReloadAllReagentPrototypes(); - }, true); - Subs.CVar(_config, CCVars.PlaytestReagentHealModifier, value => - { - UniversalReagentHealModifier = value; - _chemistryGuideData.ReloadAllReagentPrototypes(); - }, true); - Subs.CVar(_config, CCVars.PlaytestExplosionDamageModifier, value => - { - UniversalExplosionDamageModifier = value; - _explosion.ReloadMap(); - }, true); - Subs.CVar(_config, CCVars.PlaytestThrownDamageModifier, value => UniversalThrownDamageModifier = value, true); - Subs.CVar(_config, CCVars.PlaytestTopicalsHealModifier, value => UniversalTopicalsHealModifier = value, true); - Subs.CVar(_config, CCVars.PlaytestMobDamageModifier, value => UniversalMobDamageModifier = value, true); - } - - /// - /// Initialize a damageable component - /// - private void DamageableInit(EntityUid uid, DamageableComponent component, ComponentInit _) - { - if (component.DamageContainerID != null && - _prototypeManager.Resolve(component.DamageContainerID, - out var damageContainerPrototype)) - { - // Initialize damage dictionary, using the types and groups from the damage - // container prototype - foreach (var type in damageContainerPrototype.SupportedTypes) - { - component.Damage.DamageDict.TryAdd(type, FixedPoint2.Zero); - } - - foreach (var groupId in damageContainerPrototype.SupportedGroups) - { - var group = _prototypeManager.Index(groupId); - foreach (var type in group.DamageTypes) - { - component.Damage.DamageDict.TryAdd(type, FixedPoint2.Zero); - } - } - } - else - { - // No DamageContainerPrototype was given. So we will allow the container to support all damage types - foreach (var type in _prototypeManager.EnumeratePrototypes()) - { - component.Damage.DamageDict.TryAdd(type.ID, FixedPoint2.Zero); - } - } - - component.Damage.GetDamagePerGroup(_prototypeManager, component.DamagePerGroup); - component.TotalDamage = component.Damage.GetTotal(); - } - - /// - /// Directly sets the damage specifier of a damageable component. - /// - /// - /// Useful for some unfriendly folk. Also ensures that cached values are updated and that a damage changed - /// event is raised. - /// - public void SetDamage(EntityUid uid, DamageableComponent damageable, DamageSpecifier damage) - { - damageable.Damage = damage; - DamageChanged(uid, damageable); - } - - /// - /// If the damage in a DamageableComponent was changed, this function should be called. - /// - /// - /// This updates cached damage information, flags the component as dirty, and raises a damage changed event. - /// The damage changed event is used by other systems, such as damage thresholds. - /// - public void DamageChanged(EntityUid uid, DamageableComponent component, DamageSpecifier? damageDelta = null, - bool interruptsDoAfters = true, EntityUid? origin = null) - { - component.Damage.GetDamagePerGroup(_prototypeManager, component.DamagePerGroup); - component.TotalDamage = component.Damage.GetTotal(); - Dirty(uid, component); - - if (_appearanceQuery.TryGetComponent(uid, out var appearance) && damageDelta != null) - { - var data = new DamageVisualizerGroupData(component.DamagePerGroup.Keys.ToList()); - _appearance.SetData(uid, DamageVisualizerKeys.DamageUpdateGroups, data, appearance); - } - - // TODO DAMAGE - // byref struct event. - RaiseLocalEvent(uid, new DamageChangedEvent(component, damageDelta, interruptsDoAfters, origin)); - } - - /// - /// Applies damage specified via a . - /// - /// - /// is effectively just a dictionary of damage types and damage values. This - /// function just applies the container's resistances (unless otherwise specified) and then changes the - /// stored damage data. Division of group damage into types is managed by . - /// - /// - /// Returns a with information about the actual damage changes. This will be - /// null if the user had no applicable components that can take damage. - /// - /// If true, this will ignore the entity's damage modifier ( and skip raising a . - /// Whether the damage should cancel any damage sensitive do-afters - /// The entity that is causing this damage - /// If true, this will skip over applying the universal damage modifiers (see ). - /// - public DamageSpecifier? TryChangeDamage( - EntityUid? uid, - DamageSpecifier damage, - bool ignoreResistances = false, - bool interruptsDoAfters = true, - DamageableComponent? damageable = null, - EntityUid? origin = null, - bool ignoreGlobalModifiers = false) - { - if (!uid.HasValue || !_damageableQuery.Resolve(uid.Value, ref damageable, false)) - { - // TODO BODY SYSTEM pass damage onto body system - // BOBBY WHEN? - return null; - } - - if (damage.Empty) - { - return damage; - } - - var before = new BeforeDamageChangedEvent(damage, origin); - RaiseLocalEvent(uid.Value, ref before); - - if (before.Cancelled) - return null; - - // Apply resistances - if (!ignoreResistances) - { - if (damageable.DamageModifierSetId != null && - _prototypeManager.Resolve(damageable.DamageModifierSetId, out var modifierSet)) - { - damage = DamageSpecifier.ApplyModifierSet(damage, modifierSet); - } - - // TODO DAMAGE - // byref struct event. - var ev = new DamageModifyEvent(damage, origin); - RaiseLocalEvent(uid.Value, ev); - damage = ev.Damage; - - if (damage.Empty) - { - return damage; - } - } - - if (!ignoreGlobalModifiers) - damage = ApplyUniversalAllModifiers(damage); - - var delta = new DamageSpecifier(); - delta.DamageDict.EnsureCapacity(damage.DamageDict.Count); - - var dict = damageable.Damage.DamageDict; - foreach (var (type, value) in damage.DamageDict) - { - // CollectionsMarshal my beloved. - if (!dict.TryGetValue(type, out var oldValue)) - continue; - - var newValue = FixedPoint2.Max(FixedPoint2.Zero, oldValue + value); - if (newValue == oldValue) - continue; - - dict[type] = newValue; - delta.DamageDict[type] = newValue - oldValue; - } - - if (delta.DamageDict.Count > 0) - DamageChanged(uid.Value, damageable, delta, interruptsDoAfters, origin); - - return delta; - } - - /// - /// Applies the two univeral "All" modifiers, if set. - /// Individual damage source modifiers are set in their respective code. - /// - /// The damage to be changed. - public DamageSpecifier ApplyUniversalAllModifiers(DamageSpecifier damage) - { - // Checks for changes first since they're unlikely in normal play. - if (UniversalAllDamageModifier == 1f && UniversalAllHealModifier == 1f) - return damage; - - foreach (var (key, value) in damage.DamageDict) - { - if (value == 0) - continue; - - if (value > 0) - { - damage.DamageDict[key] *= UniversalAllDamageModifier; - continue; - } - - if (value < 0) - { - damage.DamageDict[key] *= UniversalAllHealModifier; - } - } - - return damage; - } - - /// - /// Sets all damage types supported by a to the specified value. - /// - /// - /// Does nothing If the given damage value is negative. - /// - public void SetAllDamage(EntityUid uid, DamageableComponent component, FixedPoint2 newValue) - { - if (newValue < 0) - { - // invalid value - return; - } - - foreach (var type in component.Damage.DamageDict.Keys) - { - component.Damage.DamageDict[type] = newValue; - } - - // Setting damage does not count as 'dealing' damage, even if it is set to a larger value, so we pass an - // empty damage delta. - DamageChanged(uid, component, new DamageSpecifier()); - } - - public void SetDamageModifierSetId(EntityUid uid, string? damageModifierSetId, DamageableComponent? comp = null) - { - if (!_damageableQuery.Resolve(uid, ref comp)) - return; - - comp.DamageModifierSetId = damageModifierSetId; - Dirty(uid, comp); - } - - private void DamageableGetState(EntityUid uid, DamageableComponent component, ref ComponentGetState args) - { - if (_netMan.IsServer) - { - args.State = new DamageableComponentState(component.Damage.DamageDict, component.DamageContainerID, component.DamageModifierSetId, component.HealthBarThreshold); - } - else - { - // avoid mispredicting damage on newly spawned entities. - args.State = new DamageableComponentState(component.Damage.DamageDict.ShallowClone(), component.DamageContainerID, component.DamageModifierSetId, component.HealthBarThreshold); - } - } - - private void OnIrradiated(EntityUid uid, DamageableComponent component, OnIrradiatedEvent args) - { - var damageValue = FixedPoint2.New(args.TotalRads); - - // Radiation should really just be a damage group instead of a list of types. - DamageSpecifier damage = new(); - foreach (var typeId in component.RadiationDamageTypeIDs) - { - damage.DamageDict.Add(typeId, damageValue); - } - - TryChangeDamage(uid, damage, interruptsDoAfters: false, origin: args.Origin); - } - - private void OnRejuvenate(EntityUid uid, DamageableComponent component, RejuvenateEvent args) - { - TryComp(uid, out var thresholds); - _mobThreshold.SetAllowRevives(uid, true, thresholds); // do this so that the state changes when we set the damage - SetAllDamage(uid, component, 0); - _mobThreshold.SetAllowRevives(uid, false, thresholds); - } - - private void DamageableHandleState(EntityUid uid, DamageableComponent component, ref ComponentHandleState args) - { - if (args.Current is not DamageableComponentState state) - { - return; - } - - component.DamageContainerID = state.DamageContainerId; - component.DamageModifierSetId = state.ModifierSetId; - component.HealthBarThreshold = state.HealthBarThreshold; - - // Has the damage actually changed? - DamageSpecifier newDamage = new() { DamageDict = new(state.DamageDict) }; - var delta = newDamage - component.Damage; - delta.TrimZeros(); - - if (!delta.Empty) - { - component.Damage = newDamage; - DamageChanged(uid, component, delta); - } - } - } + public float UniversalAllDamageModifier { get; private set; } = 1f; + public float UniversalAllHealModifier { get; private set; } = 1f; + public float UniversalMeleeDamageModifier { get; private set; } = 1f; + public float UniversalProjectileDamageModifier { get; private set; } = 1f; + public float UniversalHitscanDamageModifier { get; private set; } = 1f; + public float UniversalReagentDamageModifier { get; private set; } = 1f; + public float UniversalReagentHealModifier { get; private set; } = 1f; + public float UniversalExplosionDamageModifier { get; private set; } = 1f; + public float UniversalThrownDamageModifier { get; private set; } = 1f; + public float UniversalTopicalsHealModifier { get; private set; } = 1f; + public float UniversalMobDamageModifier { get; private set; } = 1f; /// - /// Raised before damage is done, so stuff can cancel it if necessary. + /// If the damage in a DamageableComponent was changed this function should be called. /// - [ByRefEvent] - public record struct BeforeDamageChangedEvent(DamageSpecifier Damage, EntityUid? Origin = null, bool Cancelled = false); - - /// - /// Raised on an entity when damage is about to be dealt, - /// in case anything else needs to modify it other than the base - /// damageable component. - /// - /// For example, armor. - /// - public sealed class DamageModifyEvent : EntityEventArgs, IInventoryRelayEvent + /// + /// This updates cached damage information, flags the component as dirty, and raises a damage changed event. + /// The damage changed event is used by other systems, such as damage thresholds. + /// + private void OnEntityDamageChanged( + Entity ent, + DamageSpecifier? damageDelta = null, + bool interruptsDoAfters = true, + EntityUid? origin = null + ) { - // Whenever locational damage is a thing, this should just check only that bit of armour. - public SlotFlags TargetSlots { get; } = ~SlotFlags.POCKET; + ent.Comp.Damage.GetDamagePerGroup(_prototypeManager, ent.Comp.DamagePerGroup); + ent.Comp.TotalDamage = ent.Comp.Damage.GetTotal(); + Dirty(ent); - public readonly DamageSpecifier OriginalDamage; - public DamageSpecifier Damage; - public EntityUid? Origin; - - public DamageModifyEvent(DamageSpecifier damage, EntityUid? origin = null) + if (damageDelta != null && _appearanceQuery.TryGetComponent(ent, out var appearance)) { - OriginalDamage = damage; - Damage = damage; - Origin = origin; + _appearance.SetData( + ent, + DamageVisualizerKeys.DamageUpdateGroups, + new DamageVisualizerGroupData(ent.Comp.DamagePerGroup.Keys.ToList()), + appearance + ); } + + // TODO DAMAGE + // byref struct event. + RaiseLocalEvent(ent, new DamageChangedEvent(ent.Comp, damageDelta, interruptsDoAfters, origin)); } - public sealed class DamageChangedEvent : EntityEventArgs + private void DamageableGetState(Entity ent, ref ComponentGetState args) { - /// - /// This is the component whose damage was changed. - /// - /// - /// Given that nearly every component that cares about a change in the damage, needs to know the - /// current damage values, directly passing this information prevents a lot of duplicate - /// Owner.TryGetComponent() calls. - /// - public readonly DamageableComponent Damageable; - - /// - /// The amount by which the damage has changed. If the damage was set directly to some number, this will be - /// null. - /// - public readonly DamageSpecifier? DamageDelta; - - /// - /// Was any of the damage change dealing damage, or was it all healing? - /// - public readonly bool DamageIncreased; - - /// - /// Does this event interrupt DoAfters? - /// Note: As provided in the constructor, this *does not* account for DamageIncreased. - /// As written into the event, this *does* account for DamageIncreased. - /// - public readonly bool InterruptsDoAfters; - - /// - /// Contains the entity which caused the change in damage, if any was responsible. - /// - public readonly EntityUid? Origin; - - public DamageChangedEvent(DamageableComponent damageable, DamageSpecifier? damageDelta, bool interruptsDoAfters, EntityUid? origin) + if (_netMan.IsServer) { - Damageable = damageable; - DamageDelta = damageDelta; - Origin = origin; + args.State = new DamageableComponentState( + ent.Comp.Damage.DamageDict, + ent.Comp.DamageContainerID, + ent.Comp.DamageModifierSetId, + ent.Comp.HealthBarThreshold + ); + // TODO BODY SYSTEM pass damage onto body system + // BOBBY WHEN? 😭 + // BOBBY SOON 🫡 - if (DamageDelta == null) - return; - - foreach (var damageChange in DamageDelta.DamageDict.Values) - { - if (damageChange > 0) - { - DamageIncreased = true; - break; - } - } - InterruptsDoAfters = interruptsDoAfters && DamageIncreased; + return; } + + // avoid mispredicting damage on newly spawned entities. + args.State = new DamageableComponentState( + ent.Comp.Damage.DamageDict.ShallowClone(), + ent.Comp.DamageContainerID, + ent.Comp.DamageModifierSetId, + ent.Comp.HealthBarThreshold + ); } } diff --git a/Content.Shared/Damage/Systems/PassiveDamageSystem.cs b/Content.Shared/Damage/Systems/PassiveDamageSystem.cs index e750863e24..fddf7dc975 100644 --- a/Content.Shared/Damage/Systems/PassiveDamageSystem.cs +++ b/Content.Shared/Damage/Systems/PassiveDamageSystem.cs @@ -1,10 +1,8 @@ using Content.Shared.Damage.Components; -using Content.Shared.Mobs.Systems; using Content.Shared.Mobs.Components; -using Content.Shared.FixedPoint; using Robust.Shared.Timing; -namespace Content.Shared.Damage; +namespace Content.Shared.Damage.Systems; public sealed class PassiveDamageSystem : EntitySystem { @@ -47,7 +45,7 @@ public sealed class PassiveDamageSystem : EntitySystem foreach (var allowedState in comp.AllowedStates) { if(allowedState == mobState.CurrentState) - _damageable.TryChangeDamage(uid, comp.Damage, true, false, damage); + _damageable.ChangeDamage((uid, damage), comp.Damage, true, false); } } } diff --git a/Content.Shared/Damage/Systems/RequireProjectileTargetSystem.cs b/Content.Shared/Damage/Systems/RequireProjectileTargetSystem.cs index 66b1de65e8..63b690a67c 100644 --- a/Content.Shared/Damage/Systems/RequireProjectileTargetSystem.cs +++ b/Content.Shared/Damage/Systems/RequireProjectileTargetSystem.cs @@ -1,10 +1,11 @@ +using Content.Shared.Damage.Components; using Content.Shared.Projectiles; -using Content.Shared.Weapons.Ranged.Components; using Content.Shared.Standing; -using Robust.Shared.Physics.Events; +using Content.Shared.Weapons.Ranged.Components; using Robust.Shared.Containers; +using Robust.Shared.Physics.Events; -namespace Content.Shared.Damage.Components; +namespace Content.Shared.Damage.Systems; public sealed class RequireProjectileTargetSystem : EntitySystem { diff --git a/Content.Shared/Damage/Systems/SharedGodmodeSystem.cs b/Content.Shared/Damage/Systems/SharedGodmodeSystem.cs index 4bf762c479..2a020732c2 100644 --- a/Content.Shared/Damage/Systems/SharedGodmodeSystem.cs +++ b/Content.Shared/Damage/Systems/SharedGodmodeSystem.cs @@ -85,9 +85,9 @@ public abstract class SharedGodmodeSystem : EntitySystem if (!Resolve(uid, ref godmode, false)) return; - if (TryComp(uid, out var damageable) && godmode.OldDamage != null) + if (godmode.OldDamage != null) { - _damageable.SetDamage(uid, damageable, godmode.OldDamage); + _damageable.SetDamage(uid, godmode.OldDamage); } RemComp(uid); diff --git a/Content.Shared/Damage/Systems/SlowOnDamageSystem.cs b/Content.Shared/Damage/Systems/SlowOnDamageSystem.cs index e339727200..fef7b6ae06 100644 --- a/Content.Shared/Damage/Systems/SlowOnDamageSystem.cs +++ b/Content.Shared/Damage/Systems/SlowOnDamageSystem.cs @@ -5,109 +5,108 @@ using Content.Shared.FixedPoint; using Content.Shared.Inventory; using Content.Shared.Movement.Systems; -namespace Content.Shared.Damage +namespace Content.Shared.Damage.Systems; + +public sealed class SlowOnDamageSystem : EntitySystem { - public sealed class SlowOnDamageSystem : EntitySystem + [Dependency] private readonly MovementSpeedModifierSystem _movementSpeedModifierSystem = default!; + + public override void Initialize() { - [Dependency] private readonly MovementSpeedModifierSystem _movementSpeedModifierSystem = default!; + base.Initialize(); - public override void Initialize() + SubscribeLocalEvent(OnDamageChanged); + SubscribeLocalEvent(OnRefreshMovespeed); + + SubscribeLocalEvent>(OnModifySpeed); + SubscribeLocalEvent(OnExamined); + SubscribeLocalEvent(OnGotEquipped); + SubscribeLocalEvent(OnGotUnequipped); + + SubscribeLocalEvent(OnIgnoreStartup); + SubscribeLocalEvent(OnIgnoreShutdown); + SubscribeLocalEvent(OnIgnoreModifySpeed); + } + + private void OnRefreshMovespeed(EntityUid uid, SlowOnDamageComponent component, RefreshMovementSpeedModifiersEvent args) + { + if (!TryComp(uid, out var damage)) + return; + + if (damage.TotalDamage == FixedPoint2.Zero) + return; + + // Get closest threshold + FixedPoint2 closest = FixedPoint2.Zero; + var total = damage.TotalDamage; + foreach (var thres in component.SpeedModifierThresholds) { - base.Initialize(); - - SubscribeLocalEvent(OnDamageChanged); - SubscribeLocalEvent(OnRefreshMovespeed); - - SubscribeLocalEvent>(OnModifySpeed); - SubscribeLocalEvent(OnExamined); - SubscribeLocalEvent(OnGotEquipped); - SubscribeLocalEvent(OnGotUnequipped); - - SubscribeLocalEvent(OnIgnoreStartup); - SubscribeLocalEvent(OnIgnoreShutdown); - SubscribeLocalEvent(OnIgnoreModifySpeed); + if (total >= thres.Key && thres.Key > closest) + closest = thres.Key; } - private void OnRefreshMovespeed(EntityUid uid, SlowOnDamageComponent component, RefreshMovementSpeedModifiersEvent args) + if (closest != FixedPoint2.Zero) { - if (!TryComp(uid, out var damage)) - return; + var speed = component.SpeedModifierThresholds[closest]; - if (damage.TotalDamage == FixedPoint2.Zero) - return; - - // Get closest threshold - FixedPoint2 closest = FixedPoint2.Zero; - var total = damage.TotalDamage; - foreach (var thres in component.SpeedModifierThresholds) - { - if (total >= thres.Key && thres.Key > closest) - closest = thres.Key; - } - - if (closest != FixedPoint2.Zero) - { - var speed = component.SpeedModifierThresholds[closest]; - - var ev = new ModifySlowOnDamageSpeedEvent(speed); - RaiseLocalEvent(uid, ref ev); - args.ModifySpeed(ev.Speed, ev.Speed); - } - } - - private void OnDamageChanged(EntityUid uid, SlowOnDamageComponent component, DamageChangedEvent args) - { - // We -could- only refresh if it crossed a threshold but that would kind of be a lot of duplicated - // code and this isn't a super hot path anyway since basically only humans have this - - _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(uid); - } - - private void OnModifySpeed(Entity ent, ref InventoryRelayedEvent args) - { - var dif = 1 - args.Args.Speed; - if (dif <= 0) - return; - - // reduces the slowness modifier by the given coefficient - args.Args.Speed += dif * ent.Comp.Modifier; - } - - private void OnExamined(Entity ent, ref ExaminedEvent args) - { - var msg = Loc.GetString("slow-on-damage-modifier-examine", ("mod", (1 - ent.Comp.Modifier) * 100)); - args.PushMarkup(msg); - } - - private void OnGotEquipped(Entity ent, ref ClothingGotEquippedEvent args) - { - _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(args.Wearer); - } - - private void OnGotUnequipped(Entity ent, ref ClothingGotUnequippedEvent args) - { - _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(args.Wearer); - } - - private void OnIgnoreStartup(Entity ent, ref ComponentStartup args) - { - _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(ent); - } - - private void OnIgnoreShutdown(Entity ent, ref ComponentShutdown args) - { - _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(ent); - } - - private void OnIgnoreModifySpeed(Entity ent, ref ModifySlowOnDamageSpeedEvent args) - { - args.Speed = 1f; + var ev = new ModifySlowOnDamageSpeedEvent(speed); + RaiseLocalEvent(uid, ref ev); + args.ModifySpeed(ev.Speed, ev.Speed); } } - [ByRefEvent] - public record struct ModifySlowOnDamageSpeedEvent(float Speed) : IInventoryRelayEvent + private void OnDamageChanged(EntityUid uid, SlowOnDamageComponent component, DamageChangedEvent args) { - public SlotFlags TargetSlots => SlotFlags.WITHOUT_POCKET; + // We -could- only refresh if it crossed a threshold but that would kind of be a lot of duplicated + // code and this isn't a super hot path anyway since basically only humans have this + + _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(uid); + } + + private void OnModifySpeed(Entity ent, ref InventoryRelayedEvent args) + { + var dif = 1 - args.Args.Speed; + if (dif <= 0) + return; + + // reduces the slowness modifier by the given coefficient + args.Args.Speed += dif * ent.Comp.Modifier; + } + + private void OnExamined(Entity ent, ref ExaminedEvent args) + { + var msg = Loc.GetString("slow-on-damage-modifier-examine", ("mod", (1 - ent.Comp.Modifier) * 100)); + args.PushMarkup(msg); + } + + private void OnGotEquipped(Entity ent, ref ClothingGotEquippedEvent args) + { + _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(args.Wearer); + } + + private void OnGotUnequipped(Entity ent, ref ClothingGotUnequippedEvent args) + { + _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(args.Wearer); + } + + private void OnIgnoreStartup(Entity ent, ref ComponentStartup args) + { + _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(ent); + } + + private void OnIgnoreShutdown(Entity ent, ref ComponentShutdown args) + { + _movementSpeedModifierSystem.RefreshMovementSpeedModifiers(ent); + } + + private void OnIgnoreModifySpeed(Entity ent, ref ModifySlowOnDamageSpeedEvent args) + { + args.Speed = 1f; } } + +[ByRefEvent] +public record struct ModifySlowOnDamageSpeedEvent(float Speed) : IInventoryRelayEvent +{ + public SlotFlags TargetSlots => SlotFlags.WITHOUT_POCKET; +} diff --git a/Content.Shared/Destructible/Triggers/AndTrigger.cs b/Content.Shared/Destructible/Triggers/AndTrigger.cs index ebedeee479..938f125b01 100644 --- a/Content.Shared/Destructible/Triggers/AndTrigger.cs +++ b/Content.Shared/Destructible/Triggers/AndTrigger.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Robust.Shared.Serialization; namespace Content.Shared.Destructible.Thresholds.Triggers; diff --git a/Content.Shared/Destructible/Triggers/DamageGroupTrigger.cs b/Content.Shared/Destructible/Triggers/DamageGroupTrigger.cs index 902198e33d..c1add2e891 100644 --- a/Content.Shared/Destructible/Triggers/DamageGroupTrigger.cs +++ b/Content.Shared/Destructible/Triggers/DamageGroupTrigger.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.FixedPoint; using Content.Shared.Damage.Prototypes; using Robust.Shared.Prototypes; diff --git a/Content.Shared/Destructible/Triggers/DamageTrigger.cs b/Content.Shared/Destructible/Triggers/DamageTrigger.cs index 9ec2060e5f..7a2d612f75 100644 --- a/Content.Shared/Destructible/Triggers/DamageTrigger.cs +++ b/Content.Shared/Destructible/Triggers/DamageTrigger.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.FixedPoint; using Robust.Shared.Serialization; diff --git a/Content.Shared/Destructible/Triggers/DamageTypeTrigger.cs b/Content.Shared/Destructible/Triggers/DamageTypeTrigger.cs index 8f50b62791..60bd9baf67 100644 --- a/Content.Shared/Destructible/Triggers/DamageTypeTrigger.cs +++ b/Content.Shared/Destructible/Triggers/DamageTypeTrigger.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; using Content.Shared.FixedPoint; using Robust.Shared.Prototypes; diff --git a/Content.Shared/Destructible/Triggers/IThresholdTrigger.cs b/Content.Shared/Destructible/Triggers/IThresholdTrigger.cs index 98c96a5bd5..d97394c406 100644 --- a/Content.Shared/Destructible/Triggers/IThresholdTrigger.cs +++ b/Content.Shared/Destructible/Triggers/IThresholdTrigger.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; namespace Content.Shared.Destructible.Thresholds.Triggers; diff --git a/Content.Shared/Destructible/Triggers/OrTrigger.cs b/Content.Shared/Destructible/Triggers/OrTrigger.cs index 3e379cac7f..cdf72bed7f 100644 --- a/Content.Shared/Destructible/Triggers/OrTrigger.cs +++ b/Content.Shared/Destructible/Triggers/OrTrigger.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Robust.Shared.Serialization; namespace Content.Shared.Destructible.Thresholds.Triggers; diff --git a/Content.Shared/DoAfter/SharedDoAfterSystem.cs b/Content.Shared/DoAfter/SharedDoAfterSystem.cs index c1a3d6ecee..d80f65755e 100644 --- a/Content.Shared/DoAfter/SharedDoAfterSystem.cs +++ b/Content.Shared/DoAfter/SharedDoAfterSystem.cs @@ -2,6 +2,7 @@ using System.Diagnostics.CodeAnalysis; using System.Threading.Tasks; using Content.Shared.ActionBlocker; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Hands.Components; using Content.Shared.Tag; using Robust.Shared.GameStates; diff --git a/Content.Shared/Doors/Systems/SharedDoorSystem.cs b/Content.Shared/Doors/Systems/SharedDoorSystem.cs index 50132e42dd..c031dcc7bd 100644 --- a/Content.Shared/Doors/Systems/SharedDoorSystem.cs +++ b/Content.Shared/Doors/Systems/SharedDoorSystem.cs @@ -2,7 +2,7 @@ using System.Linq; using Content.Shared.Access.Components; using Content.Shared.Access.Systems; using Content.Shared.Administration.Logs; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Doors.Components; using Content.Shared.Emag.Systems; diff --git a/Content.Shared/EntityConditions/Conditions/DamageGroupEntityConditionSystem.cs b/Content.Shared/EntityConditions/Conditions/DamageGroupEntityConditionSystem.cs index dd877140d6..3691039189 100644 --- a/Content.Shared/EntityConditions/Conditions/DamageGroupEntityConditionSystem.cs +++ b/Content.Shared/EntityConditions/Conditions/DamageGroupEntityConditionSystem.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; using Content.Shared.FixedPoint; using Robust.Shared.Prototypes; diff --git a/Content.Shared/EntityConditions/Conditions/DamageTypeEntityConditionSystem.cs b/Content.Shared/EntityConditions/Conditions/DamageTypeEntityConditionSystem.cs index 30490c72e8..f2611a8200 100644 --- a/Content.Shared/EntityConditions/Conditions/DamageTypeEntityConditionSystem.cs +++ b/Content.Shared/EntityConditions/Conditions/DamageTypeEntityConditionSystem.cs @@ -1,4 +1,5 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; using Content.Shared.FixedPoint; using Robust.Shared.Prototypes; diff --git a/Content.Shared/EntityConditions/Conditions/TotalDamageEntityConditionSystem.cs b/Content.Shared/EntityConditions/Conditions/TotalDamageEntityConditionSystem.cs index 16f4a946f3..306398b4eb 100644 --- a/Content.Shared/EntityConditions/Conditions/TotalDamageEntityConditionSystem.cs +++ b/Content.Shared/EntityConditions/Conditions/TotalDamageEntityConditionSystem.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.FixedPoint; using Robust.Shared.Prototypes; diff --git a/Content.Shared/EntityEffects/Effects/EvenHealthChangeEntityEffectSystem.cs b/Content.Shared/EntityEffects/Effects/EvenHealthChangeEntityEffectSystem.cs index 33b2041b37..b26b801264 100644 --- a/Content.Shared/EntityEffects/Effects/EvenHealthChangeEntityEffectSystem.cs +++ b/Content.Shared/EntityEffects/Effects/EvenHealthChangeEntityEffectSystem.cs @@ -1,5 +1,7 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.Localizations; using Robust.Shared.Prototypes; @@ -43,11 +45,10 @@ public sealed partial class EvenHealthChangeEntityEffectSystem : EntityEffectSys damageSpec *= args.Scale; _damageable.TryChangeDamage( - entity, + entity.AsNullable(), damageSpec, args.Effect.IgnoreResistances, - interruptsDoAfters: false, - damageable: entity.Comp); + interruptsDoAfters: false); } } diff --git a/Content.Shared/EntityEffects/Effects/HealthChangeEntityEffectSystem.cs b/Content.Shared/EntityEffects/Effects/HealthChangeEntityEffectSystem.cs index 89948cd2e4..595bf15aa5 100644 --- a/Content.Shared/EntityEffects/Effects/HealthChangeEntityEffectSystem.cs +++ b/Content.Shared/EntityEffects/Effects/HealthChangeEntityEffectSystem.cs @@ -1,4 +1,5 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Prototypes; using Content.Shared.FixedPoint; using Content.Shared.Localizations; @@ -13,7 +14,7 @@ namespace Content.Shared.EntityEffects.Effects; /// public sealed partial class HealthChangeEntityEffectSystem : EntityEffectSystem { - [Dependency] private readonly DamageableSystem _damageable = default!; + [Dependency] private readonly Damage.Systems.DamageableSystem _damageable = default!; protected override void Effect(Entity entity, ref EntityEffectEvent args) { @@ -22,7 +23,7 @@ public sealed partial class HealthChangeEntityEffectSystem : EntityEffectSystem< damageSpec *= args.Scale; _damageable.TryChangeDamage( - entity, + entity.AsNullable(), damageSpec, args.Effect.IgnoreResistances, interruptsDoAfters: false); @@ -49,10 +50,10 @@ public sealed partial class HealthChange : EntityEffectBase var damageSpec = new DamageSpecifier(Damage); - var universalReagentDamageModifier = entSys.GetEntitySystem().UniversalReagentDamageModifier; - var universalReagentHealModifier = entSys.GetEntitySystem().UniversalReagentHealModifier; + var universalReagentDamageModifier = entSys.GetEntitySystem().UniversalReagentDamageModifier; + var universalReagentHealModifier = entSys.GetEntitySystem().UniversalReagentHealModifier; - damageSpec = entSys.GetEntitySystem().ApplyUniversalAllModifiers(damageSpec); + damageSpec = entSys.GetEntitySystem().ApplyUniversalAllModifiers(damageSpec); foreach (var (kind, amount) in damageSpec.DamageDict) { diff --git a/Content.Shared/Execution/SharedExecutionSystem.cs b/Content.Shared/Execution/SharedExecutionSystem.cs index b6d52cf352..926e6e08c2 100644 --- a/Content.Shared/Execution/SharedExecutionSystem.cs +++ b/Content.Shared/Execution/SharedExecutionSystem.cs @@ -1,7 +1,7 @@ using Content.Shared.ActionBlocker; using Content.Shared.Chat; using Content.Shared.CombatMode; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Database; using Content.Shared.DoAfter; using Content.Shared.IdentityManagement; @@ -12,7 +12,6 @@ using Content.Shared.Verbs; using Content.Shared.Weapons.Melee; using Content.Shared.Weapons.Melee.Events; using Content.Shared.Interaction.Events; -using Content.Shared.Mind; using Robust.Shared.Player; using Robust.Shared.Audio.Systems; diff --git a/Content.Shared/Fax/Systems/FaxecuteSystem.cs b/Content.Shared/Fax/Systems/FaxecuteSystem.cs index 7768c7a3d2..3018b70c05 100644 --- a/Content.Shared/Fax/Systems/FaxecuteSystem.cs +++ b/Content.Shared/Fax/Systems/FaxecuteSystem.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Popups; using Content.Shared.Fax.Components; @@ -26,7 +26,7 @@ public sealed class FaxecuteSystem : EntitySystem return; var damageSpec = faxecute.Damage; - _damageable.TryChangeDamage(sendEntity, damageSpec); + _damageable.ChangeDamage(sendEntity.Value, damageSpec); _popupSystem.PopupEntity(Loc.GetString("fax-machine-popup-error", ("target", uid)), uid, PopupType.LargeCaution); return; diff --git a/Content.Shared/Flash/DamagedByFlashingSystem.cs b/Content.Shared/Flash/DamagedByFlashingSystem.cs index 103dfb663c..9dbd01b89e 100644 --- a/Content.Shared/Flash/DamagedByFlashingSystem.cs +++ b/Content.Shared/Flash/DamagedByFlashingSystem.cs @@ -1,5 +1,5 @@ using Content.Shared.Flash.Components; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; namespace Content.Shared.Flash; @@ -18,7 +18,7 @@ public sealed class DamagedByFlashingSystem : EntitySystem // Best wait for Ed's status effect system rewrite. private void OnFlashAttempt(Entity ent, ref FlashAttemptEvent args) { - _damageable.TryChangeDamage(ent, ent.Comp.FlashDamage); + _damageable.ChangeDamage(ent.Owner, ent.Comp.FlashDamage); // TODO: It would be more logical if different flashes had different power, // and the damage would be inflicted depending on the strength of the flash. diff --git a/Content.Shared/HealthExaminable/HealthExaminableSystem.cs b/Content.Shared/HealthExaminable/HealthExaminableSystem.cs index 0645c51a47..ae938e0995 100644 --- a/Content.Shared/HealthExaminable/HealthExaminableSystem.cs +++ b/Content.Shared/HealthExaminable/HealthExaminableSystem.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Examine; using Content.Shared.FixedPoint; using Content.Shared.IdentityManagement; diff --git a/Content.Shared/Implants/SharedImplanterSystem.cs b/Content.Shared/Implants/SharedImplanterSystem.cs index 6ff6d42d3b..6431b3d42e 100644 --- a/Content.Shared/Implants/SharedImplanterSystem.cs +++ b/Content.Shared/Implants/SharedImplanterSystem.cs @@ -1,7 +1,7 @@ using System.Diagnostics.CodeAnalysis; using System.Linq; using Content.Shared.Containers.ItemSlots; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.DoAfter; using Content.Shared.Examine; using Content.Shared.Forensics; diff --git a/Content.Shared/Inventory/InventorySystem.Relay.cs b/Content.Shared/Inventory/InventorySystem.Relay.cs index 392234297c..11b7f61130 100644 --- a/Content.Shared/Inventory/InventorySystem.Relay.cs +++ b/Content.Shared/Inventory/InventorySystem.Relay.cs @@ -7,6 +7,7 @@ using Content.Shared.Climbing.Events; using Content.Shared.Contraband; using Content.Shared.Damage; using Content.Shared.Damage.Events; +using Content.Shared.Damage.Systems; using Content.Shared.Electrocution; using Content.Shared.Explosion; using Content.Shared.Eye.Blinding.Systems; diff --git a/Content.Shared/Kitchen/SharedKitchenSpikeSystem.cs b/Content.Shared/Kitchen/SharedKitchenSpikeSystem.cs index 530dcb437b..7e7dbd744e 100644 --- a/Content.Shared/Kitchen/SharedKitchenSpikeSystem.cs +++ b/Content.Shared/Kitchen/SharedKitchenSpikeSystem.cs @@ -1,6 +1,6 @@ using Content.Shared.Administration.Logs; using Content.Shared.Body.Systems; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.Destructible; using Content.Shared.DoAfter; @@ -330,7 +330,7 @@ public sealed class SharedKitchenSpikeSystem : EntitySystem { EnsureComp(args.Target.Value); - _damageableSystem.TryChangeDamage(args.Target, ent.Comp.ButcherDamage, true); + _damageableSystem.ChangeDamage(args.Target.Value, ent.Comp.ButcherDamage, true); // Log severity for damaging other entities is normally medium. _logger.Add(LogType.Action, @@ -428,7 +428,7 @@ public sealed class SharedKitchenSpikeSystem : EntitySystem kitchenSpike.NextDamage += kitchenSpike.DamageInterval; Dirty(uid, kitchenSpike); - _damageableSystem.TryChangeDamage(contained, kitchenSpike.TimeDamage, true); + _damageableSystem.ChangeDamage(contained.Value, kitchenSpike.TimeDamage, true); } } diff --git a/Content.Shared/Medical/Healing/HealingSystem.cs b/Content.Shared/Medical/Healing/HealingSystem.cs index 2ac2c50871..bd9f0003ba 100644 --- a/Content.Shared/Medical/Healing/HealingSystem.cs +++ b/Content.Shared/Medical/Healing/HealingSystem.cs @@ -2,7 +2,8 @@ using Content.Shared.Administration.Logs; using Content.Shared.Body.Components; using Content.Shared.Body.Systems; using Content.Shared.Chemistry.EntitySystems; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.DoAfter; using Content.Shared.FixedPoint; @@ -76,12 +77,10 @@ public sealed class HealingSystem : EntitySystem if (healing.ModifyBloodLevel != 0 && bloodstream != null) _bloodstreamSystem.TryModifyBloodLevel((target.Owner, bloodstream), healing.ModifyBloodLevel); - var healed = _damageable.TryChangeDamage(target.Owner, healing.Damage * _damageable.UniversalTopicalsHealModifier, true, origin: args.Args.User); - - if (healed == null && healing.BloodlossModifier != 0) + if (!_damageable.TryChangeDamage(target.Owner, healing.Damage * _damageable.UniversalTopicalsHealModifier, out var healed, true, origin: args.Args.User) && healing.BloodlossModifier != 0) return; - var total = healed?.GetTotal() ?? FixedPoint2.Zero; + var total = healed.GetTotal(); // Re-verify that we can heal the damage. var dontRepeat = false; diff --git a/Content.Shared/Medical/Stethoscope/StethoscopeSystem.cs b/Content.Shared/Medical/Stethoscope/StethoscopeSystem.cs index 01d61aa06e..86a8249321 100644 --- a/Content.Shared/Medical/Stethoscope/StethoscopeSystem.cs +++ b/Content.Shared/Medical/Stethoscope/StethoscopeSystem.cs @@ -1,5 +1,5 @@ using Content.Shared.Actions; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.DoAfter; using Content.Shared.FixedPoint; using Content.Shared.Inventory; diff --git a/Content.Shared/Medical/SuitSensors/SharedSuitSensorSystem.cs b/Content.Shared/Medical/SuitSensors/SharedSuitSensorSystem.cs index 6930b029b7..861fcd8daf 100644 --- a/Content.Shared/Medical/SuitSensors/SharedSuitSensorSystem.cs +++ b/Content.Shared/Medical/SuitSensors/SharedSuitSensorSystem.cs @@ -2,7 +2,7 @@ using System.Numerics; using Content.Shared.Access.Systems; using Content.Shared.ActionBlocker; using Content.Shared.Clothing; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.DeviceNetwork; using Content.Shared.DoAfter; using Content.Shared.Emp; diff --git a/Content.Shared/Mobs/Components/MobStateComponent.cs b/Content.Shared/Mobs/Components/MobStateComponent.cs index 7cff0779cb..80a0674c96 100644 --- a/Content.Shared/Mobs/Components/MobStateComponent.cs +++ b/Content.Shared/Mobs/Components/MobStateComponent.cs @@ -1,7 +1,6 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Mobs.Systems; using Robust.Shared.GameStates; -using Robust.Shared.Serialization; namespace Content.Shared.Mobs.Components { diff --git a/Content.Shared/Mobs/Systems/MobStateSystem.Subscribers.cs b/Content.Shared/Mobs/Systems/MobStateSystem.Subscribers.cs index 7b5ee52b27..ded30499ee 100644 --- a/Content.Shared/Mobs/Systems/MobStateSystem.Subscribers.cs +++ b/Content.Shared/Mobs/Systems/MobStateSystem.Subscribers.cs @@ -3,6 +3,7 @@ using Content.Shared.Buckle.Components; using Content.Shared.CombatMode.Pacification; using Content.Shared.Damage; using Content.Shared.Damage.ForceSay; +using Content.Shared.Damage.Systems; using Content.Shared.Emoting; using Content.Shared.Hands; using Content.Shared.Interaction; diff --git a/Content.Shared/Mobs/Systems/MobStateSystem.cs b/Content.Shared/Mobs/Systems/MobStateSystem.cs index d3cfda32bb..0497f3cce0 100644 --- a/Content.Shared/Mobs/Systems/MobStateSystem.cs +++ b/Content.Shared/Mobs/Systems/MobStateSystem.cs @@ -1,9 +1,8 @@ using Content.Shared.ActionBlocker; using Content.Shared.Administration.Logs; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Mobs.Components; using Content.Shared.Standing; -using Robust.Shared.Physics.Systems; using Robust.Shared.Timing; namespace Content.Shared.Mobs.Systems; diff --git a/Content.Shared/Mobs/Systems/MobThresholdSystem.cs b/Content.Shared/Mobs/Systems/MobThresholdSystem.cs index a059c18dd8..3af7317954 100644 --- a/Content.Shared/Mobs/Systems/MobThresholdSystem.cs +++ b/Content.Shared/Mobs/Systems/MobThresholdSystem.cs @@ -2,6 +2,8 @@ using System.Diagnostics.CodeAnalysis; using System.Linq; using Content.Shared.Alert; using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.FixedPoint; using Content.Shared.Mobs.Components; using Content.Shared.Mobs.Events; diff --git a/Content.Shared/Nutrition/EntitySystems/HungerSystem.cs b/Content.Shared/Nutrition/EntitySystems/HungerSystem.cs index 559a6a1019..226f2c4c40 100644 --- a/Content.Shared/Nutrition/EntitySystems/HungerSystem.cs +++ b/Content.Shared/Nutrition/EntitySystems/HungerSystem.cs @@ -1,16 +1,14 @@ using System.Diagnostics.CodeAnalysis; using Content.Shared.Alert; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Mobs.Systems; using Content.Shared.Movement.Systems; using Content.Shared.Nutrition.Components; using Content.Shared.Rejuvenate; using Content.Shared.StatusIcon; -using Robust.Shared.Network; using Robust.Shared.Prototypes; using Robust.Shared.Random; using Robust.Shared.Timing; -using Robust.Shared.Utility; namespace Content.Shared.Nutrition.EntitySystems; diff --git a/Content.Shared/Polymorph/Systems/SharedChameleonProjectorSystem.cs b/Content.Shared/Polymorph/Systems/SharedChameleonProjectorSystem.cs index 69b9bf8f8d..3fd9ed07bd 100644 --- a/Content.Shared/Polymorph/Systems/SharedChameleonProjectorSystem.cs +++ b/Content.Shared/Polymorph/Systems/SharedChameleonProjectorSystem.cs @@ -1,6 +1,5 @@ using Content.Shared.Actions; using Content.Shared.Coordinates; -using Content.Shared.Damage; using Content.Shared.Hands; using Content.Shared.Interaction; using Content.Shared.Item; @@ -14,6 +13,7 @@ using Robust.Shared.Network; using Robust.Shared.Prototypes; using Robust.Shared.Serialization.Manager; using System.Diagnostics.CodeAnalysis; +using Content.Shared.Damage.Systems; namespace Content.Shared.Polymorph.Systems; diff --git a/Content.Shared/Repairable/RepairableSystem.cs b/Content.Shared/Repairable/RepairableSystem.cs index 7a0f01b9b6..7526faeb51 100644 --- a/Content.Shared/Repairable/RepairableSystem.cs +++ b/Content.Shared/Repairable/RepairableSystem.cs @@ -1,5 +1,6 @@ using Content.Shared.Administration.Logs; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.DoAfter; using Content.Shared.Interaction; @@ -32,14 +33,14 @@ public sealed partial class RepairableSystem : EntitySystem if (ent.Comp.Damage != null) { - var damageChanged = _damageableSystem.TryChangeDamage(ent.Owner, ent.Comp.Damage, true, false, origin: args.User); - _adminLogger.Add(LogType.Healed, $"{ToPrettyString(args.User):user} repaired {ToPrettyString(ent.Owner):target} by {damageChanged?.GetTotal()}"); + var damageChanged = _damageableSystem.ChangeDamage(ent.Owner, ent.Comp.Damage, true, false, origin: args.User); + _adminLogger.Add(LogType.Healed, $"{ToPrettyString(args.User):user} repaired {ToPrettyString(ent.Owner):target} by {damageChanged.GetTotal()}"); } else { // Repair all damage - _damageableSystem.SetAllDamage(ent.Owner, damageable, 0); + _damageableSystem.SetAllDamage((ent.Owner, damageable), 0); _adminLogger.Add(LogType.Healed, $"{ToPrettyString(args.User):user} repaired {ToPrettyString(ent.Owner):target} back to full health"); } diff --git a/Content.Shared/Silicons/Borgs/SharedBorgSystem.Relay.cs b/Content.Shared/Silicons/Borgs/SharedBorgSystem.Relay.cs index 87df866c98..7a1ca31eb5 100644 --- a/Content.Shared/Silicons/Borgs/SharedBorgSystem.Relay.cs +++ b/Content.Shared/Silicons/Borgs/SharedBorgSystem.Relay.cs @@ -1,4 +1,5 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Silicons.Borgs.Components; namespace Content.Shared.Silicons.Borgs; diff --git a/Content.Shared/Silicons/Bots/MedibotSystem.cs b/Content.Shared/Silicons/Bots/MedibotSystem.cs index 407e586eb1..68ee5ff405 100644 --- a/Content.Shared/Silicons/Bots/MedibotSystem.cs +++ b/Content.Shared/Silicons/Bots/MedibotSystem.cs @@ -1,5 +1,8 @@ +using Robust.Shared.Audio.Systems; +using Robust.Shared.Serialization; +using System.Diagnostics.CodeAnalysis; using Content.Shared.Chemistry.EntitySystems; -using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.DoAfter; using Content.Shared.Emag.Components; using Content.Shared.Emag.Systems; @@ -8,9 +11,6 @@ using Content.Shared.Mobs; using Content.Shared.Mobs.Components; using Content.Shared.NPC.Components; using Content.Shared.Popups; -using Robust.Shared.Audio.Systems; -using Robust.Shared.Serialization; -using System.Diagnostics.CodeAnalysis; namespace Content.Shared.Silicons.Bots; diff --git a/Content.Shared/Storage/EntitySystems/SecretStashSystem.cs b/Content.Shared/Storage/EntitySystems/SecretStashSystem.cs index 7e83b50fba..273359e4d3 100644 --- a/Content.Shared/Storage/EntitySystems/SecretStashSystem.cs +++ b/Content.Shared/Storage/EntitySystems/SecretStashSystem.cs @@ -1,5 +1,5 @@ using Content.Shared.Construction.EntitySystems; -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Destructible; using Content.Shared.Hands.Components; using Content.Shared.Hands.EntitySystems; diff --git a/Content.Shared/Stunnable/SharedStunSystem.Knockdown.cs b/Content.Shared/Stunnable/SharedStunSystem.Knockdown.cs index ae8f970623..fc2b01c649 100644 --- a/Content.Shared/Stunnable/SharedStunSystem.Knockdown.cs +++ b/Content.Shared/Stunnable/SharedStunSystem.Knockdown.cs @@ -3,6 +3,7 @@ using Content.Shared.Buckle.Components; using Content.Shared.CCVar; using Content.Shared.Damage; using Content.Shared.Damage.Components; +using Content.Shared.Damage.Systems; using Content.Shared.Database; using Content.Shared.DoAfter; using Content.Shared.Gravity; diff --git a/Content.Shared/Trigger/Systems/DamageOnTriggerSystem.cs b/Content.Shared/Trigger/Systems/DamageOnTriggerSystem.cs index cdcb1044f7..d021eed80d 100644 --- a/Content.Shared/Trigger/Systems/DamageOnTriggerSystem.cs +++ b/Content.Shared/Trigger/Systems/DamageOnTriggerSystem.cs @@ -5,7 +5,7 @@ namespace Content.Shared.Trigger.Systems; public sealed class DamageOnTriggerSystem : XOnTriggerSystem { - [Dependency] private readonly DamageableSystem _damageableSystem = default!; + [Dependency] private readonly Damage.Systems.DamageableSystem _damageableSystem = default!; protected override void OnTrigger(Entity ent, EntityUid target, ref TriggerEvent args) { @@ -13,7 +13,7 @@ public sealed class DamageOnTriggerSystem : XOnTriggerSystem(ent, out var damageable)) { var damageSetID = enabled ? ent.Comp.DeployedDamageModifierSetId : ent.Comp.RetractedDamageModifierSetId; - _damageable.SetDamageModifierSetId(ent, damageSetID, damageable); + _damageable.SetDamageModifierSetId((ent, damageable), damageSetID); } // Change the turret's fixtures diff --git a/Content.Shared/Weapons/Hitscan/Systems/HitscanBasicDamageSystem.cs b/Content.Shared/Weapons/Hitscan/Systems/HitscanBasicDamageSystem.cs index 130687469a..e5298a2937 100644 --- a/Content.Shared/Weapons/Hitscan/Systems/HitscanBasicDamageSystem.cs +++ b/Content.Shared/Weapons/Hitscan/Systems/HitscanBasicDamageSystem.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Weapons.Hitscan.Components; using Content.Shared.Weapons.Hitscan.Events; @@ -22,9 +22,7 @@ public sealed class HitscanBasicDamageSystem : EntitySystem var dmg = ent.Comp.Damage * _damage.UniversalHitscanDamageModifier; - var damageDealt = _damage.TryChangeDamage(args.Data.HitEntity, dmg, origin: args.Data.Gun); - - if (damageDealt == null) + if(!_damage.TryChangeDamage(args.Data.HitEntity.Value, dmg, out var damageDealt, origin: args.Data.Gun)) return; var damageEvent = new HitscanDamageDealtEvent diff --git a/Content.Shared/Weapons/Marker/SharedDamageMarkerSystem.cs b/Content.Shared/Weapons/Marker/SharedDamageMarkerSystem.cs index eab638a9fc..b236824815 100644 --- a/Content.Shared/Weapons/Marker/SharedDamageMarkerSystem.cs +++ b/Content.Shared/Weapons/Marker/SharedDamageMarkerSystem.cs @@ -1,8 +1,8 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Projectiles; using Content.Shared.Weapons.Melee.Events; using Content.Shared.Whitelist; -using Robust.Shared.Audio; using Robust.Shared.Audio.Systems; using Robust.Shared.Network; using Robust.Shared.Physics.Events; diff --git a/Content.Shared/Weapons/Melee/SharedMeleeWeaponSystem.cs b/Content.Shared/Weapons/Melee/SharedMeleeWeaponSystem.cs index 9bc0b845ae..a010dbec17 100644 --- a/Content.Shared/Weapons/Melee/SharedMeleeWeaponSystem.cs +++ b/Content.Shared/Weapons/Melee/SharedMeleeWeaponSystem.cs @@ -7,6 +7,7 @@ using Content.Shared.Administration.Components; using Content.Shared.Administration.Logs; using Content.Shared.CombatMode; using Content.Shared.Damage; +using Content.Shared.Damage.Components; using Content.Shared.Damage.Events; using Content.Shared.Damage.Systems; using Content.Shared.Database; @@ -541,9 +542,8 @@ public abstract class SharedMeleeWeaponSystem : EntitySystem RaiseLocalEvent(target.Value, attackedEvent); var modifiedDamage = DamageSpecifier.ApplyModifierSets(damage + hitEvent.BonusDamage + attackedEvent.BonusDamage, hitEvent.ModifiersList); - var damageResult = Damageable.TryChangeDamage(target, modifiedDamage, origin:user, ignoreResistances:resistanceBypass); - if (damageResult is {Empty: false}) + if (!Damageable.TryChangeDamage(target.Value, modifiedDamage, out var damageResult, origin:user, ignoreResistances:resistanceBypass)) { // If the target has stamina and is taking blunt damage, they should also take stamina damage based on their blunt to stamina factor if (damageResult.DamageDict.TryGetValue("Blunt", out var bluntDamage)) @@ -568,7 +568,7 @@ public abstract class SharedMeleeWeaponSystem : EntitySystem _meleeSound.PlayHitSound(target.Value, user, GetHighestDamageSound(modifiedDamage, _protoManager), hitEvent.HitSoundOverride, component); - if (damageResult?.GetTotal() > FixedPoint2.Zero) + if (damageResult.GetTotal() > FixedPoint2.Zero) { DoDamageEffect(targets, user, targetXform); } @@ -697,9 +697,9 @@ public abstract class SharedMeleeWeaponSystem : EntitySystem RaiseLocalEvent(entity, attackedEvent); var modifiedDamage = DamageSpecifier.ApplyModifierSets(damage + hitEvent.BonusDamage + attackedEvent.BonusDamage, hitEvent.ModifiersList); - var damageResult = Damageable.TryChangeDamage(entity, modifiedDamage, origin: user, ignoreResistances: resistanceBypass); + var damageResult = Damageable.ChangeDamage(entity, modifiedDamage, origin: user, ignoreResistances: resistanceBypass); - if (damageResult != null && damageResult.GetTotal() > FixedPoint2.Zero) + if (damageResult.GetTotal() > FixedPoint2.Zero) { // If the target has stamina and is taking blunt damage, they should also take stamina damage based on their blunt to stamina factor if (damageResult.DamageDict.TryGetValue("Blunt", out var bluntDamage)) diff --git a/Content.Shared/Weapons/Ranged/Systems/SharedGunSystem.cs b/Content.Shared/Weapons/Ranged/Systems/SharedGunSystem.cs index 1b7bf4bae8..ed8849a41a 100644 --- a/Content.Shared/Weapons/Ranged/Systems/SharedGunSystem.cs +++ b/Content.Shared/Weapons/Ranged/Systems/SharedGunSystem.cs @@ -7,6 +7,7 @@ using Content.Shared.Audio; using Content.Shared.CombatMode; using Content.Shared.Containers.ItemSlots; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Examine; using Content.Shared.Hands; using Content.Shared.Hands.EntitySystems; diff --git a/Content.Shared/Xenoarchaeology/Artifact/SharedXenoArtifactSystem.XAT.cs b/Content.Shared/Xenoarchaeology/Artifact/SharedXenoArtifactSystem.XAT.cs index 1ef85db27f..4d9e2e6df4 100644 --- a/Content.Shared/Xenoarchaeology/Artifact/SharedXenoArtifactSystem.XAT.cs +++ b/Content.Shared/Xenoarchaeology/Artifact/SharedXenoArtifactSystem.XAT.cs @@ -1,6 +1,7 @@ using System.Linq; using Content.Shared.Chemistry; using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Examine; using Content.Shared.Interaction; using Content.Shared.Movement.Pulling.Events; diff --git a/Content.Shared/Xenoarchaeology/Artifact/XAE/XAEDamageInAreaSystem.cs b/Content.Shared/Xenoarchaeology/Artifact/XAE/XAEDamageInAreaSystem.cs index 405fa338ff..a0d9d09368 100644 --- a/Content.Shared/Xenoarchaeology/Artifact/XAE/XAEDamageInAreaSystem.cs +++ b/Content.Shared/Xenoarchaeology/Artifact/XAE/XAEDamageInAreaSystem.cs @@ -1,4 +1,5 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Whitelist; using Content.Shared.Xenoarchaeology.Artifact.XAE.Components; using Robust.Shared.Random; diff --git a/Content.Shared/Xenoarchaeology/Artifact/XAT/XATDamageThresholdReachedSystem.cs b/Content.Shared/Xenoarchaeology/Artifact/XAT/XATDamageThresholdReachedSystem.cs index eab832ce6d..e392b91823 100644 --- a/Content.Shared/Xenoarchaeology/Artifact/XAT/XATDamageThresholdReachedSystem.cs +++ b/Content.Shared/Xenoarchaeology/Artifact/XAT/XATDamageThresholdReachedSystem.cs @@ -1,4 +1,5 @@ using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Xenoarchaeology.Artifact.Components; using Content.Shared.Xenoarchaeology.Artifact.XAT.Components; using Robust.Shared.Prototypes; diff --git a/Content.Shared/Xenoarchaeology/Equipment/SharedArtifactCrusherSystem.cs b/Content.Shared/Xenoarchaeology/Equipment/SharedArtifactCrusherSystem.cs index a8c4b9ff06..2807fd9250 100644 --- a/Content.Shared/Xenoarchaeology/Equipment/SharedArtifactCrusherSystem.cs +++ b/Content.Shared/Xenoarchaeology/Equipment/SharedArtifactCrusherSystem.cs @@ -1,4 +1,4 @@ -using Content.Shared.Damage; +using Content.Shared.Damage.Systems; using Content.Shared.Emag.Systems; using Content.Shared.Examine; using Content.Shared.Popups;