Fix brains, borgs etc not counting as marooned (#37148)

* init

* comments

* comment

* no more debug
This commit is contained in:
ScarKy0
2025-05-06 19:24:26 +02:00
committed by GitHub
parent ac24be2fb7
commit 9b5ddb87f5
4 changed files with 62 additions and 3 deletions

View File

@@ -39,7 +39,7 @@ public sealed class KillPersonConditionSystem : EntitySystem
return 1f; return 1f;
var targetDead = _mind.IsCharacterDeadIc(mind); var targetDead = _mind.IsCharacterDeadIc(mind);
var targetOnShuttle = _emergencyShuttle.IsTargetEscaping(mind.OwnedEntity.Value); var targetMarooned = !_emergencyShuttle.IsTargetEscaping(mind.OwnedEntity.Value) || _mind.IsCharacterUnrevivableIc(mind);
if (!_config.GetCVar(CCVars.EmergencyShuttleEnabled) && requireMaroon) if (!_config.GetCVar(CCVars.EmergencyShuttleEnabled) && requireMaroon)
{ {
requireDead = true; requireDead = true;
@@ -55,11 +55,11 @@ public sealed class KillPersonConditionSystem : EntitySystem
// If the shuttle hasn't left, give 50% progress if the target isn't on the shuttle as a "almost there!" // If the shuttle hasn't left, give 50% progress if the target isn't on the shuttle as a "almost there!"
if (requireMaroon && !_emergencyShuttle.ShuttlesLeft) if (requireMaroon && !_emergencyShuttle.ShuttlesLeft)
return targetOnShuttle ? 0f : 0.5f; return targetMarooned ? 0.5f : 0f;
// If the shuttle has already left, and the target isn't on it, 100% // If the shuttle has already left, and the target isn't on it, 100%
if (requireMaroon && _emergencyShuttle.ShuttlesLeft) if (requireMaroon && _emergencyShuttle.ShuttlesLeft)
return targetOnShuttle ? 0f : 1f; return targetMarooned ? 1f : 0f;
return 1f; // Good job you did it woohoo return 1f; // Good job you did it woohoo
} }

View File

@@ -72,6 +72,7 @@ public sealed partial class BorgSystem : SharedBorgSystem
SubscribeLocalEvent<BorgChassisComponent, PowerCellChangedEvent>(OnPowerCellChanged); SubscribeLocalEvent<BorgChassisComponent, PowerCellChangedEvent>(OnPowerCellChanged);
SubscribeLocalEvent<BorgChassisComponent, PowerCellSlotEmptyEvent>(OnPowerCellSlotEmpty); SubscribeLocalEvent<BorgChassisComponent, PowerCellSlotEmptyEvent>(OnPowerCellSlotEmpty);
SubscribeLocalEvent<BorgChassisComponent, GetCharactedDeadIcEvent>(OnGetDeadIC); SubscribeLocalEvent<BorgChassisComponent, GetCharactedDeadIcEvent>(OnGetDeadIC);
SubscribeLocalEvent<BorgChassisComponent, GetCharacterUnrevivableIcEvent>(OnGetUnrevivableIC);
SubscribeLocalEvent<BorgChassisComponent, ItemToggledEvent>(OnToggled); SubscribeLocalEvent<BorgChassisComponent, ItemToggledEvent>(OnToggled);
SubscribeLocalEvent<BorgBrainComponent, MindAddedMessage>(OnBrainMindAdded); SubscribeLocalEvent<BorgBrainComponent, MindAddedMessage>(OnBrainMindAdded);
@@ -218,6 +219,11 @@ public sealed partial class BorgSystem : SharedBorgSystem
args.Dead = true; args.Dead = true;
} }
private void OnGetUnrevivableIC(EntityUid uid, BorgChassisComponent component, ref GetCharacterUnrevivableIcEvent args)
{
args.Unrevivable = true;
}
private void OnToggled(Entity<BorgChassisComponent> ent, ref ItemToggledEvent args) private void OnToggled(Entity<BorgChassisComponent> ent, ref ItemToggledEvent args)
{ {
var (uid, comp) = ent; var (uid, comp) = ent;

View File

@@ -66,6 +66,7 @@ namespace Content.Server.Zombies
SubscribeLocalEvent<ZombieComponent, CloningEvent>(OnZombieCloning); SubscribeLocalEvent<ZombieComponent, CloningEvent>(OnZombieCloning);
SubscribeLocalEvent<ZombieComponent, TryingToSleepEvent>(OnSleepAttempt); SubscribeLocalEvent<ZombieComponent, TryingToSleepEvent>(OnSleepAttempt);
SubscribeLocalEvent<ZombieComponent, GetCharactedDeadIcEvent>(OnGetCharacterDeadIC); SubscribeLocalEvent<ZombieComponent, GetCharactedDeadIcEvent>(OnGetCharacterDeadIC);
SubscribeLocalEvent<ZombieComponent, GetCharacterUnrevivableIcEvent>(OnGetCharacterUnrevivableIC);
SubscribeLocalEvent<ZombieComponent, MindAddedMessage>(OnMindAdded); SubscribeLocalEvent<ZombieComponent, MindAddedMessage>(OnMindAdded);
SubscribeLocalEvent<ZombieComponent, MindRemovedMessage>(OnMindRemoved); SubscribeLocalEvent<ZombieComponent, MindRemovedMessage>(OnMindRemoved);
@@ -168,6 +169,11 @@ namespace Content.Server.Zombies
args.Dead = true; args.Dead = true;
} }
private void OnGetCharacterUnrevivableIC(EntityUid uid, ZombieComponent component, ref GetCharacterUnrevivableIcEvent args)
{
args.Unrevivable = true;
}
private void OnStartup(EntityUid uid, ZombieComponent component, ComponentStartup args) private void OnStartup(EntityUid uid, ZombieComponent component, ComponentStartup args)
{ {
if (component.EmoteSoundsId == null) if (component.EmoteSoundsId == null)

View File

@@ -253,6 +253,24 @@ public abstract partial class SharedMindSystem : EntitySystem
return _mobState.IsDead(mind.OwnedEntity.Value, targetMobState); return _mobState.IsDead(mind.OwnedEntity.Value, targetMobState);
} }
/// <summary>
/// True if the OwnedEntity of this mind is physically unrevivable.
/// This is mainly to check whether a mind is able to inherit their "original" character again without the need for creating a new one.
/// In cases of being a brain, being borged or a zombie they are "unrevivable"
/// </summary>
public bool IsCharacterUnrevivablePhysically(MindComponent mind)
{
if (mind.OwnedEntity == null)
return true;
// This entity cannot be dead, alive or crit, so it makes sense it cannot be revived to begin with.
if (!HasComp<MobStateComponent>(mind.OwnedEntity))
return true;
// Could use checks for the amount of damage they have, but with chemistry you can never tell what damage means someone is truly "unrevivable".
return false;
}
public virtual void Visit(EntityUid mindId, EntityUid entity, MindComponent? mind = null) public virtual void Visit(EntityUid mindId, EntityUid entity, MindComponent? mind = null)
{ {
} }
@@ -556,6 +574,27 @@ public abstract partial class SharedMindSystem : EntitySystem
return IsCharacterDeadPhysically(mind); return IsCharacterDeadPhysically(mind);
} }
/// <summary>
/// True if this Mind is 'sufficiently unrevivable' IC (Objectives, EndText).
/// Note that this is *IC logic*, it's not necessarily tied to any specific truth.
/// "If administrators decide that zombies are unrevivable, this returns true for zombies."
/// Alternative IsCharacterDeadIC that checks for whether they will be able to inherit their body again.
/// State in which they must be given a new body to "live" (borging, being a brain, etc) should count as "unrevivable".
/// </summary>
public bool IsCharacterUnrevivableIc(MindComponent mind)
{
if (mind.OwnedEntity is { } owned)
{
var ev = new GetCharacterUnrevivableIcEvent(null);
RaiseLocalEvent(owned, ref ev);
if (ev.Unrevivable != null)
return ev.Unrevivable.Value;
}
return IsCharacterUnrevivablePhysically(mind);
}
/// <summary> /// <summary>
/// A string to represent the mind for logging /// A string to represent the mind for logging
/// </summary> /// </summary>
@@ -602,3 +641,11 @@ public abstract partial class SharedMindSystem : EntitySystem
/// <param name="Dead"></param> /// <param name="Dead"></param>
[ByRefEvent] [ByRefEvent]
public record struct GetCharactedDeadIcEvent(bool? Dead); public record struct GetCharactedDeadIcEvent(bool? Dead);
/// <summary>
/// Raised on an entity to determine whether or not they are "unrevivable" in IC-logic.
/// Used to check for things such as being borged or a zombie.
/// </summary>
/// <param name="Unrevivable"></param>
[ByRefEvent]
public record struct GetCharacterUnrevivableIcEvent(bool? Unrevivable);