diff --git a/Content.Server/GameTicking/Rules/TraitorRuleSystem.cs b/Content.Server/GameTicking/Rules/TraitorRuleSystem.cs index e5c78e4b07..c70d451b0f 100644 --- a/Content.Server/GameTicking/Rules/TraitorRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/TraitorRuleSystem.cs @@ -41,6 +41,8 @@ public class TraitorRuleSystem : GameRuleSystem private readonly List _traitors = new (); private const string TraitorPrototypeID = "Traitor"; + + public int TotalTraitors => _traitors.Count; public override void Initialize() { diff --git a/Content.Server/Objectives/Conditions/RandomTraitorAliveCondition.cs b/Content.Server/Objectives/Conditions/RandomTraitorAliveCondition.cs new file mode 100644 index 0000000000..5f4c982f21 --- /dev/null +++ b/Content.Server/Objectives/Conditions/RandomTraitorAliveCondition.cs @@ -0,0 +1,79 @@ +using System.Collections.Generic; +using Content.Server.Mind.Components; +using Content.Server.Objectives.Interfaces; +using JetBrains.Annotations; +using Robust.Shared.GameObjects; +using Robust.Shared.IoC; +using Robust.Shared.Random; +using Robust.Shared.Localization; +using Robust.Shared.Utility; +using Robust.Shared.Serialization.Manager.Attributes; +using Content.Server.Traitor; + +namespace Content.Server.Objectives.Conditions +{ + [DataDefinition] + public class RandomTraitorAliveCondition : IObjectiveCondition + { + protected Mind.Mind? Target; + + public IObjectiveCondition GetAssigned(Mind.Mind mind) + { + var entityMgr = IoCManager.Resolve(); + List _allOtherTraitors = new List(); + + foreach (var targetMind in entityMgr.EntityQuery()) + { + if (targetMind.Mind?.CharacterDeadIC == false && targetMind.Mind != mind && targetMind.Mind?.HasRole() == true) + { + _allOtherTraitors.Add(targetMind.Mind); + } + } + + return new RandomTraitorAliveCondition {Target = IoCManager.Resolve().Pick(_allOtherTraitors)}; + } + + public string Title + { + get + { + var targetName = string.Empty; + + if (Target == null) + return Loc.GetString("objective-condition-other-traitor-alive-title", ("targetName", targetName)); + + if (Target.CharacterName != null) + targetName = Target.CharacterName; + else if (Target.OwnedEntity is {Valid: true} owned) + targetName = IoCManager.Resolve().GetComponent(owned).EntityName; + + return Loc.GetString("objective-condition-other-traitor-alive-title", ("targetName", targetName)); + } + } + + public string Description => Loc.GetString("objective-condition-other-traitor-alive-description"); + + public SpriteSpecifier Icon => new SpriteSpecifier.Rsi(new ResourcePath("Objects/Misc/bureaucracy.rsi"), "folder_red"); + + public float Progress => (!Target?.CharacterDeadIC ?? true) ? 1f : 0f; + + public float Difficulty => 1.75f; + + public bool Equals(IObjectiveCondition? other) + { + return other is RandomTraitorAliveCondition kpc && Equals(Target, kpc.Target); + } + + public override bool Equals(object? obj) + { + if (ReferenceEquals(null, obj)) return false; + if (ReferenceEquals(this, obj)) return true; + return obj is RandomTraitorAliveCondition alive && alive.Equals(this); + } + + public override int GetHashCode() + { + return Target?.GetHashCode() ?? 0; + } + } +} diff --git a/Content.Server/Objectives/Conditions/StayAliveCondition.cs b/Content.Server/Objectives/Conditions/StayAliveCondition.cs index 97e697f424..69f0ec9fed 100644 --- a/Content.Server/Objectives/Conditions/StayAliveCondition.cs +++ b/Content.Server/Objectives/Conditions/StayAliveCondition.cs @@ -21,7 +21,7 @@ namespace Content.Server.Objectives.Conditions public string Description => Loc.GetString("objective-condition-stay-alive-description"); - public SpriteSpecifier Icon => new SpriteSpecifier.Rsi(new ResourcePath("Objects/Misc/skub.rsi"), "icon"); //didn't know what else would have been a good icon for staying alive + public SpriteSpecifier Icon => new SpriteSpecifier.Rsi(new ResourcePath("Objects/Misc/bureaucracy.rsi"), "folder_white"); public float Progress => (_mind?.CharacterDeadIC ?? false) ? 0f : 1f; diff --git a/Content.Server/Objectives/Requirements/MultipleTraitorsRequirement.cs b/Content.Server/Objectives/Requirements/MultipleTraitorsRequirement.cs new file mode 100644 index 0000000000..fd110e2838 --- /dev/null +++ b/Content.Server/Objectives/Requirements/MultipleTraitorsRequirement.cs @@ -0,0 +1,21 @@ +using System; +using Content.Server.Objectives.Interfaces; +using Content.Server.Traitor; +using Robust.Shared.Serialization.Manager.Attributes; +using Robust.Shared.GameObjects; +using Content.Server.GameTicking.Rules; + +namespace Content.Server.Objectives.Requirements +{ + [DataDefinition] + public class MultipleTraitorsRequirement : IObjectiveRequirement + { + [DataField("traitors")] + private readonly int _requiredTraitors = 2; + + public bool CanBeAssigned(Mind.Mind mind) + { + return EntitySystem.Get().TotalTraitors >= _requiredTraitors; + } + } +} diff --git a/Resources/Locale/en-US/objectives/conditions/other-traitor-alive-condition.ftl b/Resources/Locale/en-US/objectives/conditions/other-traitor-alive-condition.ftl new file mode 100644 index 0000000000..ddff1de051 --- /dev/null +++ b/Resources/Locale/en-US/objectives/conditions/other-traitor-alive-condition.ftl @@ -0,0 +1,2 @@ +objective-condition-other-traitor-alive-title = Ensure fellow traitor {$targetName} stays alive. +objective-condition-other-traitor-alive-description = Identify yourself at your own risk. We just need them alive. diff --git a/Resources/Locale/en-US/objectives/conditions/steal-condition.ftl b/Resources/Locale/en-US/objectives/conditions/steal-condition.ftl index cb24e842df..3bb68abedf 100644 --- a/Resources/Locale/en-US/objectives/conditions/steal-condition.ftl +++ b/Resources/Locale/en-US/objectives/conditions/steal-condition.ftl @@ -1,2 +1,2 @@ -objective-condition-steal-title = Steal {$amount}{$itemName} -objective-condition-steal-description = We need you to steal {$itemName}. Don't get caught. \ No newline at end of file +objective-condition-steal-title = Steal {$amount}{$itemName}. +objective-condition-steal-description = We need you to steal {$itemName}. Don't get caught. diff --git a/Resources/Prototypes/Objectives/traitorObjectives.yml b/Resources/Prototypes/Objectives/traitorObjectives..yml similarity index 87% rename from Resources/Prototypes/Objectives/traitorObjectives.yml rename to Resources/Prototypes/Objectives/traitorObjectives..yml index f2f22bb6be..7f60a7b028 100644 --- a/Resources/Prototypes/Objectives/traitorObjectives.yml +++ b/Resources/Prototypes/Objectives/traitorObjectives..yml @@ -15,9 +15,25 @@ issuer: syndicate requirements: - !type:TraitorRequirement {} + - !type:IncompatibleConditionsRequirement + conditions: + - RandomTraitorAliveCondition conditions: - !type:KillRandomPersonCondition {} canBeDuplicate: true + +- type: objective + id: RandomTraitorAliveObjective + issuer: syndicate + requirements: + - !type:TraitorRequirement {} + - !type:IncompatibleConditionsRequirement + conditions: + - KillRandomPersonCondition + - !type:MultipleTraitorsRequirement + conditions: + - !type:RandomTraitorAliveCondition {} + canBeDuplicate: true - type: objective id: StayAliveObjective