From f2d43172588289917215c3044a4d9a74c2f3ad5b Mon Sep 17 00:00:00 2001 From: Leon Friedrich <60421075+ElectroJr@users.noreply.github.com> Date: Mon, 29 Sep 2025 05:23:40 +1300 Subject: [PATCH] Clean up some parts of ExplosionSystem (#40485) * Clean up some parts of ExplosionSystem * Update Content.Shared/Damage/DamageSpecifier.cs Co-authored-by: slarticodefast <161409025+slarticodefast@users.noreply.github.com> * Review --------- Co-authored-by: slarticodefast <161409025+slarticodefast@users.noreply.github.com> --- .../Atmos/EntitySystems/AirtightSystem.cs | 2 +- .../EntitySystems/ExplosionSystem.Airtight.cs | 54 ++++++++++++------- .../EntitySystems/ExplosionSystem.GridMap.cs | 4 +- .../ExplosionSystem.Processing.cs | 18 ++++--- .../EntitySystems/ExplosionSystem.TileFill.cs | 4 +- .../EntitySystems/ExplosionSystem.cs | 24 ++++++--- .../Damage/Components/DamageableComponent.cs | 2 +- Content.Shared/Damage/DamageSpecifier.cs | 5 ++ .../Damage/Systems/DamageableSystem.cs | 43 ++++++++++----- .../EntitySystems/SharedExplosionSystem.cs | 7 +++ 10 files changed, 109 insertions(+), 54 deletions(-) diff --git a/Content.Server/Atmos/EntitySystems/AirtightSystem.cs b/Content.Server/Atmos/EntitySystems/AirtightSystem.cs index 4a108b38a4..431707c835 100644 --- a/Content.Server/Atmos/EntitySystems/AirtightSystem.cs +++ b/Content.Server/Atmos/EntitySystems/AirtightSystem.cs @@ -123,7 +123,7 @@ namespace Content.Server.Atmos.EntitySystems public void InvalidatePosition(Entity grid, Vector2i pos) { var query = GetEntityQuery(); - _explosionSystem.UpdateAirtightMap(grid, pos, grid, query); + _explosionSystem.UpdateAirtightMap(grid, pos, grid); _atmosphereSystem.InvalidateTile(grid.Owner, pos); } diff --git a/Content.Server/Explosion/EntitySystems/ExplosionSystem.Airtight.cs b/Content.Server/Explosion/EntitySystems/ExplosionSystem.Airtight.cs index af004e112e..3d55a7e823 100644 --- a/Content.Server/Explosion/EntitySystems/ExplosionSystem.Airtight.cs +++ b/Content.Server/Explosion/EntitySystems/ExplosionSystem.Airtight.cs @@ -11,8 +11,6 @@ namespace Content.Server.Explosion.EntitySystems; public sealed partial class ExplosionSystem { - [Dependency] private readonly DestructibleSystem _destructibleSystem = default!; - private readonly Dictionary _explosionTypes = new(); private void InitAirtightMap() @@ -26,6 +24,8 @@ public sealed partial class ExplosionSystem int index = 0; foreach (var prototype in _prototypeManager.EnumeratePrototypes()) { + // TODO EXPLOSION + // just make this a field on the prototype _explosionTypes.Add(prototype.ID, index); index++; } @@ -42,10 +42,10 @@ public sealed partial class ExplosionSystem // indices to this tile-data struct. private Dictionary> _airtightMap = new(); - public void UpdateAirtightMap(EntityUid gridId, Vector2i tile, MapGridComponent? grid = null, EntityQuery? query = null) + public void UpdateAirtightMap(EntityUid gridId, Vector2i tile, MapGridComponent? grid = null) { if (Resolve(gridId, ref grid, false)) - UpdateAirtightMap(gridId, grid, tile, query); + UpdateAirtightMap(gridId, grid, tile); } /// @@ -58,7 +58,7 @@ public sealed partial class ExplosionSystem /// something like a normal and a reinforced windoor on the same tile. But given that this is a pretty rare /// occurrence, I am fine with this. /// - public void UpdateAirtightMap(EntityUid gridId, MapGridComponent grid, Vector2i tile, EntityQuery? query = null) + public void UpdateAirtightMap(EntityUid gridId, MapGridComponent grid, Vector2i tile) { var tolerance = new float[_explosionTypes.Count]; var blockedDirections = AtmosDirection.Invalid; @@ -66,18 +66,15 @@ public sealed partial class ExplosionSystem if (!_airtightMap.ContainsKey(gridId)) _airtightMap[gridId] = new(); - query ??= GetEntityQuery(); - var damageQuery = GetEntityQuery(); - var destructibleQuery = GetEntityQuery(); - var anchoredEnumerator = _mapSystem.GetAnchoredEntitiesEnumerator(gridId, grid, tile); + var anchoredEnumerator = _map.GetAnchoredEntitiesEnumerator(gridId, grid, tile); while (anchoredEnumerator.MoveNext(out var uid)) { - if (!query.Value.TryGetComponent(uid, out var airtight) || !airtight.AirBlocked) + if (!_airtightQuery.TryGetComponent(uid, out var airtight) || !airtight.AirBlocked) continue; blockedDirections |= airtight.AirBlockedDirection; - var entityTolerances = GetExplosionTolerance(uid.Value, damageQuery, destructibleQuery); + var entityTolerances = GetExplosionTolerance(uid.Value); for (var i = 0; i < tolerance.Length; i++) { tolerance[i] = Math.Max(tolerance[i], entityTolerances[i]); @@ -105,28 +102,25 @@ public sealed partial class ExplosionSystem if (!TryComp(transform.GridUid, out var grid)) return; - UpdateAirtightMap(transform.GridUid.Value, grid, _mapSystem.CoordinatesToTile(transform.GridUid.Value, grid, transform.Coordinates)); + UpdateAirtightMap(transform.GridUid.Value, grid, _map.CoordinatesToTile(transform.GridUid.Value, grid, transform.Coordinates)); } /// /// Return a dictionary that specifies how intense a given explosion type needs to be in order to destroy an entity. /// - public float[] GetExplosionTolerance( - EntityUid uid, - EntityQuery damageQuery, - EntityQuery destructibleQuery) + public float[] GetExplosionTolerance(EntityUid uid) { // How much total damage is needed to destroy this entity? This also includes "break" behaviors. This ASSUMES // that this will result in a non-airtight entity.Entities that ONLY break via construction graph node changes // are currently effectively "invincible" as far as this is concerned. This really should be done more rigorously. var totalDamageTarget = FixedPoint2.MaxValue; - if (destructibleQuery.TryGetComponent(uid, out var destructible)) + if (_destructibleQuery.TryGetComponent(uid, out var destructible)) { totalDamageTarget = _destructibleSystem.DestroyedAt(uid, destructible); } var explosionTolerance = new float[_explosionTypes.Count]; - if (totalDamageTarget == FixedPoint2.MaxValue || !damageQuery.TryGetComponent(uid, out var damageable)) + if (totalDamageTarget == FixedPoint2.MaxValue || !_damageableQuery.TryGetComponent(uid, out var damageable)) { for (var i = 0; i < explosionTolerance.Length; i++) { @@ -139,9 +133,12 @@ public sealed partial class ExplosionSystem // does not support entities dynamically changing explosive resistances (e.g. via clothing). But these probably // shouldn't be airtight structures anyways.... + var mod = _damageableSystem.UniversalAllDamageModifier * _damageableSystem.UniversalExplosionDamageModifier; foreach (var (id, index) in _explosionTypes) { - if (!_prototypeManager.TryIndex(id, out var explosionType)) + // TODO EXPLOSION SYSTEM + // cache explosion type damage. + if (!_prototypeManager.Resolve(id, out ExplosionPrototype? explosionType)) continue; // evaluate the damage that this damage type would do to this entity @@ -151,10 +148,15 @@ public sealed partial class ExplosionSystem if (!damageable.Damage.DamageDict.ContainsKey(type)) continue; + // TODO EXPLOSION SYSTEM + // add a variant of the event that gets raised once, instead of once per prototype. + // Or better yet, just calculate this manually w/o the event. + // The event mainly exists for indirect resistances via things like inventory & clothing + // But this shouldn't matter for airtight entities. var ev = new GetExplosionResistanceEvent(explosionType.ID); RaiseLocalEvent(uid, ref ev); - damagePerIntensity += value * Math.Max(0, ev.DamageCoefficient); + damagePerIntensity += value * mod * Math.Max(0, ev.DamageCoefficient); } explosionTolerance[index] = damagePerIntensity > 0 @@ -179,4 +181,16 @@ public sealed partial class ExplosionSystem public float[] ExplosionTolerance; public AtmosDirection BlockedDirections = AtmosDirection.Invalid; } + + public override void ReloadMap() + { + foreach (var(grid, dict) in _airtightMap) + { + var comp = Comp(grid); + foreach (var index in dict.Keys) + { + UpdateAirtightMap(grid, comp, index); + } + } + } } diff --git a/Content.Server/Explosion/EntitySystems/ExplosionSystem.GridMap.cs b/Content.Server/Explosion/EntitySystems/ExplosionSystem.GridMap.cs index 8515e1af42..5c032d5c82 100644 --- a/Content.Server/Explosion/EntitySystems/ExplosionSystem.GridMap.cs +++ b/Content.Server/Explosion/EntitySystems/ExplosionSystem.GridMap.cs @@ -258,7 +258,7 @@ public sealed partial class ExplosionSystem { var neighbourIndex = change.GridIndices + NeighbourVectors[i]; - if (_mapSystem.TryGetTileRef(ev.Entity, grid, neighbourIndex, out var neighbourTile) && !neighbourTile.Tile.IsEmpty) + if (_map.TryGetTileRef(ev.Entity, grid, neighbourIndex, out var neighbourTile) && !neighbourTile.Tile.IsEmpty) { var oppositeDirection = (NeighborFlag)(1 << ((i + 4) % 8)); edges[neighbourIndex] = edges.GetValueOrDefault(neighbourIndex) | oppositeDirection; @@ -307,7 +307,7 @@ public sealed partial class ExplosionSystem spaceDirections = NeighborFlag.Invalid; for (var i = 0; i < NeighbourVectors.Length; i++) { - if (!_mapSystem.TryGetTileRef(grid, grid.Comp, index + NeighbourVectors[i], out var neighborTile) || neighborTile.Tile.IsEmpty) + if (!_map.TryGetTileRef(grid, grid.Comp, index + NeighbourVectors[i], out var neighborTile) || neighborTile.Tile.IsEmpty) spaceDirections |= (NeighborFlag) (1 << i); } diff --git a/Content.Server/Explosion/EntitySystems/ExplosionSystem.Processing.cs b/Content.Server/Explosion/EntitySystems/ExplosionSystem.Processing.cs index b61f78e909..263fdabf98 100644 --- a/Content.Server/Explosion/EntitySystems/ExplosionSystem.Processing.cs +++ b/Content.Server/Explosion/EntitySystems/ExplosionSystem.Processing.cs @@ -27,8 +27,6 @@ namespace Content.Server.Explosion.EntitySystems; public sealed partial class ExplosionSystem { - [Dependency] private readonly FlammableSystem _flammableSystem = default!; - /// /// Used to limit explosion processing time. See . /// @@ -446,7 +444,7 @@ public sealed partial class ExplosionSystem GetEntitiesToDamage(uid, originalDamage, id); foreach (var (entity, damage) in _toDamage) { - if (damage.GetTotal() > 0 && TryComp(entity, out var actorComponent)) + if (_actorQuery.HasComp(entity)) { // Log damage to player entities only, cause this will create a massive amount of log spam otherwise. if (cause != null) @@ -461,7 +459,7 @@ public sealed partial class ExplosionSystem } // TODO EXPLOSIONS turn explosions into entities, and pass the the entity in as the damage origin. - _damageableSystem.TryChangeDamage(entity, damage * _damageableSystem.UniversalExplosionDamageModifier, ignoreResistances: true); + _damageableSystem.TryChangeDamage(entity, damage, ignoreResistances: true, ignoreGlobalModifiers: true); } } @@ -668,6 +666,7 @@ sealed class Explosion private readonly IEntityManager _entMan; private readonly ExplosionSystem _system; private readonly SharedMapSystem _mapSystem; + private readonly DamageableSystem _damageable; public readonly EntityUid VisualEnt; @@ -688,10 +687,10 @@ sealed class Explosion int maxTileBreak, bool canCreateVacuum, IEntityManager entMan, - IMapManager mapMan, EntityUid visualEnt, EntityUid? cause, - SharedMapSystem mapSystem) + SharedMapSystem mapSystem, + DamageableSystem damageable) { VisualEnt = visualEnt; Cause = cause; @@ -706,6 +705,7 @@ sealed class Explosion _maxTileBreak = maxTileBreak; _canCreateVacuum = canCreateVacuum; _entMan = entMan; + _damageable = damageable; _xformQuery = entMan.GetEntityQuery(); _physicsQuery = entMan.GetEntityQuery(); @@ -760,8 +760,10 @@ sealed class Explosion _expectedDamage = ExplosionType.DamagePerIntensity * _currentIntensity; } #endif - - _currentDamage = ExplosionType.DamagePerIntensity * _currentIntensity; + var modifier = _currentIntensity + * _damageable.UniversalExplosionDamageModifier + * _damageable.UniversalAllDamageModifier; + _currentDamage = ExplosionType.DamagePerIntensity * modifier; // only throw if either the explosion is small, or if this is the outer ring of a large explosion. var doThrow = Area < _system.ThrowLimit || CurrentIteration > _tileSetIntensity.Count - 6; diff --git a/Content.Server/Explosion/EntitySystems/ExplosionSystem.TileFill.cs b/Content.Server/Explosion/EntitySystems/ExplosionSystem.TileFill.cs index cee694886b..ac539da213 100644 --- a/Content.Server/Explosion/EntitySystems/ExplosionSystem.TileFill.cs +++ b/Content.Server/Explosion/EntitySystems/ExplosionSystem.TileFill.cs @@ -52,7 +52,7 @@ public sealed partial class ExplosionSystem // get the epicenter tile indices if (_mapManager.TryFindGridAt(epicenter, out var gridUid, out var candidateGrid) && - _mapSystem.TryGetTileRef(gridUid, candidateGrid, _mapSystem.WorldToTile(gridUid, candidateGrid, epicenter.Position), out var tileRef) && + _map.TryGetTileRef(gridUid, candidateGrid, _map.WorldToTile(gridUid, candidateGrid, epicenter.Position), out var tileRef) && !tileRef.Tile.IsEmpty) { epicentreGrid = gridUid; @@ -62,7 +62,7 @@ public sealed partial class ExplosionSystem { // reference grid defines coordinate system that the explosion in space will use var gridComp = Comp(referenceGrid.Value); - initialTile = _mapSystem.WorldToTile(referenceGrid.Value, gridComp, epicenter.Position); + initialTile = _map.WorldToTile(referenceGrid.Value, gridComp, epicenter.Position); } else { diff --git a/Content.Server/Explosion/EntitySystems/ExplosionSystem.cs b/Content.Server/Explosion/EntitySystems/ExplosionSystem.cs index b459f5c70f..67dbe97b29 100644 --- a/Content.Server/Explosion/EntitySystems/ExplosionSystem.cs +++ b/Content.Server/Explosion/EntitySystems/ExplosionSystem.cs @@ -2,6 +2,8 @@ using System.Linq; using System.Numerics; using Content.Server.Administration.Logs; using Content.Server.Atmos.Components; +using Content.Server.Atmos.EntitySystems; +using Content.Server.Destructible; using Content.Server.NodeContainer.EntitySystems; using Content.Server.NPC.Pathfinding; using Content.Shared.Atmos.Components; @@ -16,7 +18,6 @@ using Content.Shared.GameTicking; using Content.Shared.Inventory; using Content.Shared.Projectiles; using Content.Shared.Throwing; -using Robust.Server.GameObjects; using Robust.Server.GameStates; using Robust.Server.Player; using Robust.Shared.Audio.Systems; @@ -38,23 +39,28 @@ public sealed partial class ExplosionSystem : SharedExplosionSystem [Dependency] private readonly IPrototypeManager _prototypeManager = default!; [Dependency] private readonly IConfigurationManager _cfg = default!; [Dependency] private readonly IPlayerManager _playerManager = default!; + [Dependency] private readonly IAdminLogManager _adminLogger = default!; - [Dependency] private readonly MapSystem _mapSystem = default!; [Dependency] private readonly SharedAppearanceSystem _appearance = default!; [Dependency] private readonly DamageableSystem _damageableSystem = default!; [Dependency] private readonly NodeGroupSystem _nodeGroupSystem = default!; [Dependency] private readonly PathfindingSystem _pathfindingSystem = default!; [Dependency] private readonly SharedCameraRecoilSystem _recoilSystem = default!; - [Dependency] private readonly IAdminLogManager _adminLogger = default!; [Dependency] private readonly ThrowingSystem _throwingSystem = default!; [Dependency] private readonly PvsOverrideSystem _pvsSys = default!; [Dependency] private readonly SharedAudioSystem _audio = default!; [Dependency] private readonly SharedTransformSystem _transformSystem = default!; [Dependency] private readonly SharedMapSystem _map = default!; + [Dependency] private readonly FlammableSystem _flammableSystem = default!; + [Dependency] private readonly DestructibleSystem _destructibleSystem = default!; private EntityQuery _flammableQuery; private EntityQuery _physicsQuery; private EntityQuery _projectileQuery; + private EntityQuery _actorQuery; + private EntityQuery _destructibleQuery; + private EntityQuery _damageableQuery; + private EntityQuery _airtightQuery; /// /// "Tile-size" for space when there are no nearby grids to use as a reference. @@ -93,6 +99,10 @@ public sealed partial class ExplosionSystem : SharedExplosionSystem _flammableQuery = GetEntityQuery(); _physicsQuery = GetEntityQuery(); _projectileQuery = GetEntityQuery(); + _actorQuery = GetEntityQuery(); + _destructibleQuery = GetEntityQuery(); + _damageableQuery = GetEntityQuery(); + _airtightQuery = GetEntityQuery(); } private void OnReset(RoundRestartCleanupEvent ev) @@ -317,7 +327,7 @@ public sealed partial class ExplosionSystem : SharedExplosionSystem private Explosion? SpawnExplosion(QueuedExplosion queued) { var pos = queued.Epicenter; - if (!_mapSystem.MapExists(pos.MapId)) + if (!_map.MapExists(pos.MapId)) return null; var results = GetExplosionTiles(pos, queued.Proto.ID, queued.TotalIntensity, queued.Slope, queued.MaxTileIntensity); @@ -333,7 +343,7 @@ public sealed partial class ExplosionSystem : SharedExplosionSystem CameraShake(iterationIntensity.Count * 4f, pos, queued.TotalIntensity); //For whatever bloody reason, sound system requires ENTITY coordinates. - var mapEntityCoords = _transformSystem.ToCoordinates(_mapSystem.GetMap(pos.MapId), pos); + var mapEntityCoords = _transformSystem.ToCoordinates(_map.GetMap(pos.MapId), pos); // play sound. // for the normal audio, we want everyone in pvs range @@ -376,10 +386,10 @@ public sealed partial class ExplosionSystem : SharedExplosionSystem queued.MaxTileBreak, queued.CanCreateVacuum, EntityManager, - _mapManager, visualEnt, queued.Cause, - _map); + _map, + _damageableSystem); } private void CameraShake(float range, MapCoordinates epicenter, float totalIntensity) diff --git a/Content.Shared/Damage/Components/DamageableComponent.cs b/Content.Shared/Damage/Components/DamageableComponent.cs index 9e4e26e422..1d290181ec 100644 --- a/Content.Shared/Damage/Components/DamageableComponent.cs +++ b/Content.Shared/Damage/Components/DamageableComponent.cs @@ -44,7 +44,7 @@ namespace Content.Shared.Damage /// /// If this data-field is specified, this allows damageable components to be initialized with non-zero damage. /// - [DataField(readOnly: true)] //todo remove this readonly when implementing writing to damagespecifier + [DataField(readOnly: true)] // TODO FULL GAME SAVE public DamageSpecifier Damage = new(); /// diff --git a/Content.Shared/Damage/DamageSpecifier.cs b/Content.Shared/Damage/DamageSpecifier.cs index 00bd416e1f..7bf921baa2 100644 --- a/Content.Shared/Damage/DamageSpecifier.cs +++ b/Content.Shared/Damage/DamageSpecifier.cs @@ -20,6 +20,11 @@ namespace Content.Shared.Damage [DataDefinition, Serializable, NetSerializable] public sealed partial class DamageSpecifier : IEquatable { + // For the record I regret so many of the decisions i made when rewriting damageable + // Why is it just shitting out dictionaries left and right + // One day Arrays, stackalloc spans, and SIMD will save the day. + // TODO DAMAGEABLE REFACTOR + // These exist solely so the wiki works. Please do not touch them or use them. [JsonPropertyName("types")] [DataField("types", customTypeSerializer: typeof(PrototypeIdDictionarySerializer))] diff --git a/Content.Shared/Damage/Systems/DamageableSystem.cs b/Content.Shared/Damage/Systems/DamageableSystem.cs index f3a4f37830..b849227156 100644 --- a/Content.Shared/Damage/Systems/DamageableSystem.cs +++ b/Content.Shared/Damage/Systems/DamageableSystem.cs @@ -2,9 +2,9 @@ using System.Linq; using Content.Shared.CCVar; using Content.Shared.Chemistry; using Content.Shared.Damage.Prototypes; +using Content.Shared.Explosion.EntitySystems; using Content.Shared.FixedPoint; using Content.Shared.Inventory; -using Content.Shared.Mind.Components; using Content.Shared.Mobs.Components; using Content.Shared.Mobs.Systems; using Content.Shared.Radiation.Events; @@ -25,10 +25,10 @@ namespace Content.Shared.Damage [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 _mindContainerQuery; public float UniversalAllDamageModifier { get; private set; } = 1f; public float UniversalAllHealModifier { get; private set; } = 1f; @@ -52,7 +52,6 @@ namespace Content.Shared.Damage _appearanceQuery = GetEntityQuery(); _damageableQuery = GetEntityQuery(); - _mindContainerQuery = GetEntityQuery(); // Damage modifier CVars are updated and stored here to be queried in other systems. // Note that certain modifiers requires reloading the guidebook. @@ -60,6 +59,7 @@ namespace Content.Shared.Damage { UniversalAllDamageModifier = value; _chemistryGuideData.ReloadAllReagentPrototypes(); + _explosion.ReloadMap(); }, true); Subs.CVar(_config, CCVars.PlaytestAllHealModifier, value => { @@ -80,7 +80,11 @@ namespace Content.Shared.Damage UniversalReagentHealModifier = value; _chemistryGuideData.ReloadAllReagentPrototypes(); }, true); - Subs.CVar(_config, CCVars.PlaytestExplosionDamageModifier, value => UniversalExplosionDamageModifier = value, 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); @@ -156,6 +160,9 @@ namespace Content.Shared.Damage 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)); } @@ -171,12 +178,24 @@ namespace Content.Shared.Damage /// Returns a with information about the actual damage changes. This will be /// null if the user had no applicable components that can take damage. /// - public DamageSpecifier? TryChangeDamage(EntityUid? uid, DamageSpecifier damage, bool ignoreResistances = false, - bool interruptsDoAfters = true, DamageableComponent? damageable = null, EntityUid? origin = null) + /// 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; } @@ -195,13 +214,13 @@ namespace Content.Shared.Damage if (!ignoreResistances) { if (damageable.DamageModifierSetId != null && - _prototypeManager.Resolve(damageable.DamageModifierSetId, out var modifierSet)) + _prototypeManager.Resolve(damageable.DamageModifierSetId, out var modifierSet)) { - // TODO DAMAGE PERFORMANCE - // use a local private field instead of creating a new dictionary here.. damage = DamageSpecifier.ApplyModifierSet(damage, modifierSet); } + // TODO DAMAGE + // byref struct event. var ev = new DamageModifyEvent(damage, origin); RaiseLocalEvent(uid.Value, ev); damage = ev.Damage; @@ -212,11 +231,9 @@ namespace Content.Shared.Damage } } - damage = ApplyUniversalAllModifiers(damage); + if (!ignoreGlobalModifiers) + damage = ApplyUniversalAllModifiers(damage); - // TODO DAMAGE PERFORMANCE - // Consider using a local private field instead of creating a new dictionary here. - // Would need to check that nothing ever tries to cache the delta. var delta = new DamageSpecifier(); delta.DamageDict.EnsureCapacity(damage.DamageDict.Count); diff --git a/Content.Shared/Explosion/EntitySystems/SharedExplosionSystem.cs b/Content.Shared/Explosion/EntitySystems/SharedExplosionSystem.cs index d6053c9c3c..ce05cd3eb8 100644 --- a/Content.Shared/Explosion/EntitySystems/SharedExplosionSystem.cs +++ b/Content.Shared/Explosion/EntitySystems/SharedExplosionSystem.cs @@ -69,4 +69,11 @@ public abstract class SharedExplosionSystem : EntitySystem bool addLog = true) { } + + /// + /// This forces the explosion system to re-calculate the explosion intensity required to destroy all airtight entities. + /// + public virtual void ReloadMap() + { + } } -- 2.51.2