From 8e87aab281d4a7b9ecdc8c624326e138da0a48fc Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sat, 28 May 2022 14:51:19 -0400 Subject: [PATCH 01/40] beginning --- .../GameTicking/Rules/ZombieRuleSystem.cs | 282 ++++++++++++++++++ Content.Shared/CCVar/CCVars.cs | 13 + .../game-presets/preset-zombies.ftl | 7 + Resources/Prototypes/Roles/Antags/zombie.yml | 6 + Resources/Prototypes/game_presets.yml | 11 + Resources/Prototypes/game_rules.yml | 3 + 6 files changed, 322 insertions(+) create mode 100644 Content.Server/GameTicking/Rules/ZombieRuleSystem.cs create mode 100644 Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl create mode 100644 Resources/Prototypes/Roles/Antags/zombie.yml diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs new file mode 100644 index 000000000000..b04bd1be8c6d --- /dev/null +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -0,0 +1,282 @@ +using System.Linq; +using Content.Server.Chat.Managers; +using Content.Server.Disease; +using Content.Server.Players; +using Content.Server.RoundEnd; +using Content.Server.Spawners.Components; +using Content.Server.Station.Components; +using Content.Server.Station.Systems; +using Content.Shared.CCVar; +using Content.Shared.MobState; +using Content.Shared.Roles; +using Robust.Server.Maps; +using Robust.Server.Player; +using Robust.Shared.Configuration; +using Robust.Shared.Map; +using Robust.Shared.Physics.Collision.Shapes; +using Robust.Shared.Prototypes; +using Robust.Shared.Random; +using Robust.Shared.Utility; + +namespace Content.Server.GameTicking.Rules; + +public sealed class ZombieRuleSystem : GameRuleSystem +{ + [Dependency] private readonly IPrototypeManager _prototypeManager = default!; + [Dependency] private readonly IRobustRandom _random = default!; + [Dependency] private readonly IConfigurationManager _cfg = default!; + [Dependency] private readonly IChatManager _chatManager = default!; + [Dependency] private readonly IMapLoader _mapLoader = default!; + [Dependency] private readonly IMapManager _mapManager = default!; + [Dependency] private readonly StationSpawningSystem _stationSpawningSystem = default!; + [Dependency] private readonly StationSystem _stationSystem = default!; + [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; + [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; + + private const string PatientZeroPrototypeID = "PatientZero"; + + private Dictionary _aliveNukeops = new(); + private bool _opsWon; + + public override string Prototype => "Zombie"; + + public override void Initialize() + { + base.Initialize(); + + SubscribeLocalEvent(OnStartAttempt); + //SubscribeLocalEvent(OnPlayersSpawning); + //SubscribeLocalEvent(OnMobStateChanged); + SubscribeLocalEvent(OnRoundEndText); + SubscribeLocalEvent(OnJobAssigned); + } + + private void OnRoundEndText(RoundEndTextAppendEvent ev) + { + if (!Enabled) + return; + + ev.AddLine("ZOMBIE ROUND OVER TESTETEST"); + ev.AddLine(Loc.GetString("nukeops-list-start")); + foreach (var nukeop in _aliveNukeops) + { + ev.AddLine($"- {nukeop.Key.Session?.Name}"); + } + } + + private void OnMobStateChanged(MobStateChangedEvent ev) + { + if (!Enabled) + return; + + if (!_aliveNukeops.TryFirstOrNull(x => x.Key.OwnedEntity == ev.Entity, out var op)) return; + + _aliveNukeops[op.Value.Key] = op.Value.Key.CharacterDeadIC; + + if (_aliveNukeops.Values.All(x => !x)) + { + _roundEndSystem.EndRound(); + } + } + + private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) + { + if (!Enabled) + return; + + var list = new List(ev.Players); + var prefList = new List(); + + foreach (var player in list) + { + if (!ev.Profiles.ContainsKey(player.UserId)) + { + continue; + } + prefList.Add(player); //by default, zombies don't care whether or not you are command or nonantag crew + } + + var playersPerInfected = _cfg.GetCVar(CCVars.ZombiePlayersPerInfected); + var maxInfected = _cfg.GetCVar(CCVars.ZombieMaxInfected); + + var numInfected = Math.Max(1, + (int) Math.Min( + Math.Floor((double) ev.Players.Length / playersPerInfected), maxInfected)); + + for (var i = 0; i < numInfected; i++) + { + IPlayerSession zombie; //this isn't actually a zombie, but rather a patient 0. sue me for naming it shittily -emo + if (prefList.Count == 0) + { + if (list.Count == 0) + { + Logger.InfoS("preset", "Insufficient ready players to fill up with patient 0, stopping the selection."); + break; + } + zombie = _random.PickAndTake(list); + list.Remove(zombie); + Logger.InfoS("preset", "Insufficient preferred patient 0, picking at random."); + } + else + { + zombie = _random.PickAndTake(prefList); + list.Remove(zombie); + Logger.InfoS("preset", "Selected a preferred patient 0."); + } + + var mind = zombie.Data.ContentData()?.Mind; + if (mind == null) + { + Logger.ErrorS("preset", "Failed getting mind for picked patient 0."); + continue; + } + + DebugTools.AssertNotNull(mind.OwnedEntity); + + if(mind.OwnedEntity != null) + _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, "ZombieInfection"); + + mind.Briefing = Loc.GetString("zombie-patientzero-role-greeting"); + } + + foreach (var player in ev.Players) + { + if (player.AttachedEntity != null) + _diseaseSystem.TryAddDisease(player.AttachedEntity.Value, "ZombieInfection");//change this once zombie refactor is in. + } + } + + private void OnPlayersSpawning(RulePlayerSpawningEvent ev) + { + if (!Enabled) + return; + + // Between 1 and : needs at least n players per op. + /*var numInfected = Math.Max(1, + (int)Math.Min( + Math.Floor((double)ev.PlayerPool.Count / _cfg.GetCVar(CCVars.ZombiePlayersPerInfected)), _cfg.GetCVar(CCVars.ZombieMaxInfected))); + + _random.PickAndTake(ev.PlayerPool); + */ + + /* + var map = "/Maps/infiltrator.yml"; + + var aabbs = _stationSystem.Stations.SelectMany(x => + Comp(x).Grids.Select(x => _mapManager.GetGridComp(x).Grid.WorldAABB)).ToArray(); + var aabb = aabbs[0]; + for (int i = 1; i < aabbs.Length; i++) + { + aabb.Union(aabbs[i]); + } + + var (_, gridId) = _mapLoader.LoadBlueprint(GameTicker.DefaultMap, map, new MapLoadOptions + { + Offset = aabb.Center + MathF.Max(aabb.Height / 2f, aabb.Width / 2f) * 2.5f + }); + + if (!gridId.HasValue) + { + Logger.ErrorS("NUKEOPS", $"Gridid was null when loading \"{map}\", aborting."); + foreach (var session in ops) + { + ev.PlayerPool.Add(session); + } + return; + } + + var gridUid = _mapManager.GetGridEuid(gridId.Value); + + // TODO: Loot table or something + var commanderGear = _prototypeManager.Index("SyndicateCommanderGearFull"); + var starterGear = _prototypeManager.Index("SyndicateOperativeGearFull"); + var medicGear = _prototypeManager.Index("SyndicateOperativeMedicFull"); + + var spawns = new List(); + + // Forgive me for hardcoding prototypes + foreach (var (_, meta, xform) in EntityManager.EntityQuery(true)) + { + if (meta.EntityPrototype?.ID != "SpawnPointNukies" || xform.ParentUid != gridUid) continue; + + spawns.Add(xform.Coordinates); + } + + if (spawns.Count == 0) + { + spawns.Add(EntityManager.GetComponent(gridUid).Coordinates); + Logger.WarningS("nukies", $"Fell back to default spawn for nukies!"); + } + + // TODO: This should spawn the nukies in regardless and transfer if possible; rest should go to shot roles. + for (var i = 0; i < ops.Length; i++) + { + string name; + StartingGearPrototype gear; + + switch (i) + { + case 0: + name = $"Commander"; + gear = commanderGear; + break; + case 1: + name = $"Operator #{i}"; + gear = medicGear; + break; + default: + name = $"Operator #{i}"; + gear = starterGear; + break; + } + + var session = ops[i]; + var newMind = new Mind.Mind(session.UserId) + { + CharacterName = name + }; + newMind.ChangeOwningPlayer(session.UserId); + + var mob = EntityManager.SpawnEntity("MobHuman", _random.Pick(spawns)); + EntityManager.GetComponent(mob).EntityName = name; + + newMind.TransferTo(mob); + _stationSpawningSystem.EquipStartingGear(mob, gear, null); + + _aliveNukeops.Add(newMind, true); + + GameTicker.PlayerJoinGame(session); + }*/ + } + + private void OnStartAttempt(RoundStartAttemptEvent ev) + { + if (!Enabled) + return; + + //Uncomment this once im done local testing + /* + var minPlayers = _cfg.GetCVar(CCVars.ZombieMinPlayers); + if (!ev.Forced && ev.Players.Length < minPlayers) + { + _chatManager.DispatchServerAnnouncement(Loc.GetString("zombie-not-enough-ready-players", ("readyPlayersCount", ev.Players.Length), ("minimumPlayers", minPlayers))); + ev.Cancel(); + return; + } + + if (ev.Players.Length == 0) + { + _chatManager.DispatchServerAnnouncement(Loc.GetString("zombie-no-one-ready")); + ev.Cancel(); + return; + } + //*/ + } + + public override void Started() + { + _opsWon = false; + } + + public override void Ended() { } +} diff --git a/Content.Shared/CCVar/CCVars.cs b/Content.Shared/CCVar/CCVars.cs index 329a374391c4..bc01e5b69bfa 100644 --- a/Content.Shared/CCVar/CCVars.cs +++ b/Content.Shared/CCVar/CCVars.cs @@ -286,6 +286,19 @@ public static readonly CVarDef public static readonly CVarDef NukeopsPlayersPerOp = CVarDef.Create("nukeops.players_per_op", 5); + /* + * Zombie + */ + + public static readonly CVarDef ZombieMinPlayers = + CVarDef.Create("zombie.min_players", 25); + + public static readonly CVarDef ZombieMaxInfected = + CVarDef.Create("zombie.max_infected", 4); + + public static readonly CVarDef ZombiePlayersPerInfected = + CVarDef.Create("zombie.players_per_infected", 7); + /* * Console */ diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl new file mode 100644 index 000000000000..df38c445f943 --- /dev/null +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -0,0 +1,7 @@ +zombie-title = Zombies +zombie-description = A virus able to create the undead has been unleashed unto the station! Work with your crewmates to contain the outbreak and survive. + +zombie-not-enough-ready-players = Not enough players readied up for the game! There were {$readyPlayersCount} players readied up out of {$minimumPlayers} needed. Can't start Zombies. +zombie-no-one-ready = No players readied up! Can't start Zombies. + +zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. \ No newline at end of file diff --git a/Resources/Prototypes/Roles/Antags/zombie.yml b/Resources/Prototypes/Roles/Antags/zombie.yml new file mode 100644 index 000000000000..d69d8f24ac7b --- /dev/null +++ b/Resources/Prototypes/Roles/Antags/zombie.yml @@ -0,0 +1,6 @@ +- type: antag + id: PatientZero + name: "Patient 0" + antagonist: true + setPreference: false + objective: "Once you turn, infect as many other crew members as possible" \ No newline at end of file diff --git a/Resources/Prototypes/game_presets.yml b/Resources/Prototypes/game_presets.yml index 8a088044d41b..3851d49feb9f 100644 --- a/Resources/Prototypes/game_presets.yml +++ b/Resources/Prototypes/game_presets.yml @@ -78,3 +78,14 @@ showInVote: false rules: - Nukeops + +- type: gamePreset + id: Zombie + alias: + - zombie + - zombies + name: zombie-title + description: zombie-description + showInVote: true + rules: + - Zombie diff --git a/Resources/Prototypes/game_rules.yml b/Resources/Prototypes/game_rules.yml index dff36b9cdaa1..6e57855ccfda 100644 --- a/Resources/Prototypes/game_rules.yml +++ b/Resources/Prototypes/game_rules.yml @@ -24,3 +24,6 @@ - type: gameRule id: Secret + +- type: gameRule + id: Zombie From f45274c5c02964581f1b7a7fcab9d5a085072a31 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sat, 28 May 2022 20:34:30 -0400 Subject: [PATCH 02/40] tweakies --- .../GameTicking/Rules/ZombieRuleSystem.cs | 17 +++++++---------- 1 file changed, 7 insertions(+), 10 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index b04bd1be8c6d..bb4db16f9dc6 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -34,6 +34,7 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; private const string PatientZeroPrototypeID = "PatientZero"; + private const string InitialZombieVirusPrototype = "ZombieInfection"; private Dictionary _aliveNukeops = new(); private bool _opsWon; @@ -105,7 +106,7 @@ private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) for (var i = 0; i < numInfected; i++) { - IPlayerSession zombie; //this isn't actually a zombie, but rather a patient 0. sue me for naming it shittily -emo + IPlayerSession zombie; //this isn't actually a zombie, but rather a patient 0. sue me for naming it shitty -emo if (prefList.Count == 0) { if (list.Count == 0) @@ -133,16 +134,11 @@ private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) DebugTools.AssertNotNull(mind.OwnedEntity); - if(mind.OwnedEntity != null) - _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, "ZombieInfection"); + if (mind.OwnedEntity != null) + _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. - mind.Briefing = Loc.GetString("zombie-patientzero-role-greeting"); - } - - foreach (var player in ev.Players) - { - if (player.AttachedEntity != null) - _diseaseSystem.TryAddDisease(player.AttachedEntity.Value, "ZombieInfection");//change this once zombie refactor is in. + if (mind.Session != null) + _chatManager.DispatchServerMessage(mind.Session, Loc.GetString("zombie-patientzero-role-greeting")); } } @@ -150,6 +146,7 @@ private void OnPlayersSpawning(RulePlayerSpawningEvent ev) { if (!Enabled) return; + //these are staying here because i want the code for reference // Between 1 and : needs at least n players per op. /*var numInfected = Math.Max(1, From 475ad60c15b32a248efcf195600c20e9f7ec728d Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 29 May 2022 09:33:44 -0400 Subject: [PATCH 03/40] cburn + more stuff --- Content.Server/Chat/Managers/ChatManager.cs | 6 +++- Content.Server/Chat/Managers/IChatManager.cs | 2 +- .../GameTicking/Rules/ZombieRuleSystem.cs | 8 ++++- .../Clothing/OuterClothing/hardsuits.yml | 33 ++++++++++++++++++ .../Roles/Jobs/Fun/misc_startinggear.yml | 20 +++++++++++ .../cburn.rsi/equipped-OUTERCLOTHING.png | Bin 0 -> 2329 bytes .../Hardsuits/cburn.rsi/icon.png | Bin 0 -> 1265 bytes .../Hardsuits/cburn.rsi/inhand-left.png | Bin 0 -> 1247 bytes .../Hardsuits/cburn.rsi/inhand-right.png | Bin 0 -> 1306 bytes .../Hardsuits/cburn.rsi/meta.json | 26 ++++++++++++++ 10 files changed, 92 insertions(+), 3 deletions(-) create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/icon.png create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/inhand-left.png create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/inhand-right.png create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json diff --git a/Content.Server/Chat/Managers/ChatManager.cs b/Content.Server/Chat/Managers/ChatManager.cs index 09a187f010c2..9d263820d3a7 100644 --- a/Content.Server/Chat/Managers/ChatManager.cs +++ b/Content.Server/Chat/Managers/ChatManager.cs @@ -215,7 +215,7 @@ private void SendAdminChat(IPlayerSession player, string message) #region Utility - public void ChatMessageToOne(ChatChannel channel, string message, string messageWrap, EntityUid source, bool hideChat, INetChannel client) + public void ChatMessageToOne(ChatChannel channel, string message, string messageWrap, EntityUid source, bool hideChat, INetChannel client, Color? colorOverride = null) { var msg = new MsgChatMessage(); msg.Channel = channel; @@ -223,6 +223,10 @@ public void ChatMessageToOne(ChatChannel channel, string message, string message msg.MessageWrap = messageWrap; msg.SenderEntity = source; msg.HideChat = hideChat; + if (colorOverride != null) + { + msg.MessageColorOverride = colorOverride.Value; + } _netManager.ServerSendMessage(msg, client); } diff --git a/Content.Server/Chat/Managers/IChatManager.cs b/Content.Server/Chat/Managers/IChatManager.cs index 76a525e6f752..d87eef8cf6c8 100644 --- a/Content.Server/Chat/Managers/IChatManager.cs +++ b/Content.Server/Chat/Managers/IChatManager.cs @@ -33,7 +33,7 @@ void DispatchStationAnnouncement(string message, string sender = "CentComm", boo void SendAdminAnnouncement(string message); void ChatMessageToOne(ChatChannel channel, string message, string messageWrap, EntityUid source, bool hideChat, - INetChannel client); + INetChannel client, Color? colorOverride = null); void ChatMessageToMany(ChatChannel channel, string message, string messageWrap, EntityUid source, bool hideChat, List clients); void ChatMessageToAll(ChatChannel channel, string message, string messageWrap, Color? colorOverride = null); diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index bb4db16f9dc6..975d9563385f 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -138,7 +138,13 @@ private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. if (mind.Session != null) - _chatManager.DispatchServerMessage(mind.Session, Loc.GetString("zombie-patientzero-role-greeting")); + { + var messageWrapper = Loc.GetString("chat-manager-server-wrap-message"); + + // I went all the way to ChatManager.cs and all i got was this lousy T-shirt + _chatManager.ChatMessageToOne(Shared.Chat.ChatChannel.Server, Loc.GetString("zombie-patientzero-role-greeting"), + messageWrapper, default, false, mind.Session.ConnectedClient, Color.Plum); + } } } diff --git a/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml b/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml index d30245f7e550..7cfda5565f85 100644 --- a/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml +++ b/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml @@ -568,3 +568,36 @@ resistance: 0.3 - type: ToggleableClothing clothingPrototype: ClothingHeadHelmetHardsuitSyndieElite + +- type: entity + parent: ClothingOuterHardsuitBase + id: ClothingOuterHardsuitCBURN + name: CBURN exosuit + description: A lightweight yet strong exosuit used for special cleanup operations. + components: + - type: Sprite + sprite: Clothing/OuterClothing/Hardsuits/cburn.rsi + - type: Clothing + sprite: Clothing/OuterClothing/Hardsuits/cburn.rsi + - type: PressureProtection + highPressureMultiplier: 0.02 + lowPressureMultiplier: 1000 + - type: ClothingSpeedModifier + walkModifier: 1.0 + sprintModifier: 1.0 + - type: TemperatureProtection + coefficient: 0.001 + - type: Armor + modifiers: + coefficients: + Blunt: 0.7 + Slash: 0.7 + Piercing: 0.6 + Heat: 0.05 + Cold: 0.1 + Shock: 0.1 + Radiation: 0.1 + - type: ExplosionResistance + resistance: 0.7 + - type: ToggleableClothing + clothingPrototype: ClothingHeadHelmetHardsuitSyndieElite diff --git a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml index 36e88d4679f7..0e0ea06f853b 100644 --- a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml +++ b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml @@ -136,3 +136,23 @@ innerclothingskirt: ClothingUniformJumpskirtOperative satchel: ClothingBackpackDuffelSyndicateOperativeMedic duffelbag: ClothingBackpackDuffelSyndicateOperativeMedic + +#CBURN Unit Gear - Full Kit +- type: startingGear + id: CBURNGear + equipment: + jumpsuit: ClothingUniformJumpsuitColorBrown + back: ClothingBackpack + mask: ClothingMaskGas + eyes: ClothingEyesGlassesSunglasses + ears: ClothingHeadsetService + gloves: ClothingHandsGlovesFingerless + outerClothing: ClothingOuterHardsuitCBURN + shoes: ClothingShoesBootsJack + id: CentcomPDA + pocket1: DoubleEmergencyOxygenTankFilled + pocket2: LaserGun + belt: ClothingBeltBandolier + innerclothingskirt: ClothingUniformJumpsuitColorBrown + satchel: ClothingBackpackSatchel + duffelbag: ClothingBackpackDuffel \ No newline at end of file diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png new file mode 100644 index 0000000000000000000000000000000000000000..e400e4189193e9e7277ddb06ce35568344fe9dc6 GIT binary patch literal 2329 zcmV+!3Fh{RP)EX>4Tx04R}tkv&MmKpe$iQ?()$1v`j1WN4i%h>AFB6^c+H)C#RSm|XfHG-*gu zTpR`0f`cE6RR;BL;+afkw@7zKZ37qAElt@2E_Z;zCqp)6R|?V;3I*W(jJ_!c4BP@et6p!-eVjf38R{x^0~{Oz zBSp$y^Lcl7dvE`qY4-O6ZWD5)cX)k&000M2NklbC9LK-07T-!EtwV9l z7%ic;EY@jiN^KDo7MdlYP`32qp%?M6z4c=0Z7F+^?PYJf3(_9;;6>U?iL@+&1?wN` zpGIZDLXeo5OuCFNRoq$HX7-T2@r@cYZxYjGHy;Q|Uf#U#`~C9Xn>X+G11eOgP@zJF z3KjmRcs_Rr+%S0muBmBh>$@m6;@)>ZxUz-oA}ajjPrvTD?#}I7W-%S%(a(n)eaDpt z`oiY>ng(RFG#bQ4n-lKbzGc$#qkm`c;NkOis~;Pm%Udtn)4{D@MoU{SRn>6hH~|2pk_l*98iV)mnvSgF)K^t)-+Hv1SHGYGv`_j88is~r$Y^OCG*@|G^#Rzl0oeKgfLs4S2MqLu&FfdYEHPcz zK?s2)`O)7SMWnkO{k>60k{^T+=(=uo>iX3#4D^MI8U+J=VKa2L(bA8{7XZLAmX_1+ z^mkR&5IWoFNWb6+NF@`v)aJwZ^pXbv48y?F*#(SDOkrNrF)}fQr?U$%3Y$;&%0YH-ch;+B($Z>*5cRM7>Z`GyxPO0YY3?T&HesjZSU{iAdKRZFnhTo46Jt}5v1 zJZB1m;J5=$p!#f|=(MBXDOBGn2TlQ@B?xV+8roJhd_K`8NJl^_nXo!Q2!YQhTGt3I zLB}0&qR*lzYcLFBkE40@4;%q>1qN~p%kk!VOs*=}e76mGs~WNKIW&lkh$r5_TUQGJ z_)}fyGSZ1YUFPcL}}`oiYQrhzkF zvZo#`fAH|RhrNcwUPthtOsTmyDDLI{B@=Y|%YivW9)N~kzfz5Z@+--6@fNn8E zQa#2#y{9&^CENNQL`bR!y~XKAVd-0Cx{fiF62$wO2BbE! zm|0c<05i)fQX5&kuW5kL60~huO9|DdTC6_plN)_U4(RDTXGWq?YiGuu1_8MvDf$c^ ziAGEA1gc-?F7tX}j$7aH6c~-gtk1hoW#;GRneut3O=56x5CCxR-o29O=YETU2S*M# zXlGT*UEjY|ze0ry6)IGy@ZW@c6LIJEEfXj%CSPjUu=#$W`-9-BOvB*7PDuK5I)XKv z?H7*|99N{qvxgq3jqGP}#BRg)>yuL_IDQzSLeXnGVKEu7#p?&}-!%{03DkJ{k4Jkt ztlyfN1Bg9+j1*r6C^sfM`#L6}rxp;areD64QhXMOlNkRSi*W zgtC~x%(Ch@C<1UefIfnF$dptS~!PcJ!ckNX^(jRsQ;!@$k1%LqyJyv=bFlIn4@>#~)QL181-Ja9XJ z8ZQU}hK6HEB@-ZoSos2nbtuZV-P9ZaA;ijBqk$1ON8|jFjAMRV%zk8I3fDqAad@5; zm>0I~YoQ=UCZ=rp066AH)yWH7ZE~#vv&uT;8hg%wc*d8T|D$7&17AW_oga$wqN*Ai z#0&WTmmzrTYC#Brx}w_Z#1p@BwaMjxkW>%h*ayrr*;$jT3a*@zpzAswaPGr-+4!rf zYVGZ|CnVK>6ogz#PNcgXqc0W#+)M zJHmK;!Bvj3t8nhhrh!MJW1x8f<)*c@)dX_63O=8RN26m{*)$4WwlA(6aK=jzmRkX! zEO`O>pxR-%b>F-tC%6viOOoHp3n(`)U%mveldDkH6d9J?xjN+{nM~qx>sbhbP?YgN z5e{IV1wI$Lt{3fmS5ttE$scxJz>PqbqEP@a4>MXT%d+Rh z7uhVEt57Vi9bk{i^W_Clc=7{S*j#}feRuo=$(17s#ii?j00000NkvXXu0mjf_Gnu^ literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/icon.png b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..8d7c6be6a656a20cbf99d19edc0e9022fb1ea8b5 GIT binary patch literal 1265 zcmVEX>4Tx04R}tkv&MmKpe$iQ?()$1&fF{WT;LSL`5963Pq?8YK2xEOfLNpnlvOS zE{=k0!NHHks)LKOt`4q(Aou~|=H{g6A|?JWDYS_3;J6>}?mh0_0Ya_BG^=e4&~)2O zCE{WxyCQ~O5k@aM(2tPJEMr!ZlJFg0_XzOyF2=L`&;2>N)ttqEfJi*U4AUlFC!X50 z4bJ<-5muB{;&b9rlP*a7$aTfzH_io@1)do()2TV)2(egbVWovx(bR}1iKD8fQ@)V# zSmnIMSu0goAMvPXS6bmWZkNfxsUB5&wg`Uwzx2Cnp`zgz>RKS{4P zwdfJhvkhEaH#KDsxZD8-o($QPT`5RY$mfCgGy0}1(02=Tt$MvR_Hp_Eq^Yaq4RCM> zj1(w)&F9^nt-bwwrqSOI3T<+IV#RYk0009hNkl(ERjs>`t5gW-Cgn=6&hmx)Sqoo^)o7qeeY^*NL$ODBJB1 zde_(H1gaKwE5(|fmz;3ShZ>x1OeZ_dQA`n2q8E;br3=j1OdzlD!Y3Lt5yx| zPJ1BdSY4nXgy4(MdIhPF&fMYa@4k)AF_HksIYZMlD%+dkTxNksAEvN7ZPJ-LQHPUX#r^5Mys;fvfBHP(x)Rrw zRCf0g_hx$zJV-4t^VTOlKgG;jp9iT00PfB9icqatfBJm#eW0?tcY#C*!SZs?TE{sf zm0ALz^Xm1$H4_QwhyC-POac4fSd6B71^CiqT|dV9E3RACrQ>)1 b1;@o-Ket`~k=83300000NkvXXu0mjf0gYo+ literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/inhand-left.png b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/inhand-left.png new file mode 100644 index 0000000000000000000000000000000000000000..9071444e11964d9c0e0531f1d82376d24592a1c1 GIT binary patch literal 1247 zcmV<51R(o~P)EX>4Tx04R}tkv&MmKpe$iQ%j3f9oj*}AwzYtAS&XhRVYG*P%E_RU~>J0CJjl7 zi=*ILaPVWX>fqw6tAnc`2!4RLxj8AiNQwVT3N2zhIPS;0dyl(!fY7Wm)$ADuRLwHd z$%L5At%|`{gb_hMLI}vr)aN8A1<&zy4NMaF7kRU=q9TikzAx^7CiitGsCp`Q^j$a~|LaquJ zITlcZ3fb|4|H1EW&En*Qn-op}ffw8U7y*L2K&xTf-^aGyIsyF8z?IhV*P6i0C+Urj z7CQn4wtDJa?(N?*?f!lM{sVG&@SkWa0009PNkl9@!kVL5ClOG1VIo4K@bE%5dJ5uID_T$ zc>o^XyWIpheC(vvzP^6*uGRj(&G`8EclCwoToXWRAKT6XaQ@O&E1%DQqv@8|4X8ZN zH9fCFsa$2i&Jt*!UBi7ij*B}ovEuzI&vVUZul#T7_iWGNj!al_8?Y+QV1?;c;~mE( zSb9gGeS)QTIF8G+SAOTouB5lq4T`fx0_{_rEn=q|q4ZIR)d1=hR=*Db=L0oIV1nxC3T}M!5f^z|nnsJ9YP;6d2pFH&h2Q zLn8no4+`6d0Y61xG=dViHtoWC|@DWy8^aafAF#>~9O zwL6cjnR$<*uJxjsK#vUY79pD+09vKDxUy#XM^gK#1GGm&ujq*Z%csMr(^sul`=aa> zu^Vu9@J30IXihG)JIIWdO;8bK@bE%5ClOGgq4VWRX9$*-b?%$ zQ5Q^mvm}-v#DG8DfIrPYVL&$-4A@z&-@F^CFNquhUw7WNvm8Hi zFw(MlA`PHkVeai4CJyZG`rJS=4FHrEX>4Tx04R}tkv&MmKpe$iQ%j3f9oj*}AwzYtAS&XhRVYG*P%E_RU~>J0CJjl7 zi=*ILaPVWX>fqw6tAnc`2!4RLxj8AiNQwVT3N2zhIPS;0dyl(!fY7Wm)$ADuRLwHd z$%L5At%|`{gb_hMLI}vr)aN8A1<&zy4NMaF7kRU=q9TikzAx^7CiitGsCp`Q^j$a~|LaquJ zITlcZ3fb|4|H1EW&En*Qn-op}ffw8U7y*L2K&xTf-^aGyIsyF8z?IhV*P6i0C+Urj z7CQn4wtDJa?(N?*?f!lM{sVG&@SkWa0009~Nkl1o^MNh?pUOWUr&{GcLVRMiy0kd6- z2VqMhVKeWtE+~ZXRu-p+^3}*E}CsW@q*fzj@|;-x=l|5JCtcgb+dqA%qY@ z93)=tN-C8C;L-g%5x@^WUGm)fn}6N&+~>~3#6%Aw?wre)UR;O(j0w>?0l<~3*S%CK z)s#8b_$TXsFGSielg$-*bpK9NFd^Tc80Oy1%MlF)+i#5r1S2&FwqkElN|Es6gqsDdwHzvc!Oy?`QTP4*J`2GC&bt{(${`G-%u@nZqjTC`urTFdycfcb|{ntt4mT>jH~h;P4CoYq6z=5Hzh zRQiuniYqtfJ*8B&9}S9(DY3Mc=f>T~-qKp0j48GKZp#AX-$25T1C?d|&E5prmru8oI%eo zgb+dqA%qY@h`rZWQ(cW(O?|b~>V{{lxxhxPZ;2fsO*2C~vE7l`%UkDr@!y|x3)o4) zIx4^*OpxqUM_piUb|$)g>l$&LK Date: Sun, 29 May 2022 11:37:23 -0400 Subject: [PATCH 04/40] cburn outfit --- .../Clothing/Head/hardsuit-helmets.yml | 51 +++++++++++++++ .../Clothing/OuterClothing/hardsuits.yml | 2 +- .../Roles/Jobs/Fun/misc_startinggear.yml | 3 +- .../cburn.rsi/equipped-head-unshaded.png | Bin 0 -> 162 bytes .../Hardsuits/cburn.rsi/equipped-head.png | Bin 0 -> 623 bytes .../Head/Hardsuits/cburn.rsi/icon-flash.png | Bin 0 -> 652 bytes .../Hardsuits/cburn.rsi/icon-unshaded.png | Bin 0 -> 141 bytes .../Head/Hardsuits/cburn.rsi/icon.png | Bin 0 -> 408 bytes .../cburn.rsi/inhand-left-unshaded.png | Bin 0 -> 465 bytes .../Head/Hardsuits/cburn.rsi/inhand-left.png | Bin 0 -> 519 bytes .../cburn.rsi/inhand-right-unshaded.png | Bin 0 -> 415 bytes .../Head/Hardsuits/cburn.rsi/inhand-right.png | Bin 0 -> 527 bytes .../Hardsuits/cburn.rsi/light-overlay.png | Bin 0 -> 333 bytes .../Head/Hardsuits/cburn.rsi/meta.json | 59 ++++++++++++++++++ .../cburn.rsi/equipped-OUTERCLOTHING.png | Bin 2329 -> 2333 bytes 15 files changed, 113 insertions(+), 2 deletions(-) create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/equipped-head-unshaded.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/equipped-head.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon-flash.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon-unshaded.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-left-unshaded.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-left.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right-unshaded.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/light-overlay.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json diff --git a/Resources/Prototypes/Entities/Clothing/Head/hardsuit-helmets.yml b/Resources/Prototypes/Entities/Clothing/Head/hardsuit-helmets.yml index 3d38af729fe9..81fff225c055 100644 --- a/Resources/Prototypes/Entities/Clothing/Head/hardsuit-helmets.yml +++ b/Resources/Prototypes/Entities/Clothing/Head/hardsuit-helmets.yml @@ -404,3 +404,54 @@ Piercing: 0.8 Heat: 0.2 Radiation: 0.5 + +- type: entity + parent: ClothingHeadHardsuitWithLightBase + id: ClothingHeadHelmetCBURN + noSpawn: true + name: syndicate elite helmet + description: A pressure resistant and fireproof hood worn by special cleanup units. + components: + - type: Sprite + netsync: false + sprite: Clothing/Head/Hardsuits/cburn.rsi + layers: + - state: icon + - state: icon-unshaded + shader: unshaded + - state: light-overlay + visible: false + shader: unshaded + map: [ "light" ] + - type: Clothing + clothingVisuals: + head: + - state: equipped-head + - state: equipped-head-unshaded + shader: unshaded + inhandVisuals: + left: + - state: inhand-left + - state: inhand-left-unshaded + shader: unshaded + right: + - state: inhand-right + - state: inhand-right-unshaded + shader: unshaded + - type: PointLight + color: orange + - type: PressureProtection + highPressureMultiplier: 0.08 + lowPressureMultiplier: 1000 + - type: TemperatureProtection + coefficient: 0.005 + - type: Armor + modifiers: + coefficients: + Blunt: 0.9 + Slash: 0.9 + Piercing: 0.9 + Heat: 0.1 + Shock: 0.1 + Cold: 0.2 + Radiation: 0.2 diff --git a/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml b/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml index 7cfda5565f85..515d71a70b0c 100644 --- a/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml +++ b/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml @@ -600,4 +600,4 @@ - type: ExplosionResistance resistance: 0.7 - type: ToggleableClothing - clothingPrototype: ClothingHeadHelmetHardsuitSyndieElite + clothingPrototype: ClothingHeadHelmetCBURN \ No newline at end of file diff --git a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml index 0e0ea06f853b..744e16595273 100644 --- a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml +++ b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml @@ -150,8 +150,9 @@ outerClothing: ClothingOuterHardsuitCBURN shoes: ClothingShoesBootsJack id: CentcomPDA - pocket1: DoubleEmergencyOxygenTankFilled + pocket1: CombatKnife pocket2: LaserGun + suitstorage: YellowOxygenTankFilled belt: ClothingBeltBandolier innerclothingskirt: ClothingUniformJumpsuitColorBrown satchel: ClothingBackpackSatchel diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/equipped-head-unshaded.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/equipped-head-unshaded.png new file mode 100644 index 0000000000000000000000000000000000000000..7fd9a0b229c3448411cd7990d6404941bbb08880 GIT binary patch literal 162 zcmeAS@N?(olHy`uVBq!ia0vp^4j|0I1|(Ny7TyC=jKx9jP7LeL$-D$|Vmw_OLn`LH zJ!{C@V8GyVQK>2N_Kd_z48qn7m}zv;F>G0fqmKeuyvRMDGzj9|fi&lv??3hlFvDLVqPx%DM>^@RCt{2+P_O%Q4|O8ZzUZHmaZ|sge(dLDIIFW!O5jd<_!J;Zz(Q9Mn`E7 z+}yf!aILFO9RwW&8#+WN84{m)A{QbJWQ>E}@ZR$UJtr^EA>YrI`||EN_was%+yl^b zd!spNXR9&@k5y|2s<~b}zWAh_t;!&q%_CPR4#%!qO}K75ks`z$e@2spKX}yVNsBYS zr~tP5QL@>5NyJY{zHE%a^2!My6jxX*Hh-y$sx<4QsGgm08x5rie0Z|K1 zqCdc&LzuP*s@>tMRx?lp+b?kA-D;*2`Sb4Jv7CxJY=XC%8Z-w)T3Q+rT6nM>SIvWFj zA(9ea_+IV1`t_^21uWZ)U<(1^{ihbg!ik88h=_=Yh=^!9-2?hz1wgJJTsi;%002ov JPDHLkV1gY18@T`g literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon-flash.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon-flash.png new file mode 100644 index 0000000000000000000000000000000000000000..d37c1afe3e2fa59c546e099719f134de9d9d77b6 GIT binary patch literal 652 zcmV;70(1R|P)Px%MoC0LR9J=Wl}}I8a2Urw>)Ngx5VHW=VEi3n8sou(Q4b~~@#rhy75EBBd-cKoS_v6@9-U5mulSn3p zd~VleZZeJ2>Cx?U0giRu4%~=B6VP?rtki6Z%^Coi>@@J_Ex5e6B9(;N!9HfQMx|yW z(p(q-pnYnyyLU)tNY=l^dYaV=Nj^d7K6 e4T!EB1_s4CE+&a*IT}DC89ZJ6T-G@yGywqk4=nKj literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..adfb7557f7e7d85210cbcd1dbc25d8361a2c167f GIT binary patch literal 408 zcmV;J0cZY+P)Px$Qb|NXR9J=WmAy{FP#A_EO(&yaw56a4lY=fU3=T{#-T{+WLEsG1k)qbppzDE=V+7Mdiyzt*ZZ0Z02x#6p7g#i>TWdJ$;RdU^G?n{~_ zOVtSJh`Uc7Ld2PM+jgiQ)rg`%xu-I~a5yCN)9`a=%+|ie&Or%)@yiFFZ&R*g2urEA zZ~#araND`(QUDJC?@NvemD3Y?y~n=+061$L>uxCqARNsIeGkb0+(O?=uhFb{0D!yK z7<+p}LClX=FVOh{`w2^)qAZUn zA)oC!dUqa4osz!v`OVSo?bYx9&wkSS{bA+*Juiy299-bwWa3M$JFBMFrYAGrdu-iz z{{7nPbDb;R^5yxjT3FpBD(EQiWjZk& zDCgMkDko>4&XCHreCF(0@sEcXmPk)H1}CQdV0gAQ^qS#|j0r!a55R@N3YO*aeONBR zqI2+la+^>+vqVD)^QAAg+-IV$+-`le+5J&|gCS$jZ{0+xV=Nb9Zie1U_hI-sJ$q^G zF&3a%3$)4@OQhNBR)@*`yii;exwPuzOy;^2uJmN}rib&@|7n$(E1datdFmy*WG0X0 nIUrpd(!TdvatmJE|C6c6(ue!v6Wd&195Hyh`njxgN@xNAxeCiF literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-left.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-left.png new file mode 100644 index 0000000000000000000000000000000000000000..43f27a890f29dfdbc6e08f9a339965c03d33e4e8 GIT binary patch literal 519 zcmeAS@N?(olHy`uVBq!ia0vp^4j|0I1|(Ny7TyC=jKx9jP7LeL$-D%z4|=*dhE&XX zd&|)Ku!9Kuhy9D17wpKI>~><2f=JQikq&ha$;zl+y85gwH@bD))#BzL{6V_ zle?w$IMrvxoHO5R*W~9s{PW0YOKy3!aPP6)H5CtDZ+O2^R(#vzzMkm|w=f)d-zWZA z_KeQiN00x>eqFuN!Kv_(d+*9cdl(o#+{$|NfrsJNedXMQLc6j(0&y8RH&#xZ_KAt( zVPbl=X^~A{&6WLo`##HGsF1&~KdDeZk^Si2ytQ>kU#b^xJAEODL19PIuDm3ew}A8{ z!*7LOA9M@dbbs$Amaw5+!S{c|w0{lzFWfgyuwM7&b@5{^gEj3A+c=JiK6v+$*PQ=s z0DsdP?UKh_1u=0BhW9ypzD^Q9)cpQ;=d;U~M<~W0t|w)z4*} HQ$iB}%bM_> literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right-unshaded.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right-unshaded.png new file mode 100644 index 0000000000000000000000000000000000000000..118914c8d3f08f04301483e8c76c9a603d3f5d17 GIT binary patch literal 415 zcmeAS@N?(olHy`uVBq!ia0vp^4j|0I1|(Ny7TyC=jKx9jP7LeL$-D%zBRyRlLn`LH zy=mxu*nxrdfw(8am)Wq literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right.png new file mode 100644 index 0000000000000000000000000000000000000000..602020b276949e62f04118d9cd9c686302f6844e GIT binary patch literal 527 zcmV+q0`UEbP)Px$$w@>(RCt{2+Obcr(tn0u8;yIEIPZ0abR+Bac1BT=*B|A=tx3L+}K4v#8y_wW=t!P&_%IZjts)<41X6D_7amoJtmUo1)UXT$-1 zpk1ER_Wlli_CBcdycIZMn#ppm${s2J5z%z=M(4LgM6;if8PQ%&L%d|T?l3eKb!&tQ z;JQOPtsMO7q-hlOw2yjzMg9-)SIm@GVBM~Hm!0d#oU-2|clKAzgo_6N0000000000 z09Y^f=WcPK!PHOZu|kV$@Fw*Sh@|}itH>G>lFjCp zh2Z@Jj?<;bmsgGP{+?0++E@31*IeDMdHzC}DAp~&@n!>F2x3f6DgXdT#y12LzG@SX R$Z`Mx002ovPDHLkV1i?J>;wP+ literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/light-overlay.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/light-overlay.png new file mode 100644 index 0000000000000000000000000000000000000000..ff7347fe6ee1df2d09efdef0a797c4174822c416 GIT binary patch literal 333 zcmV-T0kZyyP)Px$2T4RhR9J=Wl)(zZFbszOWxMGPg5bfE@8I1%`n>xN17QcDutW8@>cIp;-E4Og z%nzk&mL^|ATEJv7nf_fx%AsxB58LUq-c9+Q&-YtwYntY3{3-=7lX%PXhUbC*&w|V; zSpm`WdD%@Qu6gzv1b{1wV-`dfz(n#|twoMO7C|HdRB}lS0Q)h7hxRLpRsecl3P=(n zw+Hm8>oJ6(Bsyq^F@%n7UYT7ga4x{0zFkSQA4BN016M$7KH4)YN;z;xI}Ui|;C)F{ z>4A6oJ^Ks*T+VGs0z?qt;2!VOIvyRO2F$&RSpX4)R6{_#TDv95frSr|1eON}QIjo6 fY%-Zlrk~LZL(X#79wy%000000NkvXXu0mjfQca1O literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json new file mode 100644 index 000000000000..8decf1b6af8c --- /dev/null +++ b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json @@ -0,0 +1,59 @@ +{ + "version": 1, + "license": "CC-BY-SA-3.0", + "copyright": "Made by EmoGarbage404", + "size": { + "x": 32, + "y": 32 + }, + "states": [ + { + "name": "icon" + }, + { + "name": "icon-unshaded" + }, + { + "name": "icon-flash" + }, + { + "name": "light-overlay" + }, + { + "name": "equipped-head", + "directions": 4 + }, + { + "name": "equipped-head-light", + "directions": 4 + }, + { + "name": "equipped-head-unshaded", + "directions": 4 + }, + { + "name": "inhand-left", + "directions": 4 + }, + { + "name": "inhand-left-unshaded", + "directions": 4 + }, + { + "name": "inhand-left-light", + "directions": 4 + }, + { + "name": "inhand-right", + "directions": 4 + }, + { + "name": "inhand-right-unshaded", + "directions": 4 + }, + { + "name": "inhand-right-light", + "directions": 4 + } + ] +} diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png index e400e4189193e9e7277ddb06ce35568344fe9dc6..c7ed8fa9ff56f3e7b384734c8121736a80eb526e 100644 GIT binary patch delta 1919 zcmV-_2Y~pQ5}gvTv;luqNkl7() ze9P3dRqI+5n=$m=53bt6_0Y{5*G&NU@uy#RJh#`qazQorf>+;h=E44`nOVyL0Gh;R zo6yZ0*UjwaKN2|R#qB$f%5H?g{;2t}w#mBAGCiP4Y_@(M{yWR1??+p{g1N`r-(*gfROu<+@82(@#vz7t9y$?c~6lC;H3#UV*S5JI5qx>czwmo8$kKUz{R80?RlkyFi1VR$i*_lp5a35JK?nH&<;9477ys^Zk3g zML9xIR(4I7q#%6DimmZZp4(1Q11QQ01VKP=ce}Z?Zs5Xk37K>XftHY!CzDR$tSI2= zvVz|3c2f`p#}#k_)o1HOhaJ79P<^NDIRu2(FtmS-8fY6e@cTuZAngH}bjqp#Aq0NE zXgwpeh8tiUjg9fs!B-?InM85qbKB~@wiiMOfh^~{79EQKke*vC_)IBmFH4rg zyUs6?6trH0Jo-gngDjb~9K0JjYf+@@y0!T6Zsb7s3i}N;I$d`ZdJ{N-`!#qb+zDVF zkCJaN`S7{ttFO}e2? zKa!$*@K`)vb|X;zVsDuji}T$2j)%ZRB4PdBek!vtzrds~I4u$*BO?HSp`oF&=;!Yx zz=IOo)kTLQ2<&FmP)Wz|M5Z!jNQ6V%W z##dj5fxb9++|q98I_<|mUmU*rIs{rm80d@JB39VCI)Q5lbe;BFa{%?i0C{iG`1Fjc zb9r7^-vC=LSq@usz|`z3$K`)%c?Y@H9y1`G^ykO_#3X;@(3enE=ZB)a zsH%o0@hraoWfZ>pIuJsjE~&OW$<*&$WpWuHA~irb@(Bw}bk@^l1s9G>&~+WR_c2Ts z0M`EUdRN|l@I<7B&w`K-$%*xJVB+yh0D14!;Z2{VQ@9Lp`_3cJV1Lx4VQG>S1krRz zQm`W4p=2^?0zl}TXw!d=_2lpCx{im>HLhXp>K_~IkD9U^w!&rsVC?>H726P9y?WJK zYrg*sY^?~B$wgN&%C6kGOX~*iPE3Nv1yq{0wl)*U$13>!BJNI1Vrktd_SmktGQde6 zK~!!7fQrNg6oP6;<+fepmYm?)p)W~6D=whYJbCg2z*ek6MMHOFShmONREl&ujq`1% zAP7Q9jR#6F0J|4BD0E#f+4!!80PB3!w1C2e7cQ0$cj-_y2ZZ>Y5}6XPv;lumNklbC9LK-07T-!EtwV9l7%ic;EY@jiN^KDo z7MdlYP`32qp%?M6z4c=0Z7F+^?PYJf3(_9;;6>U?iL@+&1?wN`pGIZDLXeo5OuCFN zRoq$HX7-T2@r@cYZxYjGHy;Q|Uf#U#`~C9Xn>X+G11eOgP@#W9g$fn^r+7Yh2i!1t z|E{TNY3sWvHsaoQKe)1m>mn-r<4?ctx$e>V^pG;nB~B8-2%>2l~S1`nw{+dq>>2?4aeZ~i8j%U zmWHZo=BU4zM*^!K8=uQtFWS?=tzYFtT+`A>B@+OEBgY9;RYOKgTQ61B zaO5}v0Hl%$Xj&SB_wSmHtmD*IRc+sTw47JJpaZl|Mh*?fpeSqb*3}}?-40dNtXHJF z9p1WHD9Rd!hGWQRX&f|Hd0_Pc*t7xI`T&4i|3C)}^o4)T>sPxhF*5cRM7>Z`GyxPO0YY3?T&HesjZSU{iAdKRZFnhTo46Jt}5v1JZB1m;J5=$ zp!#f|=(MBXDOBGn2TlQ@B?xV+8roJhd_K`8NJoD_Dw(i4KnQ`)CtBACEkVZ}aiY(n zC~GhbV~?YG^$#2YbOi=-3(N85dQ7e=*nGDQd8-<+@i{bzjff}Sz*|=f0Qgf~=Q7fX zK3(iG+XUWC1B4J5M(%xbRk3~7KHU{|J1idsHw$#=jZZIm2KvJ0%BF!cUb3eiEr0Ov zxrcwfhQnS*`i1KA>K9xCb~i!@fh^~S7M+U#kepq}drdLyZcCPf`>rpN04#Gjxo+QxuyV+d-6Mf`lPMw{OOa(XlXQ^;BJnae8b)C zG~nuS(}}7*##8c@mzsPVEVmmk?kPYQoqC(MYJ7F;yu*K^K@82~K+X>Wo`j1C@I;`KC zngfVEeT)>x@f_EI$jq_|p(SU$rllbs`+#UqhZVZcl;K>EJ`&S}3`JRkwpD)(QEY^= zn83`k>NqF@a5#WIg0e$zUe(aw>$j37$^q4(2^pg=7WWv;(-+4lLiDkd%?hC@G2Xgb z^!G-=6P9+%r8Xb>d!z8y)uO36fd1a7En|i4s}s1Uz@;{ywFb~A43LW!jZ93rI+y2# zjSaBTHIc|^p9GicQ22%{fz|F492ubz4&2bZw>T$E{vXziQVI$T&a65n+ zF9-sLhGR%26Ci|G`2vS^D9X0o)EodI#L8Nufe|-H?_*FrmSc%BuQ z7q;zdp&&*krfm5DIOa#y$qQU%h*ayrr*;$jT3a*@zpzAswaPGr-+4!rf zYVGZ|CnVK>6ogz#PNcgXqc0W#v;A`A$))X0*-MMo*wo|N002ovPDHLkV1mV~ Bt{ngX From b077645963457b7f3d169b2ec589a903cea6216f Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 29 May 2022 11:44:46 -0400 Subject: [PATCH 05/40] json momento --- .../Clothing/Head/Hardsuits/cburn.rsi/meta.json | 12 ------------ .../OuterClothing/Hardsuits/cburn.rsi/meta.json | 2 +- 2 files changed, 1 insertion(+), 13 deletions(-) diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json index 8decf1b6af8c..16f509fa99f2 100644 --- a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json +++ b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json @@ -23,10 +23,6 @@ "name": "equipped-head", "directions": 4 }, - { - "name": "equipped-head-light", - "directions": 4 - }, { "name": "equipped-head-unshaded", "directions": 4 @@ -39,10 +35,6 @@ "name": "inhand-left-unshaded", "directions": 4 }, - { - "name": "inhand-left-light", - "directions": 4 - }, { "name": "inhand-right", "directions": 4 @@ -50,10 +42,6 @@ { "name": "inhand-right-unshaded", "directions": 4 - }, - { - "name": "inhand-right-light", - "directions": 4 } ] } diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json index f2bcccc0c689..2cfc2220e1a7 100644 --- a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json +++ b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json @@ -1,7 +1,7 @@ { "version": 1, "license": "CC-BY-SA-3.0", - "copyright": "Taken from tgstation at commit https://github.com/tgstation/tgstation/commit/40d89d11ea4a5cb81d61dc1018b46f4e7d32c62a. Further modifications and derivate works (inhand-left and inhand-right) under same license.", + "copyright": "Made by EmoGarbage404", "size": { "x": 32, "y": 32 From 6aafc1381992af12717da830c014e4185a4a1e59 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 29 May 2022 19:33:52 -0400 Subject: [PATCH 06/40] nuke arm event --- .../GameTicking/Rules/ZombieRuleSystem.cs | 29 ++++++++++++------- .../game-presets/preset-zombies.ftl | 7 ++++- 2 files changed, 24 insertions(+), 12 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 975d9563385f..2cfb4f290a98 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -1,6 +1,7 @@ using System.Linq; using Content.Server.Chat.Managers; using Content.Server.Disease; +using Content.Server.Nuke; using Content.Server.Players; using Content.Server.RoundEnd; using Content.Server.Spawners.Components; @@ -32,6 +33,8 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly StationSystem _stationSystem = default!; [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; + [Dependency] private readonly NukeSystem _nukeSystem = default!; + [Dependency] private readonly NukeCodeSystem _nukeCodeSystem = default!; private const string PatientZeroPrototypeID = "PatientZero"; private const string InitialZombieVirusPrototype = "ZombieInfection"; @@ -67,17 +70,7 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) private void OnMobStateChanged(MobStateChangedEvent ev) { - if (!Enabled) - return; - - if (!_aliveNukeops.TryFirstOrNull(x => x.Key.OwnedEntity == ev.Entity, out var op)) return; - - _aliveNukeops[op.Value.Key] = op.Value.Key.CharacterDeadIC; - - if (_aliveNukeops.Values.All(x => !x)) - { - _roundEndSystem.EndRound(); - } + } private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) @@ -282,4 +275,18 @@ public override void Started() } public override void Ended() { } + + /// EVENTS + /// These are all the functions that handle midround events + /// that can occur during zombie mode + + private void UnlockNuke() + { + _chatManager.DispatchStationAnnouncement(Loc.GetString("zombie-nuke-armed-event", ("code",_nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); + foreach (var nuke in EntityManager.EntityQuery().ToList()) + { + if (nuke.DiskSlot.ContainerSlot != null) + nuke.DiskSlot.ContainerSlot.Insert(Spawn("NukeDisk", Transform(nuke.Owner).Coordinates)); + } + } } diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index df38c445f943..726a28974f6c 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -4,4 +4,9 @@ zombie-description = A virus able to create the undead has been unleashed unto t zombie-not-enough-ready-players = Not enough players readied up for the game! There were {$readyPlayersCount} players readied up out of {$minimumPlayers} needed. Can't start Zombies. zombie-no-one-ready = No players readied up! Can't start Zombies. -zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. \ No newline at end of file +#Patient 0 +zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. + +#EVENTS +#Nuke Event +zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. The code is {$code}. \ No newline at end of file From c47ebeacff19f0d1e1ca61206739a5a29324f6b6 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 29 May 2022 23:59:20 -0400 Subject: [PATCH 07/40] shuttle spawning --- .../GameTicking/Rules/ZombieRuleSystem.cs | 190 +++++++++--------- .../game-presets/preset-zombies.ftl | 9 +- 2 files changed, 95 insertions(+), 104 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 2cfb4f290a98..404fb4100283 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -3,10 +3,12 @@ using Content.Server.Disease; using Content.Server.Nuke; using Content.Server.Players; +using Content.Server.Roles; using Content.Server.RoundEnd; using Content.Server.Spawners.Components; using Content.Server.Station.Components; using Content.Server.Station.Systems; +using Content.Server.Traitor; using Content.Shared.CCVar; using Content.Shared.MobState; using Content.Shared.Roles; @@ -29,6 +31,7 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly IChatManager _chatManager = default!; [Dependency] private readonly IMapLoader _mapLoader = default!; [Dependency] private readonly IMapManager _mapManager = default!; + [Dependency] private readonly IPlayerManager _playerManager = default!; [Dependency] private readonly StationSpawningSystem _stationSpawningSystem = default!; [Dependency] private readonly StationSystem _stationSystem = default!; [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; @@ -75,70 +78,7 @@ private void OnMobStateChanged(MobStateChangedEvent ev) private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) { - if (!Enabled) - return; - - var list = new List(ev.Players); - var prefList = new List(); - - foreach (var player in list) - { - if (!ev.Profiles.ContainsKey(player.UserId)) - { - continue; - } - prefList.Add(player); //by default, zombies don't care whether or not you are command or nonantag crew - } - - var playersPerInfected = _cfg.GetCVar(CCVars.ZombiePlayersPerInfected); - var maxInfected = _cfg.GetCVar(CCVars.ZombieMaxInfected); - - var numInfected = Math.Max(1, - (int) Math.Min( - Math.Floor((double) ev.Players.Length / playersPerInfected), maxInfected)); - - for (var i = 0; i < numInfected; i++) - { - IPlayerSession zombie; //this isn't actually a zombie, but rather a patient 0. sue me for naming it shitty -emo - if (prefList.Count == 0) - { - if (list.Count == 0) - { - Logger.InfoS("preset", "Insufficient ready players to fill up with patient 0, stopping the selection."); - break; - } - zombie = _random.PickAndTake(list); - list.Remove(zombie); - Logger.InfoS("preset", "Insufficient preferred patient 0, picking at random."); - } - else - { - zombie = _random.PickAndTake(prefList); - list.Remove(zombie); - Logger.InfoS("preset", "Selected a preferred patient 0."); - } - - var mind = zombie.Data.ContentData()?.Mind; - if (mind == null) - { - Logger.ErrorS("preset", "Failed getting mind for picked patient 0."); - continue; - } - - DebugTools.AssertNotNull(mind.OwnedEntity); - - if (mind.OwnedEntity != null) - _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. - - if (mind.Session != null) - { - var messageWrapper = Loc.GetString("chat-manager-server-wrap-message"); - - // I went all the way to ChatManager.cs and all i got was this lousy T-shirt - _chatManager.ChatMessageToOne(Shared.Chat.ChatChannel.Server, Loc.GetString("zombie-patientzero-role-greeting"), - messageWrapper, default, false, mind.Session.ConnectedClient, Color.Plum); - } - } + InfectInitialPlayers(); } private void OnPlayersSpawning(RulePlayerSpawningEvent ev) @@ -147,41 +87,7 @@ private void OnPlayersSpawning(RulePlayerSpawningEvent ev) return; //these are staying here because i want the code for reference - // Between 1 and : needs at least n players per op. - /*var numInfected = Math.Max(1, - (int)Math.Min( - Math.Floor((double)ev.PlayerPool.Count / _cfg.GetCVar(CCVars.ZombiePlayersPerInfected)), _cfg.GetCVar(CCVars.ZombieMaxInfected))); - - _random.PickAndTake(ev.PlayerPool); - */ - /* - var map = "/Maps/infiltrator.yml"; - - var aabbs = _stationSystem.Stations.SelectMany(x => - Comp(x).Grids.Select(x => _mapManager.GetGridComp(x).Grid.WorldAABB)).ToArray(); - var aabb = aabbs[0]; - for (int i = 1; i < aabbs.Length; i++) - { - aabb.Union(aabbs[i]); - } - - var (_, gridId) = _mapLoader.LoadBlueprint(GameTicker.DefaultMap, map, new MapLoadOptions - { - Offset = aabb.Center + MathF.Max(aabb.Height / 2f, aabb.Width / 2f) * 2.5f - }); - - if (!gridId.HasValue) - { - Logger.ErrorS("NUKEOPS", $"Gridid was null when loading \"{map}\", aborting."); - foreach (var session in ops) - { - ev.PlayerPool.Add(session); - } - return; - } - - var gridUid = _mapManager.GetGridEuid(gridId.Value); // TODO: Loot table or something var commanderGear = _prototypeManager.Index("SyndicateCommanderGearFull"); @@ -271,22 +177,106 @@ private void OnStartAttempt(RoundStartAttemptEvent ev) public override void Started() { - _opsWon = false; + InfectInitialPlayers(); } public override void Ended() { } + /// + /// Infects the first players with the passive zombie virus. + /// + private void InfectInitialPlayers() + { + var playerList = _playerManager.ServerSessions.ToList(); + + if (playerList.Count == 0) + return; + + var playersPerInfected = _cfg.GetCVar(CCVars.ZombiePlayersPerInfected); + var maxInfected = _cfg.GetCVar(CCVars.ZombieMaxInfected); + + var numInfected = Math.Max(1, + (int) Math.Min( + Math.Floor((double) playerList.Count / playersPerInfected), maxInfected)); + + for (var i = 0; i < numInfected; i++) + { + if (playerList.Count == 0) + { + Logger.InfoS("preset", "Insufficient number of players. stopping selection."); + break; + } + IPlayerSession zombie = _random.PickAndTake(playerList); + playerList.Remove(zombie); + Logger.InfoS("preset", "Selected a patient 0."); + + var mind = zombie.Data.ContentData()?.Mind; + if (mind == null) + { + Logger.ErrorS("preset", "Failed getting mind for picked patient 0."); + continue; + } + + DebugTools.AssertNotNull(mind.OwnedEntity); + + mind.AddRole(new TraitorRole(mind, _prototypeManager.Index(PatientZeroPrototypeID))); + if (mind.OwnedEntity != null) + _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. + + if (mind.Session != null) + { + var messageWrapper = Loc.GetString("chat-manager-server-wrap-message"); + + // I went all the way to ChatManager.cs and all i got was this lousy T-shirt + _chatManager.ChatMessageToOne(Shared.Chat.ChatChannel.Server, Loc.GetString("zombie-patientzero-role-greeting"), + messageWrapper, default, false, mind.Session.ConnectedClient, Color.Plum); + } + } + } + /// EVENTS /// These are all the functions that handle midround events /// that can occur during zombie mode - + + /// + /// This event announces the nuke code and spawns + /// the disk inside of it. This is for round end + /// so the duplicated disks shouldn't really matter. + /// private void UnlockNuke() { _chatManager.DispatchStationAnnouncement(Loc.GetString("zombie-nuke-armed-event", ("code",_nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); foreach (var nuke in EntityManager.EntityQuery().ToList()) { if (nuke.DiskSlot.ContainerSlot != null) + { nuke.DiskSlot.ContainerSlot.Insert(Spawn("NukeDisk", Transform(nuke.Owner).Coordinates)); + } + + } + } + + /// + /// Spawns a shuttle a distance away from the main station + /// This code is 100% canibalized from nukies + /// idk how it works. -emo + /// + /// The file path to the map file + private void SpawnShuttle(string map) + { + _chatManager.DispatchStationAnnouncement(Loc.GetString("zombie-shuttle-call-event", ("code", _nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); + + var aabbs = _stationSystem.Stations.SelectMany(x => + Comp(x).Grids.Select(x => _mapManager.GetGridComp(x).Grid.WorldAABB)).ToArray(); + var aabb = aabbs[0]; + for (int i = 1; i < aabbs.Length; i++) + { + aabb.Union(aabbs[i]); } + + var (_, gridId) = _mapLoader.LoadBlueprint(GameTicker.DefaultMap, map, new MapLoadOptions + { + Offset = aabb.Center + MathF.Max(aabb.Height / 2f, aabb.Width / 2f) * 2.5f + }); } } diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index 726a28974f6c..0fc568815c4a 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -4,9 +4,10 @@ zombie-description = A virus able to create the undead has been unleashed unto t zombie-not-enough-ready-players = Not enough players readied up for the game! There were {$readyPlayersCount} players readied up out of {$minimumPlayers} needed. Can't start Zombies. zombie-no-one-ready = No players readied up! Can't start Zombies. -#Patient 0 zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. -#EVENTS -#Nuke Event -zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. The code is {$code}. \ No newline at end of file +zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. A disk has been automatically teleported inside of it. The code to detonate the device is: {$code}. +zombie-end-nuke-armed-event-fail = The nuke was not detonated. +zombie-end-nuke-armed-eveent-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. + +zombie-shuttle-call-event = In response to the zombie outbreak, we have dispatched a shuttle containing an emergency team to your station. \ No newline at end of file From 12d08aa4d0c07c1c72361956718258d46240582f Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Mon, 30 May 2022 00:04:49 -0400 Subject: [PATCH 08/40] mini --- Content.Server/GameTicking/Rules/ZombieRuleSystem.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 404fb4100283..90c2eb37054d 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -177,6 +177,7 @@ private void OnStartAttempt(RoundStartAttemptEvent ev) public override void Started() { + //this technically will run twice with zombies on roundstart, but it doesn't matter because it fails instantly InfectInitialPlayers(); } From 4c218ae03bb67c5fb46776bcb202a3c7a53ead4c Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sat, 28 May 2022 14:51:19 -0400 Subject: [PATCH 09/40] beginning --- .../GameTicking/Rules/ZombieRuleSystem.cs | 282 ++++++++++++++++++ Content.Shared/CCVar/CCVars.cs | 13 + .../game-presets/preset-zombies.ftl | 7 + Resources/Prototypes/Roles/Antags/zombie.yml | 6 + Resources/Prototypes/game_presets.yml | 11 + Resources/Prototypes/game_rules.yml | 3 + 6 files changed, 322 insertions(+) create mode 100644 Content.Server/GameTicking/Rules/ZombieRuleSystem.cs create mode 100644 Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl create mode 100644 Resources/Prototypes/Roles/Antags/zombie.yml diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs new file mode 100644 index 000000000000..b04bd1be8c6d --- /dev/null +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -0,0 +1,282 @@ +using System.Linq; +using Content.Server.Chat.Managers; +using Content.Server.Disease; +using Content.Server.Players; +using Content.Server.RoundEnd; +using Content.Server.Spawners.Components; +using Content.Server.Station.Components; +using Content.Server.Station.Systems; +using Content.Shared.CCVar; +using Content.Shared.MobState; +using Content.Shared.Roles; +using Robust.Server.Maps; +using Robust.Server.Player; +using Robust.Shared.Configuration; +using Robust.Shared.Map; +using Robust.Shared.Physics.Collision.Shapes; +using Robust.Shared.Prototypes; +using Robust.Shared.Random; +using Robust.Shared.Utility; + +namespace Content.Server.GameTicking.Rules; + +public sealed class ZombieRuleSystem : GameRuleSystem +{ + [Dependency] private readonly IPrototypeManager _prototypeManager = default!; + [Dependency] private readonly IRobustRandom _random = default!; + [Dependency] private readonly IConfigurationManager _cfg = default!; + [Dependency] private readonly IChatManager _chatManager = default!; + [Dependency] private readonly IMapLoader _mapLoader = default!; + [Dependency] private readonly IMapManager _mapManager = default!; + [Dependency] private readonly StationSpawningSystem _stationSpawningSystem = default!; + [Dependency] private readonly StationSystem _stationSystem = default!; + [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; + [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; + + private const string PatientZeroPrototypeID = "PatientZero"; + + private Dictionary _aliveNukeops = new(); + private bool _opsWon; + + public override string Prototype => "Zombie"; + + public override void Initialize() + { + base.Initialize(); + + SubscribeLocalEvent(OnStartAttempt); + //SubscribeLocalEvent(OnPlayersSpawning); + //SubscribeLocalEvent(OnMobStateChanged); + SubscribeLocalEvent(OnRoundEndText); + SubscribeLocalEvent(OnJobAssigned); + } + + private void OnRoundEndText(RoundEndTextAppendEvent ev) + { + if (!Enabled) + return; + + ev.AddLine("ZOMBIE ROUND OVER TESTETEST"); + ev.AddLine(Loc.GetString("nukeops-list-start")); + foreach (var nukeop in _aliveNukeops) + { + ev.AddLine($"- {nukeop.Key.Session?.Name}"); + } + } + + private void OnMobStateChanged(MobStateChangedEvent ev) + { + if (!Enabled) + return; + + if (!_aliveNukeops.TryFirstOrNull(x => x.Key.OwnedEntity == ev.Entity, out var op)) return; + + _aliveNukeops[op.Value.Key] = op.Value.Key.CharacterDeadIC; + + if (_aliveNukeops.Values.All(x => !x)) + { + _roundEndSystem.EndRound(); + } + } + + private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) + { + if (!Enabled) + return; + + var list = new List(ev.Players); + var prefList = new List(); + + foreach (var player in list) + { + if (!ev.Profiles.ContainsKey(player.UserId)) + { + continue; + } + prefList.Add(player); //by default, zombies don't care whether or not you are command or nonantag crew + } + + var playersPerInfected = _cfg.GetCVar(CCVars.ZombiePlayersPerInfected); + var maxInfected = _cfg.GetCVar(CCVars.ZombieMaxInfected); + + var numInfected = Math.Max(1, + (int) Math.Min( + Math.Floor((double) ev.Players.Length / playersPerInfected), maxInfected)); + + for (var i = 0; i < numInfected; i++) + { + IPlayerSession zombie; //this isn't actually a zombie, but rather a patient 0. sue me for naming it shittily -emo + if (prefList.Count == 0) + { + if (list.Count == 0) + { + Logger.InfoS("preset", "Insufficient ready players to fill up with patient 0, stopping the selection."); + break; + } + zombie = _random.PickAndTake(list); + list.Remove(zombie); + Logger.InfoS("preset", "Insufficient preferred patient 0, picking at random."); + } + else + { + zombie = _random.PickAndTake(prefList); + list.Remove(zombie); + Logger.InfoS("preset", "Selected a preferred patient 0."); + } + + var mind = zombie.Data.ContentData()?.Mind; + if (mind == null) + { + Logger.ErrorS("preset", "Failed getting mind for picked patient 0."); + continue; + } + + DebugTools.AssertNotNull(mind.OwnedEntity); + + if(mind.OwnedEntity != null) + _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, "ZombieInfection"); + + mind.Briefing = Loc.GetString("zombie-patientzero-role-greeting"); + } + + foreach (var player in ev.Players) + { + if (player.AttachedEntity != null) + _diseaseSystem.TryAddDisease(player.AttachedEntity.Value, "ZombieInfection");//change this once zombie refactor is in. + } + } + + private void OnPlayersSpawning(RulePlayerSpawningEvent ev) + { + if (!Enabled) + return; + + // Between 1 and : needs at least n players per op. + /*var numInfected = Math.Max(1, + (int)Math.Min( + Math.Floor((double)ev.PlayerPool.Count / _cfg.GetCVar(CCVars.ZombiePlayersPerInfected)), _cfg.GetCVar(CCVars.ZombieMaxInfected))); + + _random.PickAndTake(ev.PlayerPool); + */ + + /* + var map = "/Maps/infiltrator.yml"; + + var aabbs = _stationSystem.Stations.SelectMany(x => + Comp(x).Grids.Select(x => _mapManager.GetGridComp(x).Grid.WorldAABB)).ToArray(); + var aabb = aabbs[0]; + for (int i = 1; i < aabbs.Length; i++) + { + aabb.Union(aabbs[i]); + } + + var (_, gridId) = _mapLoader.LoadBlueprint(GameTicker.DefaultMap, map, new MapLoadOptions + { + Offset = aabb.Center + MathF.Max(aabb.Height / 2f, aabb.Width / 2f) * 2.5f + }); + + if (!gridId.HasValue) + { + Logger.ErrorS("NUKEOPS", $"Gridid was null when loading \"{map}\", aborting."); + foreach (var session in ops) + { + ev.PlayerPool.Add(session); + } + return; + } + + var gridUid = _mapManager.GetGridEuid(gridId.Value); + + // TODO: Loot table or something + var commanderGear = _prototypeManager.Index("SyndicateCommanderGearFull"); + var starterGear = _prototypeManager.Index("SyndicateOperativeGearFull"); + var medicGear = _prototypeManager.Index("SyndicateOperativeMedicFull"); + + var spawns = new List(); + + // Forgive me for hardcoding prototypes + foreach (var (_, meta, xform) in EntityManager.EntityQuery(true)) + { + if (meta.EntityPrototype?.ID != "SpawnPointNukies" || xform.ParentUid != gridUid) continue; + + spawns.Add(xform.Coordinates); + } + + if (spawns.Count == 0) + { + spawns.Add(EntityManager.GetComponent(gridUid).Coordinates); + Logger.WarningS("nukies", $"Fell back to default spawn for nukies!"); + } + + // TODO: This should spawn the nukies in regardless and transfer if possible; rest should go to shot roles. + for (var i = 0; i < ops.Length; i++) + { + string name; + StartingGearPrototype gear; + + switch (i) + { + case 0: + name = $"Commander"; + gear = commanderGear; + break; + case 1: + name = $"Operator #{i}"; + gear = medicGear; + break; + default: + name = $"Operator #{i}"; + gear = starterGear; + break; + } + + var session = ops[i]; + var newMind = new Mind.Mind(session.UserId) + { + CharacterName = name + }; + newMind.ChangeOwningPlayer(session.UserId); + + var mob = EntityManager.SpawnEntity("MobHuman", _random.Pick(spawns)); + EntityManager.GetComponent(mob).EntityName = name; + + newMind.TransferTo(mob); + _stationSpawningSystem.EquipStartingGear(mob, gear, null); + + _aliveNukeops.Add(newMind, true); + + GameTicker.PlayerJoinGame(session); + }*/ + } + + private void OnStartAttempt(RoundStartAttemptEvent ev) + { + if (!Enabled) + return; + + //Uncomment this once im done local testing + /* + var minPlayers = _cfg.GetCVar(CCVars.ZombieMinPlayers); + if (!ev.Forced && ev.Players.Length < minPlayers) + { + _chatManager.DispatchServerAnnouncement(Loc.GetString("zombie-not-enough-ready-players", ("readyPlayersCount", ev.Players.Length), ("minimumPlayers", minPlayers))); + ev.Cancel(); + return; + } + + if (ev.Players.Length == 0) + { + _chatManager.DispatchServerAnnouncement(Loc.GetString("zombie-no-one-ready")); + ev.Cancel(); + return; + } + //*/ + } + + public override void Started() + { + _opsWon = false; + } + + public override void Ended() { } +} diff --git a/Content.Shared/CCVar/CCVars.cs b/Content.Shared/CCVar/CCVars.cs index 6f4d1fc8fd64..fdafe9e496cb 100644 --- a/Content.Shared/CCVar/CCVars.cs +++ b/Content.Shared/CCVar/CCVars.cs @@ -286,6 +286,19 @@ public static readonly CVarDef public static readonly CVarDef NukeopsPlayersPerOp = CVarDef.Create("nukeops.players_per_op", 5); + /* + * Zombie + */ + + public static readonly CVarDef ZombieMinPlayers = + CVarDef.Create("zombie.min_players", 25); + + public static readonly CVarDef ZombieMaxInfected = + CVarDef.Create("zombie.max_infected", 4); + + public static readonly CVarDef ZombiePlayersPerInfected = + CVarDef.Create("zombie.players_per_infected", 7); + /* * Console */ diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl new file mode 100644 index 000000000000..df38c445f943 --- /dev/null +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -0,0 +1,7 @@ +zombie-title = Zombies +zombie-description = A virus able to create the undead has been unleashed unto the station! Work with your crewmates to contain the outbreak and survive. + +zombie-not-enough-ready-players = Not enough players readied up for the game! There were {$readyPlayersCount} players readied up out of {$minimumPlayers} needed. Can't start Zombies. +zombie-no-one-ready = No players readied up! Can't start Zombies. + +zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. \ No newline at end of file diff --git a/Resources/Prototypes/Roles/Antags/zombie.yml b/Resources/Prototypes/Roles/Antags/zombie.yml new file mode 100644 index 000000000000..d69d8f24ac7b --- /dev/null +++ b/Resources/Prototypes/Roles/Antags/zombie.yml @@ -0,0 +1,6 @@ +- type: antag + id: PatientZero + name: "Patient 0" + antagonist: true + setPreference: false + objective: "Once you turn, infect as many other crew members as possible" \ No newline at end of file diff --git a/Resources/Prototypes/game_presets.yml b/Resources/Prototypes/game_presets.yml index 8a088044d41b..3851d49feb9f 100644 --- a/Resources/Prototypes/game_presets.yml +++ b/Resources/Prototypes/game_presets.yml @@ -78,3 +78,14 @@ showInVote: false rules: - Nukeops + +- type: gamePreset + id: Zombie + alias: + - zombie + - zombies + name: zombie-title + description: zombie-description + showInVote: true + rules: + - Zombie diff --git a/Resources/Prototypes/game_rules.yml b/Resources/Prototypes/game_rules.yml index dff36b9cdaa1..6e57855ccfda 100644 --- a/Resources/Prototypes/game_rules.yml +++ b/Resources/Prototypes/game_rules.yml @@ -24,3 +24,6 @@ - type: gameRule id: Secret + +- type: gameRule + id: Zombie From 65a8ef48fd92e80e6eb278ccce9279013e5534f3 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sat, 28 May 2022 20:34:30 -0400 Subject: [PATCH 10/40] tweakies --- .../GameTicking/Rules/ZombieRuleSystem.cs | 17 +++++++---------- 1 file changed, 7 insertions(+), 10 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index b04bd1be8c6d..bb4db16f9dc6 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -34,6 +34,7 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; private const string PatientZeroPrototypeID = "PatientZero"; + private const string InitialZombieVirusPrototype = "ZombieInfection"; private Dictionary _aliveNukeops = new(); private bool _opsWon; @@ -105,7 +106,7 @@ private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) for (var i = 0; i < numInfected; i++) { - IPlayerSession zombie; //this isn't actually a zombie, but rather a patient 0. sue me for naming it shittily -emo + IPlayerSession zombie; //this isn't actually a zombie, but rather a patient 0. sue me for naming it shitty -emo if (prefList.Count == 0) { if (list.Count == 0) @@ -133,16 +134,11 @@ private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) DebugTools.AssertNotNull(mind.OwnedEntity); - if(mind.OwnedEntity != null) - _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, "ZombieInfection"); + if (mind.OwnedEntity != null) + _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. - mind.Briefing = Loc.GetString("zombie-patientzero-role-greeting"); - } - - foreach (var player in ev.Players) - { - if (player.AttachedEntity != null) - _diseaseSystem.TryAddDisease(player.AttachedEntity.Value, "ZombieInfection");//change this once zombie refactor is in. + if (mind.Session != null) + _chatManager.DispatchServerMessage(mind.Session, Loc.GetString("zombie-patientzero-role-greeting")); } } @@ -150,6 +146,7 @@ private void OnPlayersSpawning(RulePlayerSpawningEvent ev) { if (!Enabled) return; + //these are staying here because i want the code for reference // Between 1 and : needs at least n players per op. /*var numInfected = Math.Max(1, From e74ba8fc60e05f42863e54e40ca44f7aa8bc1a5a Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 29 May 2022 09:33:44 -0400 Subject: [PATCH 11/40] cburn + more stuff --- Content.Server/Chat/Managers/ChatManager.cs | 6 +++- Content.Server/Chat/Managers/IChatManager.cs | 2 +- .../GameTicking/Rules/ZombieRuleSystem.cs | 8 ++++- .../Clothing/OuterClothing/hardsuits.yml | 33 ++++++++++++++++++ .../Roles/Jobs/Fun/misc_startinggear.yml | 20 +++++++++++ .../cburn.rsi/equipped-OUTERCLOTHING.png | Bin 0 -> 2329 bytes .../Hardsuits/cburn.rsi/icon.png | Bin 0 -> 1265 bytes .../Hardsuits/cburn.rsi/inhand-left.png | Bin 0 -> 1247 bytes .../Hardsuits/cburn.rsi/inhand-right.png | Bin 0 -> 1306 bytes .../Hardsuits/cburn.rsi/meta.json | 26 ++++++++++++++ 10 files changed, 92 insertions(+), 3 deletions(-) create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/icon.png create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/inhand-left.png create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/inhand-right.png create mode 100644 Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json diff --git a/Content.Server/Chat/Managers/ChatManager.cs b/Content.Server/Chat/Managers/ChatManager.cs index d62b38fcee5d..d6bcfb3214f4 100644 --- a/Content.Server/Chat/Managers/ChatManager.cs +++ b/Content.Server/Chat/Managers/ChatManager.cs @@ -213,7 +213,7 @@ private void SendAdminChat(IPlayerSession player, string message) #region Utility - public void ChatMessageToOne(ChatChannel channel, string message, string messageWrap, EntityUid source, bool hideChat, INetChannel client) + public void ChatMessageToOne(ChatChannel channel, string message, string messageWrap, EntityUid source, bool hideChat, INetChannel client, Color? colorOverride = null) { var msg = new MsgChatMessage(); msg.Channel = channel; @@ -221,6 +221,10 @@ public void ChatMessageToOne(ChatChannel channel, string message, string message msg.MessageWrap = messageWrap; msg.SenderEntity = source; msg.HideChat = hideChat; + if (colorOverride != null) + { + msg.MessageColorOverride = colorOverride.Value; + } _netManager.ServerSendMessage(msg, client); } diff --git a/Content.Server/Chat/Managers/IChatManager.cs b/Content.Server/Chat/Managers/IChatManager.cs index 76a525e6f752..d87eef8cf6c8 100644 --- a/Content.Server/Chat/Managers/IChatManager.cs +++ b/Content.Server/Chat/Managers/IChatManager.cs @@ -33,7 +33,7 @@ void DispatchStationAnnouncement(string message, string sender = "CentComm", boo void SendAdminAnnouncement(string message); void ChatMessageToOne(ChatChannel channel, string message, string messageWrap, EntityUid source, bool hideChat, - INetChannel client); + INetChannel client, Color? colorOverride = null); void ChatMessageToMany(ChatChannel channel, string message, string messageWrap, EntityUid source, bool hideChat, List clients); void ChatMessageToAll(ChatChannel channel, string message, string messageWrap, Color? colorOverride = null); diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index bb4db16f9dc6..975d9563385f 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -138,7 +138,13 @@ private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. if (mind.Session != null) - _chatManager.DispatchServerMessage(mind.Session, Loc.GetString("zombie-patientzero-role-greeting")); + { + var messageWrapper = Loc.GetString("chat-manager-server-wrap-message"); + + // I went all the way to ChatManager.cs and all i got was this lousy T-shirt + _chatManager.ChatMessageToOne(Shared.Chat.ChatChannel.Server, Loc.GetString("zombie-patientzero-role-greeting"), + messageWrapper, default, false, mind.Session.ConnectedClient, Color.Plum); + } } } diff --git a/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml b/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml index d30245f7e550..7cfda5565f85 100644 --- a/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml +++ b/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml @@ -568,3 +568,36 @@ resistance: 0.3 - type: ToggleableClothing clothingPrototype: ClothingHeadHelmetHardsuitSyndieElite + +- type: entity + parent: ClothingOuterHardsuitBase + id: ClothingOuterHardsuitCBURN + name: CBURN exosuit + description: A lightweight yet strong exosuit used for special cleanup operations. + components: + - type: Sprite + sprite: Clothing/OuterClothing/Hardsuits/cburn.rsi + - type: Clothing + sprite: Clothing/OuterClothing/Hardsuits/cburn.rsi + - type: PressureProtection + highPressureMultiplier: 0.02 + lowPressureMultiplier: 1000 + - type: ClothingSpeedModifier + walkModifier: 1.0 + sprintModifier: 1.0 + - type: TemperatureProtection + coefficient: 0.001 + - type: Armor + modifiers: + coefficients: + Blunt: 0.7 + Slash: 0.7 + Piercing: 0.6 + Heat: 0.05 + Cold: 0.1 + Shock: 0.1 + Radiation: 0.1 + - type: ExplosionResistance + resistance: 0.7 + - type: ToggleableClothing + clothingPrototype: ClothingHeadHelmetHardsuitSyndieElite diff --git a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml index 36e88d4679f7..0e0ea06f853b 100644 --- a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml +++ b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml @@ -136,3 +136,23 @@ innerclothingskirt: ClothingUniformJumpskirtOperative satchel: ClothingBackpackDuffelSyndicateOperativeMedic duffelbag: ClothingBackpackDuffelSyndicateOperativeMedic + +#CBURN Unit Gear - Full Kit +- type: startingGear + id: CBURNGear + equipment: + jumpsuit: ClothingUniformJumpsuitColorBrown + back: ClothingBackpack + mask: ClothingMaskGas + eyes: ClothingEyesGlassesSunglasses + ears: ClothingHeadsetService + gloves: ClothingHandsGlovesFingerless + outerClothing: ClothingOuterHardsuitCBURN + shoes: ClothingShoesBootsJack + id: CentcomPDA + pocket1: DoubleEmergencyOxygenTankFilled + pocket2: LaserGun + belt: ClothingBeltBandolier + innerclothingskirt: ClothingUniformJumpsuitColorBrown + satchel: ClothingBackpackSatchel + duffelbag: ClothingBackpackDuffel \ No newline at end of file diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png new file mode 100644 index 0000000000000000000000000000000000000000..e400e4189193e9e7277ddb06ce35568344fe9dc6 GIT binary patch literal 2329 zcmV+!3Fh{RP)EX>4Tx04R}tkv&MmKpe$iQ?()$1v`j1WN4i%h>AFB6^c+H)C#RSm|XfHG-*gu zTpR`0f`cE6RR;BL;+afkw@7zKZ37qAElt@2E_Z;zCqp)6R|?V;3I*W(jJ_!c4BP@et6p!-eVjf38R{x^0~{Oz zBSp$y^Lcl7dvE`qY4-O6ZWD5)cX)k&000M2NklbC9LK-07T-!EtwV9l z7%ic;EY@jiN^KDo7MdlYP`32qp%?M6z4c=0Z7F+^?PYJf3(_9;;6>U?iL@+&1?wN` zpGIZDLXeo5OuCFNRoq$HX7-T2@r@cYZxYjGHy;Q|Uf#U#`~C9Xn>X+G11eOgP@zJF z3KjmRcs_Rr+%S0muBmBh>$@m6;@)>ZxUz-oA}ajjPrvTD?#}I7W-%S%(a(n)eaDpt z`oiY>ng(RFG#bQ4n-lKbzGc$#qkm`c;NkOis~;Pm%Udtn)4{D@MoU{SRn>6hH~|2pk_l*98iV)mnvSgF)K^t)-+Hv1SHGYGv`_j88is~r$Y^OCG*@|G^#Rzl0oeKgfLs4S2MqLu&FfdYEHPcz zK?s2)`O)7SMWnkO{k>60k{^T+=(=uo>iX3#4D^MI8U+J=VKa2L(bA8{7XZLAmX_1+ z^mkR&5IWoFNWb6+NF@`v)aJwZ^pXbv48y?F*#(SDOkrNrF)}fQr?U$%3Y$;&%0YH-ch;+B($Z>*5cRM7>Z`GyxPO0YY3?T&HesjZSU{iAdKRZFnhTo46Jt}5v1 zJZB1m;J5=$p!#f|=(MBXDOBGn2TlQ@B?xV+8roJhd_K`8NJl^_nXo!Q2!YQhTGt3I zLB}0&qR*lzYcLFBkE40@4;%q>1qN~p%kk!VOs*=}e76mGs~WNKIW&lkh$r5_TUQGJ z_)}fyGSZ1YUFPcL}}`oiYQrhzkF zvZo#`fAH|RhrNcwUPthtOsTmyDDLI{B@=Y|%YivW9)N~kzfz5Z@+--6@fNn8E zQa#2#y{9&^CENNQL`bR!y~XKAVd-0Cx{fiF62$wO2BbE! zm|0c<05i)fQX5&kuW5kL60~huO9|DdTC6_plN)_U4(RDTXGWq?YiGuu1_8MvDf$c^ ziAGEA1gc-?F7tX}j$7aH6c~-gtk1hoW#;GRneut3O=56x5CCxR-o29O=YETU2S*M# zXlGT*UEjY|ze0ry6)IGy@ZW@c6LIJEEfXj%CSPjUu=#$W`-9-BOvB*7PDuK5I)XKv z?H7*|99N{qvxgq3jqGP}#BRg)>yuL_IDQzSLeXnGVKEu7#p?&}-!%{03DkJ{k4Jkt ztlyfN1Bg9+j1*r6C^sfM`#L6}rxp;areD64QhXMOlNkRSi*W zgtC~x%(Ch@C<1UefIfnF$dptS~!PcJ!ckNX^(jRsQ;!@$k1%LqyJyv=bFlIn4@>#~)QL181-Ja9XJ z8ZQU}hK6HEB@-ZoSos2nbtuZV-P9ZaA;ijBqk$1ON8|jFjAMRV%zk8I3fDqAad@5; zm>0I~YoQ=UCZ=rp066AH)yWH7ZE~#vv&uT;8hg%wc*d8T|D$7&17AW_oga$wqN*Ai z#0&WTmmzrTYC#Brx}w_Z#1p@BwaMjxkW>%h*ayrr*;$jT3a*@zpzAswaPGr-+4!rf zYVGZ|CnVK>6ogz#PNcgXqc0W#+)M zJHmK;!Bvj3t8nhhrh!MJW1x8f<)*c@)dX_63O=8RN26m{*)$4WwlA(6aK=jzmRkX! zEO`O>pxR-%b>F-tC%6viOOoHp3n(`)U%mveldDkH6d9J?xjN+{nM~qx>sbhbP?YgN z5e{IV1wI$Lt{3fmS5ttE$scxJz>PqbqEP@a4>MXT%d+Rh z7uhVEt57Vi9bk{i^W_Clc=7{S*j#}feRuo=$(17s#ii?j00000NkvXXu0mjf_Gnu^ literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/icon.png b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..8d7c6be6a656a20cbf99d19edc0e9022fb1ea8b5 GIT binary patch literal 1265 zcmVEX>4Tx04R}tkv&MmKpe$iQ?()$1&fF{WT;LSL`5963Pq?8YK2xEOfLNpnlvOS zE{=k0!NHHks)LKOt`4q(Aou~|=H{g6A|?JWDYS_3;J6>}?mh0_0Ya_BG^=e4&~)2O zCE{WxyCQ~O5k@aM(2tPJEMr!ZlJFg0_XzOyF2=L`&;2>N)ttqEfJi*U4AUlFC!X50 z4bJ<-5muB{;&b9rlP*a7$aTfzH_io@1)do()2TV)2(egbVWovx(bR}1iKD8fQ@)V# zSmnIMSu0goAMvPXS6bmWZkNfxsUB5&wg`Uwzx2Cnp`zgz>RKS{4P zwdfJhvkhEaH#KDsxZD8-o($QPT`5RY$mfCgGy0}1(02=Tt$MvR_Hp_Eq^Yaq4RCM> zj1(w)&F9^nt-bwwrqSOI3T<+IV#RYk0009hNkl(ERjs>`t5gW-Cgn=6&hmx)Sqoo^)o7qeeY^*NL$ODBJB1 zde_(H1gaKwE5(|fmz;3ShZ>x1OeZ_dQA`n2q8E;br3=j1OdzlD!Y3Lt5yx| zPJ1BdSY4nXgy4(MdIhPF&fMYa@4k)AF_HksIYZMlD%+dkTxNksAEvN7ZPJ-LQHPUX#r^5Mys;fvfBHP(x)Rrw zRCf0g_hx$zJV-4t^VTOlKgG;jp9iT00PfB9icqatfBJm#eW0?tcY#C*!SZs?TE{sf zm0ALz^Xm1$H4_QwhyC-POac4fSd6B71^CiqT|dV9E3RACrQ>)1 b1;@o-Ket`~k=83300000NkvXXu0mjf0gYo+ literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/inhand-left.png b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/inhand-left.png new file mode 100644 index 0000000000000000000000000000000000000000..9071444e11964d9c0e0531f1d82376d24592a1c1 GIT binary patch literal 1247 zcmV<51R(o~P)EX>4Tx04R}tkv&MmKpe$iQ%j3f9oj*}AwzYtAS&XhRVYG*P%E_RU~>J0CJjl7 zi=*ILaPVWX>fqw6tAnc`2!4RLxj8AiNQwVT3N2zhIPS;0dyl(!fY7Wm)$ADuRLwHd z$%L5At%|`{gb_hMLI}vr)aN8A1<&zy4NMaF7kRU=q9TikzAx^7CiitGsCp`Q^j$a~|LaquJ zITlcZ3fb|4|H1EW&En*Qn-op}ffw8U7y*L2K&xTf-^aGyIsyF8z?IhV*P6i0C+Urj z7CQn4wtDJa?(N?*?f!lM{sVG&@SkWa0009PNkl9@!kVL5ClOG1VIo4K@bE%5dJ5uID_T$ zc>o^XyWIpheC(vvzP^6*uGRj(&G`8EclCwoToXWRAKT6XaQ@O&E1%DQqv@8|4X8ZN zH9fCFsa$2i&Jt*!UBi7ij*B}ovEuzI&vVUZul#T7_iWGNj!al_8?Y+QV1?;c;~mE( zSb9gGeS)QTIF8G+SAOTouB5lq4T`fx0_{_rEn=q|q4ZIR)d1=hR=*Db=L0oIV1nxC3T}M!5f^z|nnsJ9YP;6d2pFH&h2Q zLn8no4+`6d0Y61xG=dViHtoWC|@DWy8^aafAF#>~9O zwL6cjnR$<*uJxjsK#vUY79pD+09vKDxUy#XM^gK#1GGm&ujq*Z%csMr(^sul`=aa> zu^Vu9@J30IXihG)JIIWdO;8bK@bE%5ClOGgq4VWRX9$*-b?%$ zQ5Q^mvm}-v#DG8DfIrPYVL&$-4A@z&-@F^CFNquhUw7WNvm8Hi zFw(MlA`PHkVeai4CJyZG`rJS=4FHrEX>4Tx04R}tkv&MmKpe$iQ%j3f9oj*}AwzYtAS&XhRVYG*P%E_RU~>J0CJjl7 zi=*ILaPVWX>fqw6tAnc`2!4RLxj8AiNQwVT3N2zhIPS;0dyl(!fY7Wm)$ADuRLwHd z$%L5At%|`{gb_hMLI}vr)aN8A1<&zy4NMaF7kRU=q9TikzAx^7CiitGsCp`Q^j$a~|LaquJ zITlcZ3fb|4|H1EW&En*Qn-op}ffw8U7y*L2K&xTf-^aGyIsyF8z?IhV*P6i0C+Urj z7CQn4wtDJa?(N?*?f!lM{sVG&@SkWa0009~Nkl1o^MNh?pUOWUr&{GcLVRMiy0kd6- z2VqMhVKeWtE+~ZXRu-p+^3}*E}CsW@q*fzj@|;-x=l|5JCtcgb+dqA%qY@ z93)=tN-C8C;L-g%5x@^WUGm)fn}6N&+~>~3#6%Aw?wre)UR;O(j0w>?0l<~3*S%CK z)s#8b_$TXsFGSielg$-*bpK9NFd^Tc80Oy1%MlF)+i#5r1S2&FwqkElN|Es6gqsDdwHzvc!Oy?`QTP4*J`2GC&bt{(${`G-%u@nZqjTC`urTFdycfcb|{ntt4mT>jH~h;P4CoYq6z=5Hzh zRQiuniYqtfJ*8B&9}S9(DY3Mc=f>T~-qKp0j48GKZp#AX-$25T1C?d|&E5prmru8oI%eo zgb+dqA%qY@h`rZWQ(cW(O?|b~>V{{lxxhxPZ;2fsO*2C~vE7l`%UkDr@!y|x3)o4) zIx4^*OpxqUM_piUb|$)g>l$&LK Date: Sun, 29 May 2022 11:37:23 -0400 Subject: [PATCH 12/40] cburn outfit --- .../Clothing/Head/hardsuit-helmets.yml | 51 +++++++++++++++ .../Clothing/OuterClothing/hardsuits.yml | 2 +- .../Roles/Jobs/Fun/misc_startinggear.yml | 3 +- .../cburn.rsi/equipped-head-unshaded.png | Bin 0 -> 162 bytes .../Hardsuits/cburn.rsi/equipped-head.png | Bin 0 -> 623 bytes .../Head/Hardsuits/cburn.rsi/icon-flash.png | Bin 0 -> 652 bytes .../Hardsuits/cburn.rsi/icon-unshaded.png | Bin 0 -> 141 bytes .../Head/Hardsuits/cburn.rsi/icon.png | Bin 0 -> 408 bytes .../cburn.rsi/inhand-left-unshaded.png | Bin 0 -> 465 bytes .../Head/Hardsuits/cburn.rsi/inhand-left.png | Bin 0 -> 519 bytes .../cburn.rsi/inhand-right-unshaded.png | Bin 0 -> 415 bytes .../Head/Hardsuits/cburn.rsi/inhand-right.png | Bin 0 -> 527 bytes .../Hardsuits/cburn.rsi/light-overlay.png | Bin 0 -> 333 bytes .../Head/Hardsuits/cburn.rsi/meta.json | 59 ++++++++++++++++++ .../cburn.rsi/equipped-OUTERCLOTHING.png | Bin 2329 -> 2333 bytes 15 files changed, 113 insertions(+), 2 deletions(-) create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/equipped-head-unshaded.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/equipped-head.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon-flash.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon-unshaded.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-left-unshaded.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-left.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right-unshaded.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/light-overlay.png create mode 100644 Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json diff --git a/Resources/Prototypes/Entities/Clothing/Head/hardsuit-helmets.yml b/Resources/Prototypes/Entities/Clothing/Head/hardsuit-helmets.yml index 3d38af729fe9..81fff225c055 100644 --- a/Resources/Prototypes/Entities/Clothing/Head/hardsuit-helmets.yml +++ b/Resources/Prototypes/Entities/Clothing/Head/hardsuit-helmets.yml @@ -404,3 +404,54 @@ Piercing: 0.8 Heat: 0.2 Radiation: 0.5 + +- type: entity + parent: ClothingHeadHardsuitWithLightBase + id: ClothingHeadHelmetCBURN + noSpawn: true + name: syndicate elite helmet + description: A pressure resistant and fireproof hood worn by special cleanup units. + components: + - type: Sprite + netsync: false + sprite: Clothing/Head/Hardsuits/cburn.rsi + layers: + - state: icon + - state: icon-unshaded + shader: unshaded + - state: light-overlay + visible: false + shader: unshaded + map: [ "light" ] + - type: Clothing + clothingVisuals: + head: + - state: equipped-head + - state: equipped-head-unshaded + shader: unshaded + inhandVisuals: + left: + - state: inhand-left + - state: inhand-left-unshaded + shader: unshaded + right: + - state: inhand-right + - state: inhand-right-unshaded + shader: unshaded + - type: PointLight + color: orange + - type: PressureProtection + highPressureMultiplier: 0.08 + lowPressureMultiplier: 1000 + - type: TemperatureProtection + coefficient: 0.005 + - type: Armor + modifiers: + coefficients: + Blunt: 0.9 + Slash: 0.9 + Piercing: 0.9 + Heat: 0.1 + Shock: 0.1 + Cold: 0.2 + Radiation: 0.2 diff --git a/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml b/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml index 7cfda5565f85..515d71a70b0c 100644 --- a/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml +++ b/Resources/Prototypes/Entities/Clothing/OuterClothing/hardsuits.yml @@ -600,4 +600,4 @@ - type: ExplosionResistance resistance: 0.7 - type: ToggleableClothing - clothingPrototype: ClothingHeadHelmetHardsuitSyndieElite + clothingPrototype: ClothingHeadHelmetCBURN \ No newline at end of file diff --git a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml index 0e0ea06f853b..744e16595273 100644 --- a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml +++ b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml @@ -150,8 +150,9 @@ outerClothing: ClothingOuterHardsuitCBURN shoes: ClothingShoesBootsJack id: CentcomPDA - pocket1: DoubleEmergencyOxygenTankFilled + pocket1: CombatKnife pocket2: LaserGun + suitstorage: YellowOxygenTankFilled belt: ClothingBeltBandolier innerclothingskirt: ClothingUniformJumpsuitColorBrown satchel: ClothingBackpackSatchel diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/equipped-head-unshaded.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/equipped-head-unshaded.png new file mode 100644 index 0000000000000000000000000000000000000000..7fd9a0b229c3448411cd7990d6404941bbb08880 GIT binary patch literal 162 zcmeAS@N?(olHy`uVBq!ia0vp^4j|0I1|(Ny7TyC=jKx9jP7LeL$-D$|Vmw_OLn`LH zJ!{C@V8GyVQK>2N_Kd_z48qn7m}zv;F>G0fqmKeuyvRMDGzj9|fi&lv??3hlFvDLVqPx%DM>^@RCt{2+P_O%Q4|O8ZzUZHmaZ|sge(dLDIIFW!O5jd<_!J;Zz(Q9Mn`E7 z+}yf!aILFO9RwW&8#+WN84{m)A{QbJWQ>E}@ZR$UJtr^EA>YrI`||EN_was%+yl^b zd!spNXR9&@k5y|2s<~b}zWAh_t;!&q%_CPR4#%!qO}K75ks`z$e@2spKX}yVNsBYS zr~tP5QL@>5NyJY{zHE%a^2!My6jxX*Hh-y$sx<4QsGgm08x5rie0Z|K1 zqCdc&LzuP*s@>tMRx?lp+b?kA-D;*2`Sb4Jv7CxJY=XC%8Z-w)T3Q+rT6nM>SIvWFj zA(9ea_+IV1`t_^21uWZ)U<(1^{ihbg!ik88h=_=Yh=^!9-2?hz1wgJJTsi;%002ov JPDHLkV1gY18@T`g literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon-flash.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon-flash.png new file mode 100644 index 0000000000000000000000000000000000000000..d37c1afe3e2fa59c546e099719f134de9d9d77b6 GIT binary patch literal 652 zcmV;70(1R|P)Px%MoC0LR9J=Wl}}I8a2Urw>)Ngx5VHW=VEi3n8sou(Q4b~~@#rhy75EBBd-cKoS_v6@9-U5mulSn3p zd~VleZZeJ2>Cx?U0giRu4%~=B6VP?rtki6Z%^Coi>@@J_Ex5e6B9(;N!9HfQMx|yW z(p(q-pnYnyyLU)tNY=l^dYaV=Nj^d7K6 e4T!EB1_s4CE+&a*IT}DC89ZJ6T-G@yGywqk4=nKj literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..adfb7557f7e7d85210cbcd1dbc25d8361a2c167f GIT binary patch literal 408 zcmV;J0cZY+P)Px$Qb|NXR9J=WmAy{FP#A_EO(&yaw56a4lY=fU3=T{#-T{+WLEsG1k)qbppzDE=V+7Mdiyzt*ZZ0Z02x#6p7g#i>TWdJ$;RdU^G?n{~_ zOVtSJh`Uc7Ld2PM+jgiQ)rg`%xu-I~a5yCN)9`a=%+|ie&Or%)@yiFFZ&R*g2urEA zZ~#araND`(QUDJC?@NvemD3Y?y~n=+061$L>uxCqARNsIeGkb0+(O?=uhFb{0D!yK z7<+p}LClX=FVOh{`w2^)qAZUn zA)oC!dUqa4osz!v`OVSo?bYx9&wkSS{bA+*Juiy299-bwWa3M$JFBMFrYAGrdu-iz z{{7nPbDb;R^5yxjT3FpBD(EQiWjZk& zDCgMkDko>4&XCHreCF(0@sEcXmPk)H1}CQdV0gAQ^qS#|j0r!a55R@N3YO*aeONBR zqI2+la+^>+vqVD)^QAAg+-IV$+-`le+5J&|gCS$jZ{0+xV=Nb9Zie1U_hI-sJ$q^G zF&3a%3$)4@OQhNBR)@*`yii;exwPuzOy;^2uJmN}rib&@|7n$(E1datdFmy*WG0X0 nIUrpd(!TdvatmJE|C6c6(ue!v6Wd&195Hyh`njxgN@xNAxeCiF literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-left.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-left.png new file mode 100644 index 0000000000000000000000000000000000000000..43f27a890f29dfdbc6e08f9a339965c03d33e4e8 GIT binary patch literal 519 zcmeAS@N?(olHy`uVBq!ia0vp^4j|0I1|(Ny7TyC=jKx9jP7LeL$-D%z4|=*dhE&XX zd&|)Ku!9Kuhy9D17wpKI>~><2f=JQikq&ha$;zl+y85gwH@bD))#BzL{6V_ zle?w$IMrvxoHO5R*W~9s{PW0YOKy3!aPP6)H5CtDZ+O2^R(#vzzMkm|w=f)d-zWZA z_KeQiN00x>eqFuN!Kv_(d+*9cdl(o#+{$|NfrsJNedXMQLc6j(0&y8RH&#xZ_KAt( zVPbl=X^~A{&6WLo`##HGsF1&~KdDeZk^Si2ytQ>kU#b^xJAEODL19PIuDm3ew}A8{ z!*7LOA9M@dbbs$Amaw5+!S{c|w0{lzFWfgyuwM7&b@5{^gEj3A+c=JiK6v+$*PQ=s z0DsdP?UKh_1u=0BhW9ypzD^Q9)cpQ;=d;U~M<~W0t|w)z4*} HQ$iB}%bM_> literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right-unshaded.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right-unshaded.png new file mode 100644 index 0000000000000000000000000000000000000000..118914c8d3f08f04301483e8c76c9a603d3f5d17 GIT binary patch literal 415 zcmeAS@N?(olHy`uVBq!ia0vp^4j|0I1|(Ny7TyC=jKx9jP7LeL$-D%zBRyRlLn`LH zy=mxu*nxrdfw(8am)Wq literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/inhand-right.png new file mode 100644 index 0000000000000000000000000000000000000000..602020b276949e62f04118d9cd9c686302f6844e GIT binary patch literal 527 zcmV+q0`UEbP)Px$$w@>(RCt{2+Obcr(tn0u8;yIEIPZ0abR+Bac1BT=*B|A=tx3L+}K4v#8y_wW=t!P&_%IZjts)<41X6D_7amoJtmUo1)UXT$-1 zpk1ER_Wlli_CBcdycIZMn#ppm${s2J5z%z=M(4LgM6;if8PQ%&L%d|T?l3eKb!&tQ z;JQOPtsMO7q-hlOw2yjzMg9-)SIm@GVBM~Hm!0d#oU-2|clKAzgo_6N0000000000 z09Y^f=WcPK!PHOZu|kV$@Fw*Sh@|}itH>G>lFjCp zh2Z@Jj?<;bmsgGP{+?0++E@31*IeDMdHzC}DAp~&@n!>F2x3f6DgXdT#y12LzG@SX R$Z`Mx002ovPDHLkV1i?J>;wP+ literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/light-overlay.png b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/light-overlay.png new file mode 100644 index 0000000000000000000000000000000000000000..ff7347fe6ee1df2d09efdef0a797c4174822c416 GIT binary patch literal 333 zcmV-T0kZyyP)Px$2T4RhR9J=Wl)(zZFbszOWxMGPg5bfE@8I1%`n>xN17QcDutW8@>cIp;-E4Og z%nzk&mL^|ATEJv7nf_fx%AsxB58LUq-c9+Q&-YtwYntY3{3-=7lX%PXhUbC*&w|V; zSpm`WdD%@Qu6gzv1b{1wV-`dfz(n#|twoMO7C|HdRB}lS0Q)h7hxRLpRsecl3P=(n zw+Hm8>oJ6(Bsyq^F@%n7UYT7ga4x{0zFkSQA4BN016M$7KH4)YN;z;xI}Ui|;C)F{ z>4A6oJ^Ks*T+VGs0z?qt;2!VOIvyRO2F$&RSpX4)R6{_#TDv95frSr|1eON}QIjo6 fY%-Zlrk~LZL(X#79wy%000000NkvXXu0mjfQca1O literal 0 HcmV?d00001 diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json new file mode 100644 index 000000000000..8decf1b6af8c --- /dev/null +++ b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json @@ -0,0 +1,59 @@ +{ + "version": 1, + "license": "CC-BY-SA-3.0", + "copyright": "Made by EmoGarbage404", + "size": { + "x": 32, + "y": 32 + }, + "states": [ + { + "name": "icon" + }, + { + "name": "icon-unshaded" + }, + { + "name": "icon-flash" + }, + { + "name": "light-overlay" + }, + { + "name": "equipped-head", + "directions": 4 + }, + { + "name": "equipped-head-light", + "directions": 4 + }, + { + "name": "equipped-head-unshaded", + "directions": 4 + }, + { + "name": "inhand-left", + "directions": 4 + }, + { + "name": "inhand-left-unshaded", + "directions": 4 + }, + { + "name": "inhand-left-light", + "directions": 4 + }, + { + "name": "inhand-right", + "directions": 4 + }, + { + "name": "inhand-right-unshaded", + "directions": 4 + }, + { + "name": "inhand-right-light", + "directions": 4 + } + ] +} diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/equipped-OUTERCLOTHING.png index e400e4189193e9e7277ddb06ce35568344fe9dc6..c7ed8fa9ff56f3e7b384734c8121736a80eb526e 100644 GIT binary patch delta 1919 zcmV-_2Y~pQ5}gvTv;luqNkl7() ze9P3dRqI+5n=$m=53bt6_0Y{5*G&NU@uy#RJh#`qazQorf>+;h=E44`nOVyL0Gh;R zo6yZ0*UjwaKN2|R#qB$f%5H?g{;2t}w#mBAGCiP4Y_@(M{yWR1??+p{g1N`r-(*gfROu<+@82(@#vz7t9y$?c~6lC;H3#UV*S5JI5qx>czwmo8$kKUz{R80?RlkyFi1VR$i*_lp5a35JK?nH&<;9477ys^Zk3g zML9xIR(4I7q#%6DimmZZp4(1Q11QQ01VKP=ce}Z?Zs5Xk37K>XftHY!CzDR$tSI2= zvVz|3c2f`p#}#k_)o1HOhaJ79P<^NDIRu2(FtmS-8fY6e@cTuZAngH}bjqp#Aq0NE zXgwpeh8tiUjg9fs!B-?InM85qbKB~@wiiMOfh^~{79EQKke*vC_)IBmFH4rg zyUs6?6trH0Jo-gngDjb~9K0JjYf+@@y0!T6Zsb7s3i}N;I$d`ZdJ{N-`!#qb+zDVF zkCJaN`S7{ttFO}e2? zKa!$*@K`)vb|X;zVsDuji}T$2j)%ZRB4PdBek!vtzrds~I4u$*BO?HSp`oF&=;!Yx zz=IOo)kTLQ2<&FmP)Wz|M5Z!jNQ6V%W z##dj5fxb9++|q98I_<|mUmU*rIs{rm80d@JB39VCI)Q5lbe;BFa{%?i0C{iG`1Fjc zb9r7^-vC=LSq@usz|`z3$K`)%c?Y@H9y1`G^ykO_#3X;@(3enE=ZB)a zsH%o0@hraoWfZ>pIuJsjE~&OW$<*&$WpWuHA~irb@(Bw}bk@^l1s9G>&~+WR_c2Ts z0M`EUdRN|l@I<7B&w`K-$%*xJVB+yh0D14!;Z2{VQ@9Lp`_3cJV1Lx4VQG>S1krRz zQm`W4p=2^?0zl}TXw!d=_2lpCx{im>HLhXp>K_~IkD9U^w!&rsVC?>H726P9y?WJK zYrg*sY^?~B$wgN&%C6kGOX~*iPE3Nv1yq{0wl)*U$13>!BJNI1Vrktd_SmktGQde6 zK~!!7fQrNg6oP6;<+fepmYm?)p)W~6D=whYJbCg2z*ek6MMHOFShmONREl&ujq`1% zAP7Q9jR#6F0J|4BD0E#f+4!!80PB3!w1C2e7cQ0$cj-_y2ZZ>Y5}6XPv;lumNklbC9LK-07T-!EtwV9l7%ic;EY@jiN^KDo z7MdlYP`32qp%?M6z4c=0Z7F+^?PYJf3(_9;;6>U?iL@+&1?wN`pGIZDLXeo5OuCFN zRoq$HX7-T2@r@cYZxYjGHy;Q|Uf#U#`~C9Xn>X+G11eOgP@#W9g$fn^r+7Yh2i!1t z|E{TNY3sWvHsaoQKe)1m>mn-r<4?ctx$e>V^pG;nB~B8-2%>2l~S1`nw{+dq>>2?4aeZ~i8j%U zmWHZo=BU4zM*^!K8=uQtFWS?=tzYFtT+`A>B@+OEBgY9;RYOKgTQ61B zaO5}v0Hl%$Xj&SB_wSmHtmD*IRc+sTw47JJpaZl|Mh*?fpeSqb*3}}?-40dNtXHJF z9p1WHD9Rd!hGWQRX&f|Hd0_Pc*t7xI`T&4i|3C)}^o4)T>sPxhF*5cRM7>Z`GyxPO0YY3?T&HesjZSU{iAdKRZFnhTo46Jt}5v1JZB1m;J5=$ zp!#f|=(MBXDOBGn2TlQ@B?xV+8roJhd_K`8NJoD_Dw(i4KnQ`)CtBACEkVZ}aiY(n zC~GhbV~?YG^$#2YbOi=-3(N85dQ7e=*nGDQd8-<+@i{bzjff}Sz*|=f0Qgf~=Q7fX zK3(iG+XUWC1B4J5M(%xbRk3~7KHU{|J1idsHw$#=jZZIm2KvJ0%BF!cUb3eiEr0Ov zxrcwfhQnS*`i1KA>K9xCb~i!@fh^~S7M+U#kepq}drdLyZcCPf`>rpN04#Gjxo+QxuyV+d-6Mf`lPMw{OOa(XlXQ^;BJnae8b)C zG~nuS(}}7*##8c@mzsPVEVmmk?kPYQoqC(MYJ7F;yu*K^K@82~K+X>Wo`j1C@I;`KC zngfVEeT)>x@f_EI$jq_|p(SU$rllbs`+#UqhZVZcl;K>EJ`&S}3`JRkwpD)(QEY^= zn83`k>NqF@a5#WIg0e$zUe(aw>$j37$^q4(2^pg=7WWv;(-+4lLiDkd%?hC@G2Xgb z^!G-=6P9+%r8Xb>d!z8y)uO36fd1a7En|i4s}s1Uz@;{ywFb~A43LW!jZ93rI+y2# zjSaBTHIc|^p9GicQ22%{fz|F492ubz4&2bZw>T$E{vXziQVI$T&a65n+ zF9-sLhGR%26Ci|G`2vS^D9X0o)EodI#L8Nufe|-H?_*FrmSc%BuQ z7q;zdp&&*krfm5DIOa#y$qQU%h*ayrr*;$jT3a*@zpzAswaPGr-+4!rf zYVGZ|CnVK>6ogz#PNcgXqc0W#v;A`A$))X0*-MMo*wo|N002ovPDHLkV1mV~ Bt{ngX From 33c90bb758fc7ec69845803adf2c44d6c74cde96 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 29 May 2022 11:44:46 -0400 Subject: [PATCH 13/40] json momento --- .../Clothing/Head/Hardsuits/cburn.rsi/meta.json | 12 ------------ .../OuterClothing/Hardsuits/cburn.rsi/meta.json | 2 +- 2 files changed, 1 insertion(+), 13 deletions(-) diff --git a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json index 8decf1b6af8c..16f509fa99f2 100644 --- a/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json +++ b/Resources/Textures/Clothing/Head/Hardsuits/cburn.rsi/meta.json @@ -23,10 +23,6 @@ "name": "equipped-head", "directions": 4 }, - { - "name": "equipped-head-light", - "directions": 4 - }, { "name": "equipped-head-unshaded", "directions": 4 @@ -39,10 +35,6 @@ "name": "inhand-left-unshaded", "directions": 4 }, - { - "name": "inhand-left-light", - "directions": 4 - }, { "name": "inhand-right", "directions": 4 @@ -50,10 +42,6 @@ { "name": "inhand-right-unshaded", "directions": 4 - }, - { - "name": "inhand-right-light", - "directions": 4 } ] } diff --git a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json index f2bcccc0c689..2cfc2220e1a7 100644 --- a/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json +++ b/Resources/Textures/Clothing/OuterClothing/Hardsuits/cburn.rsi/meta.json @@ -1,7 +1,7 @@ { "version": 1, "license": "CC-BY-SA-3.0", - "copyright": "Taken from tgstation at commit https://github.com/tgstation/tgstation/commit/40d89d11ea4a5cb81d61dc1018b46f4e7d32c62a. Further modifications and derivate works (inhand-left and inhand-right) under same license.", + "copyright": "Made by EmoGarbage404", "size": { "x": 32, "y": 32 From 4b7f1eff17db59fc8b88dbb322b0ce02475d2a6d Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 29 May 2022 19:33:52 -0400 Subject: [PATCH 14/40] nuke arm event --- .../GameTicking/Rules/ZombieRuleSystem.cs | 29 ++++++++++++------- .../game-presets/preset-zombies.ftl | 7 ++++- 2 files changed, 24 insertions(+), 12 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 975d9563385f..2cfb4f290a98 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -1,6 +1,7 @@ using System.Linq; using Content.Server.Chat.Managers; using Content.Server.Disease; +using Content.Server.Nuke; using Content.Server.Players; using Content.Server.RoundEnd; using Content.Server.Spawners.Components; @@ -32,6 +33,8 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly StationSystem _stationSystem = default!; [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; + [Dependency] private readonly NukeSystem _nukeSystem = default!; + [Dependency] private readonly NukeCodeSystem _nukeCodeSystem = default!; private const string PatientZeroPrototypeID = "PatientZero"; private const string InitialZombieVirusPrototype = "ZombieInfection"; @@ -67,17 +70,7 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) private void OnMobStateChanged(MobStateChangedEvent ev) { - if (!Enabled) - return; - - if (!_aliveNukeops.TryFirstOrNull(x => x.Key.OwnedEntity == ev.Entity, out var op)) return; - - _aliveNukeops[op.Value.Key] = op.Value.Key.CharacterDeadIC; - - if (_aliveNukeops.Values.All(x => !x)) - { - _roundEndSystem.EndRound(); - } + } private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) @@ -282,4 +275,18 @@ public override void Started() } public override void Ended() { } + + /// EVENTS + /// These are all the functions that handle midround events + /// that can occur during zombie mode + + private void UnlockNuke() + { + _chatManager.DispatchStationAnnouncement(Loc.GetString("zombie-nuke-armed-event", ("code",_nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); + foreach (var nuke in EntityManager.EntityQuery().ToList()) + { + if (nuke.DiskSlot.ContainerSlot != null) + nuke.DiskSlot.ContainerSlot.Insert(Spawn("NukeDisk", Transform(nuke.Owner).Coordinates)); + } + } } diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index df38c445f943..726a28974f6c 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -4,4 +4,9 @@ zombie-description = A virus able to create the undead has been unleashed unto t zombie-not-enough-ready-players = Not enough players readied up for the game! There were {$readyPlayersCount} players readied up out of {$minimumPlayers} needed. Can't start Zombies. zombie-no-one-ready = No players readied up! Can't start Zombies. -zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. \ No newline at end of file +#Patient 0 +zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. + +#EVENTS +#Nuke Event +zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. The code is {$code}. \ No newline at end of file From 67e5625af30a3962d0c96f880b5a34226813dfa4 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 29 May 2022 23:59:20 -0400 Subject: [PATCH 15/40] shuttle spawning --- .../GameTicking/Rules/ZombieRuleSystem.cs | 190 +++++++++--------- .../game-presets/preset-zombies.ftl | 9 +- 2 files changed, 95 insertions(+), 104 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 2cfb4f290a98..404fb4100283 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -3,10 +3,12 @@ using Content.Server.Disease; using Content.Server.Nuke; using Content.Server.Players; +using Content.Server.Roles; using Content.Server.RoundEnd; using Content.Server.Spawners.Components; using Content.Server.Station.Components; using Content.Server.Station.Systems; +using Content.Server.Traitor; using Content.Shared.CCVar; using Content.Shared.MobState; using Content.Shared.Roles; @@ -29,6 +31,7 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly IChatManager _chatManager = default!; [Dependency] private readonly IMapLoader _mapLoader = default!; [Dependency] private readonly IMapManager _mapManager = default!; + [Dependency] private readonly IPlayerManager _playerManager = default!; [Dependency] private readonly StationSpawningSystem _stationSpawningSystem = default!; [Dependency] private readonly StationSystem _stationSystem = default!; [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; @@ -75,70 +78,7 @@ private void OnMobStateChanged(MobStateChangedEvent ev) private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) { - if (!Enabled) - return; - - var list = new List(ev.Players); - var prefList = new List(); - - foreach (var player in list) - { - if (!ev.Profiles.ContainsKey(player.UserId)) - { - continue; - } - prefList.Add(player); //by default, zombies don't care whether or not you are command or nonantag crew - } - - var playersPerInfected = _cfg.GetCVar(CCVars.ZombiePlayersPerInfected); - var maxInfected = _cfg.GetCVar(CCVars.ZombieMaxInfected); - - var numInfected = Math.Max(1, - (int) Math.Min( - Math.Floor((double) ev.Players.Length / playersPerInfected), maxInfected)); - - for (var i = 0; i < numInfected; i++) - { - IPlayerSession zombie; //this isn't actually a zombie, but rather a patient 0. sue me for naming it shitty -emo - if (prefList.Count == 0) - { - if (list.Count == 0) - { - Logger.InfoS("preset", "Insufficient ready players to fill up with patient 0, stopping the selection."); - break; - } - zombie = _random.PickAndTake(list); - list.Remove(zombie); - Logger.InfoS("preset", "Insufficient preferred patient 0, picking at random."); - } - else - { - zombie = _random.PickAndTake(prefList); - list.Remove(zombie); - Logger.InfoS("preset", "Selected a preferred patient 0."); - } - - var mind = zombie.Data.ContentData()?.Mind; - if (mind == null) - { - Logger.ErrorS("preset", "Failed getting mind for picked patient 0."); - continue; - } - - DebugTools.AssertNotNull(mind.OwnedEntity); - - if (mind.OwnedEntity != null) - _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. - - if (mind.Session != null) - { - var messageWrapper = Loc.GetString("chat-manager-server-wrap-message"); - - // I went all the way to ChatManager.cs and all i got was this lousy T-shirt - _chatManager.ChatMessageToOne(Shared.Chat.ChatChannel.Server, Loc.GetString("zombie-patientzero-role-greeting"), - messageWrapper, default, false, mind.Session.ConnectedClient, Color.Plum); - } - } + InfectInitialPlayers(); } private void OnPlayersSpawning(RulePlayerSpawningEvent ev) @@ -147,41 +87,7 @@ private void OnPlayersSpawning(RulePlayerSpawningEvent ev) return; //these are staying here because i want the code for reference - // Between 1 and : needs at least n players per op. - /*var numInfected = Math.Max(1, - (int)Math.Min( - Math.Floor((double)ev.PlayerPool.Count / _cfg.GetCVar(CCVars.ZombiePlayersPerInfected)), _cfg.GetCVar(CCVars.ZombieMaxInfected))); - - _random.PickAndTake(ev.PlayerPool); - */ - /* - var map = "/Maps/infiltrator.yml"; - - var aabbs = _stationSystem.Stations.SelectMany(x => - Comp(x).Grids.Select(x => _mapManager.GetGridComp(x).Grid.WorldAABB)).ToArray(); - var aabb = aabbs[0]; - for (int i = 1; i < aabbs.Length; i++) - { - aabb.Union(aabbs[i]); - } - - var (_, gridId) = _mapLoader.LoadBlueprint(GameTicker.DefaultMap, map, new MapLoadOptions - { - Offset = aabb.Center + MathF.Max(aabb.Height / 2f, aabb.Width / 2f) * 2.5f - }); - - if (!gridId.HasValue) - { - Logger.ErrorS("NUKEOPS", $"Gridid was null when loading \"{map}\", aborting."); - foreach (var session in ops) - { - ev.PlayerPool.Add(session); - } - return; - } - - var gridUid = _mapManager.GetGridEuid(gridId.Value); // TODO: Loot table or something var commanderGear = _prototypeManager.Index("SyndicateCommanderGearFull"); @@ -271,22 +177,106 @@ private void OnStartAttempt(RoundStartAttemptEvent ev) public override void Started() { - _opsWon = false; + InfectInitialPlayers(); } public override void Ended() { } + /// + /// Infects the first players with the passive zombie virus. + /// + private void InfectInitialPlayers() + { + var playerList = _playerManager.ServerSessions.ToList(); + + if (playerList.Count == 0) + return; + + var playersPerInfected = _cfg.GetCVar(CCVars.ZombiePlayersPerInfected); + var maxInfected = _cfg.GetCVar(CCVars.ZombieMaxInfected); + + var numInfected = Math.Max(1, + (int) Math.Min( + Math.Floor((double) playerList.Count / playersPerInfected), maxInfected)); + + for (var i = 0; i < numInfected; i++) + { + if (playerList.Count == 0) + { + Logger.InfoS("preset", "Insufficient number of players. stopping selection."); + break; + } + IPlayerSession zombie = _random.PickAndTake(playerList); + playerList.Remove(zombie); + Logger.InfoS("preset", "Selected a patient 0."); + + var mind = zombie.Data.ContentData()?.Mind; + if (mind == null) + { + Logger.ErrorS("preset", "Failed getting mind for picked patient 0."); + continue; + } + + DebugTools.AssertNotNull(mind.OwnedEntity); + + mind.AddRole(new TraitorRole(mind, _prototypeManager.Index(PatientZeroPrototypeID))); + if (mind.OwnedEntity != null) + _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. + + if (mind.Session != null) + { + var messageWrapper = Loc.GetString("chat-manager-server-wrap-message"); + + // I went all the way to ChatManager.cs and all i got was this lousy T-shirt + _chatManager.ChatMessageToOne(Shared.Chat.ChatChannel.Server, Loc.GetString("zombie-patientzero-role-greeting"), + messageWrapper, default, false, mind.Session.ConnectedClient, Color.Plum); + } + } + } + /// EVENTS /// These are all the functions that handle midround events /// that can occur during zombie mode - + + /// + /// This event announces the nuke code and spawns + /// the disk inside of it. This is for round end + /// so the duplicated disks shouldn't really matter. + /// private void UnlockNuke() { _chatManager.DispatchStationAnnouncement(Loc.GetString("zombie-nuke-armed-event", ("code",_nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); foreach (var nuke in EntityManager.EntityQuery().ToList()) { if (nuke.DiskSlot.ContainerSlot != null) + { nuke.DiskSlot.ContainerSlot.Insert(Spawn("NukeDisk", Transform(nuke.Owner).Coordinates)); + } + + } + } + + /// + /// Spawns a shuttle a distance away from the main station + /// This code is 100% canibalized from nukies + /// idk how it works. -emo + /// + /// The file path to the map file + private void SpawnShuttle(string map) + { + _chatManager.DispatchStationAnnouncement(Loc.GetString("zombie-shuttle-call-event", ("code", _nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); + + var aabbs = _stationSystem.Stations.SelectMany(x => + Comp(x).Grids.Select(x => _mapManager.GetGridComp(x).Grid.WorldAABB)).ToArray(); + var aabb = aabbs[0]; + for (int i = 1; i < aabbs.Length; i++) + { + aabb.Union(aabbs[i]); } + + var (_, gridId) = _mapLoader.LoadBlueprint(GameTicker.DefaultMap, map, new MapLoadOptions + { + Offset = aabb.Center + MathF.Max(aabb.Height / 2f, aabb.Width / 2f) * 2.5f + }); } } diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index 726a28974f6c..0fc568815c4a 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -4,9 +4,10 @@ zombie-description = A virus able to create the undead has been unleashed unto t zombie-not-enough-ready-players = Not enough players readied up for the game! There were {$readyPlayersCount} players readied up out of {$minimumPlayers} needed. Can't start Zombies. zombie-no-one-ready = No players readied up! Can't start Zombies. -#Patient 0 zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. -#EVENTS -#Nuke Event -zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. The code is {$code}. \ No newline at end of file +zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. A disk has been automatically teleported inside of it. The code to detonate the device is: {$code}. +zombie-end-nuke-armed-event-fail = The nuke was not detonated. +zombie-end-nuke-armed-eveent-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. + +zombie-shuttle-call-event = In response to the zombie outbreak, we have dispatched a shuttle containing an emergency team to your station. \ No newline at end of file From f375d208d386f8edc7bdbdacbdca23fd7be49dc9 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Mon, 30 May 2022 00:04:49 -0400 Subject: [PATCH 16/40] mini --- Content.Server/GameTicking/Rules/ZombieRuleSystem.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 404fb4100283..90c2eb37054d 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -177,6 +177,7 @@ private void OnStartAttempt(RoundStartAttemptEvent ev) public override void Started() { + //this technically will run twice with zombies on roundstart, but it doesn't matter because it fails instantly InfectInitialPlayers(); } From bd706146e3586750f22135cac647bb270febbffc Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Mon, 30 May 2022 13:47:59 -0400 Subject: [PATCH 17/40] events + weighted prototype --- .../GameTicking/Rules/ZombieRuleSystem.cs | 26 ++++++++++++++++++- .../Prototypes/Entities/Mobs/NPCs/human.yml | 14 ++++++++++ Resources/Prototypes/zombie_weights.yml | 8 ++++++ 3 files changed, 47 insertions(+), 1 deletion(-) create mode 100644 Resources/Prototypes/zombie_weights.yml diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 90c2eb37054d..8003131a6f94 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -11,6 +11,8 @@ using Content.Server.Traitor; using Content.Shared.CCVar; using Content.Shared.MobState; +using Content.Shared.Random; +using Content.Shared.Random.Helpers; using Content.Shared.Roles; using Robust.Server.Maps; using Robust.Server.Player; @@ -39,9 +41,14 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly NukeSystem _nukeSystem = default!; [Dependency] private readonly NukeCodeSystem _nukeCodeSystem = default!; + private const string ZombieEventsWeightedRandomID = "ZombieEvents"; + private const string PatientZeroPrototypeID = "PatientZero"; + + private const string InitialZombieVirusPrototype = "ZombieInfection"; + private string? _midRoundEvent; private Dictionary _aliveNukeops = new(); private bool _opsWon; @@ -79,6 +86,7 @@ private void OnMobStateChanged(MobStateChangedEvent ev) private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) { InfectInitialPlayers(); + ChooseMidRoundEvent(); } private void OnPlayersSpawning(RulePlayerSpawningEvent ev) @@ -238,7 +246,23 @@ private void InfectInitialPlayers() /// EVENTS /// These are all the functions that handle midround events /// that can occur during zombie mode - + private void ChooseMidRoundEvent() + { + switch (_prototypeManager.Index(ZombieEventsWeightedRandomID).Pick(_random)) + { + case ("Nuke"): + UnlockNuke(); + break; + case ("ERT"): + SpawnShuttle("/maps/dart.yml"); + break; + case ("CBURN"): + SpawnShuttle("/maps/infiltrator.yml"); + break; + } + } + + /// /// This event announces the nuke code and spawns /// the disk inside of it. This is for round end diff --git a/Resources/Prototypes/Entities/Mobs/NPCs/human.yml b/Resources/Prototypes/Entities/Mobs/NPCs/human.yml index d74d8f96eee8..7cc186461f22 100644 --- a/Resources/Prototypes/Entities/Mobs/NPCs/human.yml +++ b/Resources/Prototypes/Entities/Mobs/NPCs/human.yml @@ -30,6 +30,20 @@ - Idle - Spirate +- type: entity + parent: MobHuman + id: MobCBURNUnit + name: CBURN Agent + description: A miserable pile of secrets + components: + - type: RandomHumanoidAppearance + - type: Loadout + prototype: CBURNGear + - type: GhostTakeoverAvailable + makeSentient: false + name: CBURN Agent + description: A highly trained Centcomm agent, capable of dealing with various threats. + - type: entity parent: MobHumanBase suffix: Dead diff --git a/Resources/Prototypes/zombie_weights.yml b/Resources/Prototypes/zombie_weights.yml new file mode 100644 index 000000000000..3f9c74d2b90c --- /dev/null +++ b/Resources/Prototypes/zombie_weights.yml @@ -0,0 +1,8 @@ +#Each of these values are hardcoded into +#ZombieRuleSystem.cs because I'm a bastard. -emo +- type: weightedRandom + id: ZombieEvents + weights: + Nuke: 0.50 + ERT: 0.50 + CBURN: 0.25 \ No newline at end of file From 4e324209f63015b94f46a0d3a49c5f390ba780b1 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 <98561806+EmoGarbage404@users.noreply.github.com> Date: Mon, 30 May 2022 22:29:39 -0400 Subject: [PATCH 18/40] Update ZombieRuleSystem.cs --- Content.Server/GameTicking/Rules/ZombieRuleSystem.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 8003131a6f94..f7a7012fd6c5 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -254,10 +254,10 @@ private void ChooseMidRoundEvent() UnlockNuke(); break; case ("ERT"): - SpawnShuttle("/maps/dart.yml"); + SpawnShuttle("/Maps/dart.yml"); break; case ("CBURN"): - SpawnShuttle("/maps/infiltrator.yml"); + SpawnShuttle("/Maps/infiltrator.yml"); break; } } From 55f1ba0ccd28c6ea5490fae3795dadc47f7d40e5 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Tue, 31 May 2022 22:06:26 -0400 Subject: [PATCH 19/40] ert+ cburn gon --- .../GameTicking/Rules/ZombieRuleSystem.cs | 47 +------------------ Resources/Prototypes/zombie_weights.yml | 8 ---- 2 files changed, 2 insertions(+), 53 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index f7a7012fd6c5..9b7591981b62 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -42,6 +42,7 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly NukeCodeSystem _nukeCodeSystem = default!; private const string ZombieEventsWeightedRandomID = "ZombieEvents"; + private const string ZombieVariantsWeightedRandomID = "ZombieVariants"; private const string PatientZeroPrototypeID = "PatientZero"; @@ -86,7 +87,6 @@ private void OnMobStateChanged(MobStateChangedEvent ev) private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) { InfectInitialPlayers(); - ChooseMidRoundEvent(); } private void OnPlayersSpawning(RulePlayerSpawningEvent ev) @@ -243,30 +243,11 @@ private void InfectInitialPlayers() } } - /// EVENTS - /// These are all the functions that handle midround events - /// that can occur during zombie mode - private void ChooseMidRoundEvent() - { - switch (_prototypeManager.Index(ZombieEventsWeightedRandomID).Pick(_random)) - { - case ("Nuke"): - UnlockNuke(); - break; - case ("ERT"): - SpawnShuttle("/Maps/dart.yml"); - break; - case ("CBURN"): - SpawnShuttle("/Maps/infiltrator.yml"); - break; - } - } - /// /// This event announces the nuke code and spawns /// the disk inside of it. This is for round end - /// so the duplicated disks shouldn't really matter. + /// so the duplicated disk shouldn't really matter. /// private void UnlockNuke() { @@ -280,28 +261,4 @@ private void UnlockNuke() } } - - /// - /// Spawns a shuttle a distance away from the main station - /// This code is 100% canibalized from nukies - /// idk how it works. -emo - /// - /// The file path to the map file - private void SpawnShuttle(string map) - { - _chatManager.DispatchStationAnnouncement(Loc.GetString("zombie-shuttle-call-event", ("code", _nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); - - var aabbs = _stationSystem.Stations.SelectMany(x => - Comp(x).Grids.Select(x => _mapManager.GetGridComp(x).Grid.WorldAABB)).ToArray(); - var aabb = aabbs[0]; - for (int i = 1; i < aabbs.Length; i++) - { - aabb.Union(aabbs[i]); - } - - var (_, gridId) = _mapLoader.LoadBlueprint(GameTicker.DefaultMap, map, new MapLoadOptions - { - Offset = aabb.Center + MathF.Max(aabb.Height / 2f, aabb.Width / 2f) * 2.5f - }); - } } diff --git a/Resources/Prototypes/zombie_weights.yml b/Resources/Prototypes/zombie_weights.yml index 3f9c74d2b90c..e69de29bb2d1 100644 --- a/Resources/Prototypes/zombie_weights.yml +++ b/Resources/Prototypes/zombie_weights.yml @@ -1,8 +0,0 @@ -#Each of these values are hardcoded into -#ZombieRuleSystem.cs because I'm a bastard. -emo -- type: weightedRandom - id: ZombieEvents - weights: - Nuke: 0.50 - ERT: 0.50 - CBURN: 0.25 \ No newline at end of file From cd06eeb5c22ce6330ae856bbe06b07fd27228724 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Mon, 6 Jun 2022 08:48:32 -0400 Subject: [PATCH 20/40] more shit --- Content.Server/GameTicking/Rules/ZombieRuleSystem.cs | 5 ----- .../en-US/game-ticking/game-presets/preset-zombies.ftl | 4 +--- 2 files changed, 1 insertion(+), 8 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 9b7591981b62..2e0760c2c602 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -41,15 +41,10 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly NukeSystem _nukeSystem = default!; [Dependency] private readonly NukeCodeSystem _nukeCodeSystem = default!; - private const string ZombieEventsWeightedRandomID = "ZombieEvents"; private const string ZombieVariantsWeightedRandomID = "ZombieVariants"; - private const string PatientZeroPrototypeID = "PatientZero"; - - private const string InitialZombieVirusPrototype = "ZombieInfection"; - private string? _midRoundEvent; private Dictionary _aliveNukeops = new(); private bool _opsWon; diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index 0fc568815c4a..b3ce4a665a26 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -8,6 +8,4 @@ zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get s zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. A disk has been automatically teleported inside of it. The code to detonate the device is: {$code}. zombie-end-nuke-armed-event-fail = The nuke was not detonated. -zombie-end-nuke-armed-eveent-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. - -zombie-shuttle-call-event = In response to the zombie outbreak, we have dispatched a shuttle containing an emergency team to your station. \ No newline at end of file +zombie-end-nuke-armed-eveent-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. \ No newline at end of file From 67ae8ea469dfeeec0bad317dd673164c716c644e Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Mon, 13 Jun 2022 17:25:44 -0400 Subject: [PATCH 21/40] zombies do some more shit now idk --- .../GameTicking/Rules/ZombieRuleSystem.cs | 13 ++++--- Content.Server/Zombies/ZombieComponent.cs | 11 ++++++ Content.Server/Zombies/ZombieSystem.cs | 37 ++++++++++++++++++- .../Zombies/ZombifyOnDeathSystem.cs | 7 +++- 4 files changed, 58 insertions(+), 10 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 2e0760c2c602..ef19d441c18f 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -1,6 +1,7 @@ using System.Linq; using Content.Server.Chat.Managers; using Content.Server.Disease; +using Content.Server.GameTicking.Rules.Configurations; using Content.Server.Nuke; using Content.Server.Players; using Content.Server.Roles; @@ -43,7 +44,7 @@ public sealed class ZombieRuleSystem : GameRuleSystem private const string ZombieVariantsWeightedRandomID = "ZombieVariants"; private const string PatientZeroPrototypeID = "PatientZero"; - private const string InitialZombieVirusPrototype = "ZombieInfection"; + private const string InitialZombieVirusPrototype = "ActiveZombieVirus"; private Dictionary _aliveNukeops = new(); private bool _opsWon; @@ -178,13 +179,13 @@ private void OnStartAttempt(RoundStartAttemptEvent ev) //*/ } - public override void Started() + public override void Started(GameRuleConfiguration configuration) { //this technically will run twice with zombies on roundstart, but it doesn't matter because it fails instantly InfectInitialPlayers(); } - public override void Ended() { } + public override void Ended(GameRuleConfiguration configuration) { } /// /// Infects the first players with the passive zombie virus. @@ -246,14 +247,14 @@ private void InfectInitialPlayers() /// private void UnlockNuke() { - _chatManager.DispatchStationAnnouncement(Loc.GetString("zombie-nuke-armed-event", ("code",_nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); - foreach (var nuke in EntityManager.EntityQuery().ToList()) + //_chatManager.(Loc.GetString("zombie-nuke-armed-event", ("code",_nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); + /*foreach (var nuke in EntityManager.EntityQuery().ToList()) { if (nuke.DiskSlot.ContainerSlot != null) { nuke.DiskSlot.ContainerSlot.Insert(Spawn("NukeDisk", Transform(nuke.Owner).Coordinates)); } - } + }*/ } } diff --git a/Content.Server/Zombies/ZombieComponent.cs b/Content.Server/Zombies/ZombieComponent.cs index 57f59c5b5f8d..7366590a9009 100644 --- a/Content.Server/Zombies/ZombieComponent.cs +++ b/Content.Server/Zombies/ZombieComponent.cs @@ -8,5 +8,16 @@ public sealed class ZombieComponent : Component /// attacks another zombie. longe name /// public float OtherZombieDamageCoefficient = 0.75f; + + /// + /// The baseline infection chance you have if you are completely nude + /// + public float MaxZombieInfectionChance = 0.75f; + + /// + /// The minimum infection chance possible. This is simply to prevent + /// being invincible by bundling up. + /// + public float MinZombieInfectionChance = 0.1f; } } diff --git a/Content.Server/Zombies/ZombieSystem.cs b/Content.Server/Zombies/ZombieSystem.cs index 818e3941b42a..99a183b2f24c 100644 --- a/Content.Server/Zombies/ZombieSystem.cs +++ b/Content.Server/Zombies/ZombieSystem.cs @@ -7,6 +7,10 @@ using Content.Shared.Chemistry.Components; using Content.Shared.MobState.Components; using Content.Server.Disease; +using Content.Shared.Inventory; +using Content.Server.Popups; +using Robust.Shared.Player; +using Content.Server.Inventory; namespace Content.Server.Zombies { @@ -15,13 +19,42 @@ public sealed class ZombieSystem : EntitySystem [Dependency] private readonly DiseaseSystem _disease = default!; [Dependency] private readonly BloodstreamSystem _bloodstream = default!; [Dependency] private readonly ZombifyOnDeathSystem _zombify = default!; + [Dependency] private readonly ServerInventorySystem _inv = default!; [Dependency] private readonly IRobustRandom _robustRandom = default!; + [Dependency] private readonly ILogManager _logManager = default!; public override void Initialize() { base.Initialize(); + SubscribeLocalEvent(OnMeleeHit); } + private float GetZombieInfectionChance(EntityUid uid, ZombieComponent component) + { + float baseChance = component.MaxZombieInfectionChance; + + if (!TryComp(uid, out var inventoryComponent)) + return baseChance; + + if (!_inv.TryGetContainerSlotEnumerator(uid, out var enumerator, inventoryComponent)) + return baseChance; + + var items = 0f; + var total = 0f; + while (enumerator.MoveNext(out var con)) + { + total++; + if (con.ContainedEntity != null) + items++; + } + + var max = component.MaxZombieInfectionChance; + var min = component.MinZombieInfectionChance; + //gets a value between the max and min based on how many items the entity is wearing + float chance = (max-min) * ((total - items)/total) + min; + return chance; + } + private void OnMeleeHit(EntityUid uid, ZombieComponent component, MeleeHitEvent args) { if (!EntityManager.TryGetComponent(args.User, out var zombieComp)) @@ -38,11 +71,11 @@ private void OnMeleeHit(EntityUid uid, ZombieComponent component, MeleeHitEvent if (!TryComp(entity, out var mobState) || HasComp(entity)) continue; - if (_robustRandom.Prob(0.5f) && HasComp(entity)) + if (HasComp(entity) && _robustRandom.Prob(GetZombieInfectionChance(entity, component))) _disease.TryAddDisease(entity, "ActiveZombieVirus"); if (HasComp(entity)) - args.BonusDamage = args.BaseDamage * zombieComp.OtherZombieDamageCoefficient; + args.BonusDamage = -args.BaseDamage * zombieComp.OtherZombieDamageCoefficient; if ((mobState.IsDead() || mobState.IsCritical()) && !HasComp(entity)) diff --git a/Content.Server/Zombies/ZombifyOnDeathSystem.cs b/Content.Server/Zombies/ZombifyOnDeathSystem.cs index 580bfb9cedb1..331e36e2aeaa 100644 --- a/Content.Server/Zombies/ZombifyOnDeathSystem.cs +++ b/Content.Server/Zombies/ZombifyOnDeathSystem.cs @@ -24,6 +24,7 @@ using Robust.Shared.Containers; using Content.Shared.Movement.Components; using Content.Shared.MobState; +using Robust.Server.GameObjects; namespace Content.Server.Zombies { @@ -39,6 +40,7 @@ public sealed class ZombifyOnDeathSystem : EntitySystem [Dependency] private readonly DamageableSystem _damageable = default!; [Dependency] private readonly DiseaseSystem _disease = default!; [Dependency] private readonly SharedHumanoidAppearanceSystem _sharedHuApp = default!; + [Dependency] private readonly IChatManager _chatMan = default!; public override void Initialize() @@ -73,7 +75,6 @@ public void ZombifyEntity(EntityUid target) if (HasComp(target)) return; - _disease.CureAllDiseases(target); RemComp(target); RemComp(target); RemComp(target); @@ -100,11 +101,13 @@ public void ZombifyEntity(EntityUid target) var melee = EnsureComp(target); melee.Arc = zombiecomp.AttackArc; melee.ClickArc = zombiecomp.AttackArc; + melee.Range = 0.75f; + //lord forgive me for the hardcoded damage DamageSpecifier dspec = new(); dspec.DamageDict.Add("Slash", 13); dspec.DamageDict.Add("Piercing", 7); - melee.Damage = dspec; + melee.Damage = dspec; _damageable.SetDamageModifierSetId(target, "Zombie"); _bloodstream.SetBloodLossThreshold(target, 0f); From f87b76f5703048d52d559ce3640d5ade2cbf7066 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Fri, 17 Jun 2022 11:07:17 -0400 Subject: [PATCH 22/40] big shit goin on --- .../GameTicking/Rules/ZombieRuleSystem.cs | 188 ++++++++---------- .../Zombies/ZombifyOnDeathSystem.cs | 65 +++--- .../game-presets/preset-zombies.ftl | 14 +- Resources/Locale/en-US/zombies/zombie.ftl | 2 +- 4 files changed, 141 insertions(+), 128 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index ef19d441c18f..0d52c5ebfa5e 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -10,8 +10,12 @@ using Content.Server.Station.Components; using Content.Server.Station.Systems; using Content.Server.Traitor; +using Content.Server.Zombies; using Content.Shared.CCVar; +using Content.Shared.CharacterAppearance.Components; +using Content.Shared.FixedPoint; using Content.Shared.MobState; +using Content.Shared.MobState.Components; using Content.Shared.Random; using Content.Shared.Random.Helpers; using Content.Shared.Roles; @@ -42,14 +46,11 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly NukeSystem _nukeSystem = default!; [Dependency] private readonly NukeCodeSystem _nukeCodeSystem = default!; - private const string ZombieVariantsWeightedRandomID = "ZombieVariants"; - private const string PatientZeroPrototypeID = "PatientZero"; - private const string InitialZombieVirusPrototype = "ActiveZombieVirus"; - - private Dictionary _aliveNukeops = new(); - private bool _opsWon; + private Dictionary _initialInfected = new(); public override string Prototype => "Zombie"; + private const string PatientZeroPrototypeID = "PatientZero"; + private const string InitialZombieVirusPrototype = "ActiveZombieVirus"; public override void Initialize() { @@ -57,9 +58,11 @@ public override void Initialize() SubscribeLocalEvent(OnStartAttempt); //SubscribeLocalEvent(OnPlayersSpawning); - //SubscribeLocalEvent(OnMobStateChanged); + SubscribeLocalEvent(OnMobStateChanged); SubscribeLocalEvent(OnRoundEndText); SubscribeLocalEvent(OnJobAssigned); + + SubscribeLocalEvent(OnEntityZombified); } private void OnRoundEndText(RoundEndTextAppendEvent ev) @@ -67,92 +70,58 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) if (!Enabled) return; - ev.AddLine("ZOMBIE ROUND OVER TESTETEST"); - ev.AddLine(Loc.GetString("nukeops-list-start")); - foreach (var nukeop in _aliveNukeops) + //it's my if-else chain and no one can tell me how to write it! + var percent = GetInfectedPercentage(); + Logger.Debug(percent.ToString()); + if (percent <= 0) + ev.AddLine(Loc.GetString("zombie-round-end-amount-none")); + else if (percent <= 0.25) + ev.AddLine(Loc.GetString("zombie-round-end-amount-low")); + else if (percent <= 0.5) + ev.AddLine(Loc.GetString("zombie-round-end-amount-medium", ("percent", (percent * 100).ToString()))); + else if (percent < 1) + ev.AddLine(Loc.GetString("zombie-round-end-amount-high", ("percent", (percent * 100).ToString()))); + else + ev.AddLine(Loc.GetString("zombie-round-end-amount-all")); + + ev.AddLine(Loc.GetString("zombie-round-end-initial-count", ("initialCount", _initialInfected.Count))); + foreach (var player in _initialInfected) { - ev.AddLine($"- {nukeop.Key.Session?.Name}"); + ev.AddLine(Loc.GetString("zombie-round-end-user-was-initial", + ("name", player.Key), + ("username", player.Value))); } } - private void OnMobStateChanged(MobStateChangedEvent ev) - { - - } - private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) { + if (!Enabled) + return; + + _initialInfected = new(); + InfectInitialPlayers(); } - private void OnPlayersSpawning(RulePlayerSpawningEvent ev) + private void OnMobStateChanged(MobStateChangedEvent ev) { if (!Enabled) return; - //these are staying here because i want the code for reference - - /* - - // TODO: Loot table or something - var commanderGear = _prototypeManager.Index("SyndicateCommanderGearFull"); - var starterGear = _prototypeManager.Index("SyndicateOperativeGearFull"); - var medicGear = _prototypeManager.Index("SyndicateOperativeMedicFull"); - - var spawns = new List(); - - // Forgive me for hardcoding prototypes - foreach (var (_, meta, xform) in EntityManager.EntityQuery(true)) - { - if (meta.EntityPrototype?.ID != "SpawnPointNukies" || xform.ParentUid != gridUid) continue; - - spawns.Add(xform.Coordinates); - } - - if (spawns.Count == 0) - { - spawns.Add(EntityManager.GetComponent(gridUid).Coordinates); - Logger.WarningS("nukies", $"Fell back to default spawn for nukies!"); - } - - // TODO: This should spawn the nukies in regardless and transfer if possible; rest should go to shot roles. - for (var i = 0; i < ops.Length; i++) - { - string name; - StartingGearPrototype gear; - - switch (i) - { - case 0: - name = $"Commander"; - gear = commanderGear; - break; - case 1: - name = $"Operator #{i}"; - gear = medicGear; - break; - default: - name = $"Operator #{i}"; - gear = starterGear; - break; - } - - var session = ops[i]; - var newMind = new Mind.Mind(session.UserId) - { - CharacterName = name - }; - newMind.ChangeOwningPlayer(session.UserId); + } - var mob = EntityManager.SpawnEntity("MobHuman", _random.Pick(spawns)); - EntityManager.GetComponent(mob).EntityName = name; + private void OnEntityZombified(EntityZombifiedEvent ev) + { + if (!Enabled) + return; - newMind.TransferTo(mob); - _stationSpawningSystem.EquipStartingGear(mob, gear, null); + //we only care about players, not monkeys and such. + if (!HasComp(ev.Target)) + return; - _aliveNukeops.Add(newMind, true); + var percent = GetInfectedPercentage(); - GameTicker.PlayerJoinGame(session); - }*/ + if (percent >= 1) + _roundEndSystem.EndRound(); } private void OnStartAttempt(RoundStartAttemptEvent ev) @@ -187,12 +156,40 @@ public override void Started(GameRuleConfiguration configuration) public override void Ended(GameRuleConfiguration configuration) { } + private FixedPoint2 GetInfectedPercentage() + { + var allPlayers = EntityQuery(); + var totalPlayers = new List(); + var livingZombies = new List(); + foreach (var ent in allPlayers) + { + if (ent.Item2.IsAlive()) + { + totalPlayers.Add(ent.Item2.Owner); + + if (HasComp(ent.Item1.Owner)) + livingZombies.Add(ent.Item2.Owner); + } + } + Logger.Debug((livingZombies.Count / totalPlayers.Count).ToString()); + return (FixedPoint2) livingZombies.Count / (FixedPoint2) totalPlayers.Count; + } + /// - /// Infects the first players with the passive zombie virus. + /// Infects the first players with the passive zombie virus. + /// Also records their names for the end of round screen. /// private void InfectInitialPlayers() { - var playerList = _playerManager.ServerSessions.ToList(); + var allPlayers = _playerManager.ServerSessions.ToList(); + var playerList = new List(); + foreach (var player in allPlayers) + { + if (player.AttachedEntity != null) + { + playerList.Add(player); + } + } if (playerList.Count == 0) return; @@ -211,7 +208,7 @@ private void InfectInitialPlayers() Logger.InfoS("preset", "Insufficient number of players. stopping selection."); break; } - IPlayerSession zombie = _random.PickAndTake(playerList); + var zombie = _random.PickAndTake(playerList); playerList.Remove(zombie); Logger.InfoS("preset", "Selected a patient 0."); @@ -221,40 +218,29 @@ private void InfectInitialPlayers() Logger.ErrorS("preset", "Failed getting mind for picked patient 0."); continue; } - + DebugTools.AssertNotNull(mind.OwnedEntity); mind.AddRole(new TraitorRole(mind, _prototypeManager.Index(PatientZeroPrototypeID))); + var inCharacterName = string.Empty; if (mind.OwnedEntity != null) - _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); //change this once zombie refactor is in. + { + _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); + inCharacterName = MetaData(mind.OwnedEntity.Value).EntityName; + } if (mind.Session != null) { var messageWrapper = Loc.GetString("chat-manager-server-wrap-message"); + //gets the names now in case the players leave. + if (inCharacterName != null) + _initialInfected.Add(inCharacterName, mind.Session.Name); + // I went all the way to ChatManager.cs and all i got was this lousy T-shirt _chatManager.ChatMessageToOne(Shared.Chat.ChatChannel.Server, Loc.GetString("zombie-patientzero-role-greeting"), messageWrapper, default, false, mind.Session.ConnectedClient, Color.Plum); } } } - - - /// - /// This event announces the nuke code and spawns - /// the disk inside of it. This is for round end - /// so the duplicated disk shouldn't really matter. - /// - private void UnlockNuke() - { - //_chatManager.(Loc.GetString("zombie-nuke-armed-event", ("code",_nukeCodeSystem.Code)), "Centcomm", default, Color.Crimson); - /*foreach (var nuke in EntityManager.EntityQuery().ToList()) - { - if (nuke.DiskSlot.ContainerSlot != null) - { - nuke.DiskSlot.ContainerSlot.Insert(Spawn("NukeDisk", Transform(nuke.Owner).Coordinates)); - } - - }*/ - } } diff --git a/Content.Server/Zombies/ZombifyOnDeathSystem.cs b/Content.Server/Zombies/ZombifyOnDeathSystem.cs index 331e36e2aeaa..73fe0f30736a 100644 --- a/Content.Server/Zombies/ZombifyOnDeathSystem.cs +++ b/Content.Server/Zombies/ZombifyOnDeathSystem.cs @@ -24,12 +24,11 @@ using Robust.Shared.Containers; using Content.Shared.Movement.Components; using Content.Shared.MobState; -using Robust.Server.GameObjects; namespace Content.Server.Zombies { /// - /// Handles zombie propagation and inherent zombie traits + /// Handles zombie propagation and inherent zombie traits /// public sealed class ZombifyOnDeathSystem : EntitySystem { @@ -38,9 +37,7 @@ public sealed class ZombifyOnDeathSystem : EntitySystem [Dependency] private readonly BloodstreamSystem _bloodstream = default!; [Dependency] private readonly ServerInventorySystem _serverInventory = default!; [Dependency] private readonly DamageableSystem _damageable = default!; - [Dependency] private readonly DiseaseSystem _disease = default!; [Dependency] private readonly SharedHumanoidAppearanceSystem _sharedHuApp = default!; - [Dependency] private readonly IChatManager _chatMan = default!; public override void Initialize() @@ -49,7 +46,7 @@ public override void Initialize() SubscribeLocalEvent(OnDamageChanged); } - + /// /// Handles an entity turning into a zombie when they die or go into crit /// @@ -67,9 +64,10 @@ private void OnDamageChanged(EntityUid uid, ZombifyOnDeathComponent component, M /// /// This is the general purpose function to call if you want to zombify an entity. - /// It handles both humanoid and nonhumanoid transformation. + /// It handles both humanoid and nonhumanoid transformation and everything should be called through it. /// /// the entity being zombified + /// the entity that zombifies it. Used for data tracking public void ZombifyEntity(EntityUid target) { if (HasComp(target)) @@ -80,19 +78,8 @@ public void ZombifyEntity(EntityUid target) RemComp(target); RemComp(target); RemComp(target); - - var zombiecomp = EnsureComp(target); - if (TryComp(target, out var huApComp)) - { - var appearance = huApComp.Appearance; - _sharedHuApp.UpdateAppearance(target, appearance.WithSkinColor(zombiecomp.SkinColor), huApComp); - _sharedHuApp.ForceAppearanceUpdate(target, huApComp); - } - - if (!HasComp(target)) - MakeSentientCommand.MakeSentient(target, EntityManager); - EnsureComp(target).Accent = "zombie"; + var zombiecomp = EnsureComp(target); //funny add delet go brrr RemComp(target); @@ -103,11 +90,18 @@ public void ZombifyEntity(EntityUid target) melee.ClickArc = zombiecomp.AttackArc; melee.Range = 0.75f; - //lord forgive me for the hardcoded damage - DamageSpecifier dspec = new(); - dspec.DamageDict.Add("Slash", 13); - dspec.DamageDict.Add("Piercing", 7); - melee.Damage = dspec; + if (TryComp(target, out var huApComp)) + { + var appearance = huApComp.Appearance; + _sharedHuApp.UpdateAppearance(target, appearance.WithSkinColor(zombiecomp.SkinColor), huApComp); + _sharedHuApp.ForceAppearanceUpdate(target, huApComp); + + //lord forgive me for the hardcoded damage + DamageSpecifier dspec = new(); + dspec.DamageDict.Add("Slash", 13); + dspec.DamageDict.Add("Piercing", 7); + melee.Damage = dspec; + } _damageable.SetDamageModifierSetId(target, "Zombie"); _bloodstream.SetBloodLossThreshold(target, 0f); @@ -115,6 +109,9 @@ public void ZombifyEntity(EntityUid target) _popupSystem.PopupEntity(Loc.GetString("zombie-transform", ("target", target)), target, Filter.Pvs(target)); _serverInventory.TryUnequip(target, "gloves", true, true); + if (!HasComp(target)) + MakeSentientCommand.MakeSentient(target, EntityManager); + if (TryComp(target, out var tempComp)) tempComp.ColdDamage.ClampMax(0); @@ -126,7 +123,7 @@ public void ZombifyEntity(EntityUid target) var mindcomp = EnsureComp(target); if (mindcomp.Mind != null && mindcomp.Mind.TryGetSession(out var session)) - _chatMan.DispatchServerMessage(session, Loc.GetString("zombie-infection-greeting")); + _chatMan.DispatchServerMessage(session, Loc.GetString("zombie-infection-greeting")); if (!HasComp(target) && !mindcomp.HasMind) //this specific component gives build test trouble so pop off, ig { @@ -143,8 +140,26 @@ public void ZombifyEntity(EntityUid target) _sharedHands.RemoveHand(target, hand.Name); } RemComp(target); - EnsureComp(target); + + RaiseLocalEvent(new EntityZombifiedEvent(target)); } } + + /// + /// Event raised whenever an entity is zombified. + /// Used by the zombie gamemode to track total infections. + /// + public sealed class EntityZombifiedEvent : EventArgs + { + /// + /// The entity that was zombified. + /// + public EntityUid Target; + + public EntityZombifiedEvent(EntityUid target) + { + Target = target; + } + }; } diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index b3ce4a665a26..ceb6590b5717 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -8,4 +8,16 @@ zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get s zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. A disk has been automatically teleported inside of it. The code to detonate the device is: {$code}. zombie-end-nuke-armed-event-fail = The nuke was not detonated. -zombie-end-nuke-armed-eveent-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. \ No newline at end of file +zombie-end-nuke-armed-event-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. + +zombie-round-end-initial-count = {$initialCount -> + [one] There was one initial infected. + *[other] There were {$initialCount} initial infected. +} +zombie-round-end-user-was-initial = - [color=Plum]{$name}[/color] ([color=gray]{$username}[/color]) was one of the initial infected. + +zombie-round-end-amount-none = [color=green]All of the zombies were eradicated![/color] +zombie-round-end-amount-low = [color=green]Almost all of the zombies were exterminated.[/color] +zombie-round-end-amount-medium = [color=yellow]{$percent}% of the crew were turned into zombies.[/color] +zombie-round-end-amount-high = [color=crimson]{$percent}% of the crew were turned into zombies.[/color] +zombie-round-end-amount-all = [color=darkred]The entire crew became zombies![/color] \ No newline at end of file diff --git a/Resources/Locale/en-US/zombies/zombie.ftl b/Resources/Locale/en-US/zombies/zombie.ftl index 606717ed3501..21405eda95f1 100644 --- a/Resources/Locale/en-US/zombies/zombie.ftl +++ b/Resources/Locale/en-US/zombies/zombie.ftl @@ -2,6 +2,6 @@ zombie-transform = {CAPITALIZE(THE($target))} turned into a zombie! zombie-infection-greeting = You have become a zombie. Your goal is to seek out the living and to try to infect them. Work together with your fellow zombies to overpower the remaining crewmates. zombie-generic = zombie -zombie-name-prefix = zombified {$target} +zombie-name-prefix = Zombie {$target} zombie-role-desc = A malevolent creature of the dead. zombie-role-rules = You are an antagonist. Search out the living and bite them in order to infect them and turn them into zombies. Work together with other the zombies to overtake the station. From d02cd0f13c4478c96b4aa98128975188812997a4 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Fri, 17 Jun 2022 11:41:10 -0400 Subject: [PATCH 23/40] prototype fix --- Content.Server/GameTicking/Rules/NukeopsRuleSystem.cs | 2 +- Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Content.Server/GameTicking/Rules/NukeopsRuleSystem.cs b/Content.Server/GameTicking/Rules/NukeopsRuleSystem.cs index c3d581092537..109237acc7f9 100644 --- a/Content.Server/GameTicking/Rules/NukeopsRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/NukeopsRuleSystem.cs @@ -1,4 +1,4 @@ -using System.Linq; +using System.Linq; using Content.Server.CharacterAppearance.Components; using Content.Server.Chat.Managers; using Content.Server.GameTicking.Rules.Configurations; diff --git a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml index add7eff98850..a0b6874dd8d4 100644 --- a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml +++ b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml @@ -152,7 +152,7 @@ shoes: ClothingShoesBootsJack id: CentcomPDA pocket1: CombatKnife - pocket2: LaserGun + pocket2: WeaponLaserGun suitstorage: YellowOxygenTankFilled belt: ClothingBeltBandolier innerclothingskirt: ClothingUniformJumpsuitColorBrown From 11f432f97930850d13bf400d26b3db3a401b6a52 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Fri, 17 Jun 2022 16:49:56 -0400 Subject: [PATCH 24/40] zombie code cleanup + warnings + my life --- .../GameTicking/Rules/ZombieRuleSystem.cs | 18 ++++- Content.Server/Zombies/ZombieComponent.cs | 25 +++++++ .../Zombies/ZombifyOnDeathComponent.cs | 9 +-- .../Zombies/ZombifyOnDeathSystem.cs | 74 +++++++++++++++---- .../game-presets/preset-zombies.ftl | 4 +- Resources/Prototypes/Roles/Antags/zombie.yml | 13 +++- 6 files changed, 111 insertions(+), 32 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 0d52c5ebfa5e..b7ead549d6fa 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -49,7 +49,7 @@ public sealed class ZombieRuleSystem : GameRuleSystem private Dictionary _initialInfected = new(); public override string Prototype => "Zombie"; - private const string PatientZeroPrototypeID = "PatientZero"; + private const string PatientZeroPrototypeID = "InitialInfected"; private const string InitialZombieVirusPrototype = "ActiveZombieVirus"; public override void Initialize() @@ -70,9 +70,9 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) if (!Enabled) return; - //it's my if-else chain and no one can tell me how to write it! + //this is just the general condition thing used for determining the win/lose text var percent = GetInfectedPercentage(); - Logger.Debug(percent.ToString()); + if (percent <= 0) ev.AddLine(Loc.GetString("zombie-round-end-amount-none")); else if (percent <= 0.25) @@ -103,10 +103,22 @@ private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) InfectInitialPlayers(); } + /// + /// This is just checked if the last human somehow dies + /// by starving or flying off into space. + /// private void OnMobStateChanged(MobStateChangedEvent ev) { if (!Enabled) return; + + if (!HasComp(ev.Entity)) + return; + + var percent = GetInfectedPercentage(); + + if (percent >= 1) + _roundEndSystem.EndRound(); } private void OnEntityZombified(EntityZombifiedEvent ev) diff --git a/Content.Server/Zombies/ZombieComponent.cs b/Content.Server/Zombies/ZombieComponent.cs index 7366590a9009..926d74fb372b 100644 --- a/Content.Server/Zombies/ZombieComponent.cs +++ b/Content.Server/Zombies/ZombieComponent.cs @@ -1,3 +1,7 @@ +using Content.Shared.Roles; +using Content.Shared.Weapons.Melee; +using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom.Prototype; + namespace Content.Server.Zombies { [RegisterComponent] @@ -7,17 +11,38 @@ public sealed class ZombieComponent : Component /// The coefficient of the damage reduction applied when a zombie /// attacks another zombie. longe name /// + [ViewVariables] public float OtherZombieDamageCoefficient = 0.75f; /// /// The baseline infection chance you have if you are completely nude /// + [ViewVariables] public float MaxZombieInfectionChance = 0.75f; /// /// The minimum infection chance possible. This is simply to prevent /// being invincible by bundling up. /// + [ViewVariables] public float MinZombieInfectionChance = 0.1f; + + /// + /// The skin color of the zombie + /// + [ViewVariables, DataField("skinColor")] + public Color SkinColor = new Color(0.70f, 0.72f, 0.48f, 1); + + /// + /// The attack arc of the zombie + /// + [ViewVariables, DataField("attackArc", customTypeSerializer: typeof(PrototypeIdSerializer))] + public string AttackArc = "claw"; + + /// + /// The role prototype of the zombie antag role + /// + [ViewVariables, DataField("zombieRoldId", customTypeSerializer: typeof(PrototypeIdSerializer))] + public readonly string ZombieRoleId = "Zombie"; } } diff --git a/Content.Server/Zombies/ZombifyOnDeathComponent.cs b/Content.Server/Zombies/ZombifyOnDeathComponent.cs index c43ad57f5100..793e356eeb99 100644 --- a/Content.Server/Zombies/ZombifyOnDeathComponent.cs +++ b/Content.Server/Zombies/ZombifyOnDeathComponent.cs @@ -1,15 +1,8 @@ -using Content.Shared.Weapons.Melee; -using Robust.Shared.Serialization.TypeSerializers.Implementations.Custom.Prototype; - namespace Content.Server.Zombies { [RegisterComponent] public sealed class ZombifyOnDeathComponent : Component { - [DataField("skinColor")] - public Color SkinColor = new Color(0.70f, 0.72f, 0.48f, 1); - - [DataField("attackArc", customTypeSerializer: typeof(PrototypeIdSerializer))] - public string AttackArc = "claw"; + //this is not the component you are looking for } } diff --git a/Content.Server/Zombies/ZombifyOnDeathSystem.cs b/Content.Server/Zombies/ZombifyOnDeathSystem.cs index 73fe0f30736a..5580803d3432 100644 --- a/Content.Server/Zombies/ZombifyOnDeathSystem.cs +++ b/Content.Server/Zombies/ZombifyOnDeathSystem.cs @@ -20,16 +20,21 @@ using Content.Server.Mind.Commands; using Content.Server.Temperature.Components; using Content.Server.Weapon.Melee.Components; -using Content.Server.Disease; using Robust.Shared.Containers; using Content.Shared.Movement.Components; using Content.Shared.MobState; +using Robust.Shared.Prototypes; +using Content.Shared.Roles; +using Content.Server.Traitor; namespace Content.Server.Zombies { /// /// Handles zombie propagation and inherent zombie traits /// + /// + /// Don't Shitcode Open Inside + /// public sealed class ZombifyOnDeathSystem : EntitySystem { [Dependency] private readonly SharedHandsSystem _sharedHands = default!; @@ -39,6 +44,7 @@ public sealed class ZombifyOnDeathSystem : EntitySystem [Dependency] private readonly DamageableSystem _damageable = default!; [Dependency] private readonly SharedHumanoidAppearanceSystem _sharedHuApp = default!; [Dependency] private readonly IChatManager _chatMan = default!; + [Dependency] private readonly IPrototypeManager _proto = default!; public override void Initialize() { @@ -52,87 +58,123 @@ public override void Initialize() /// private void OnDamageChanged(EntityUid uid, ZombifyOnDeathComponent component, MobStateChangedEvent args) { - if (!TryComp(uid, out var mobstate)) - return; - - if (mobstate.IsDead() || - mobstate.IsCritical()) + if (args.CurrentMobState.IsDead() || + args.CurrentMobState.IsCritical()) { ZombifyEntity(uid); } } /// - /// This is the general purpose function to call if you want to zombify an entity. - /// It handles both humanoid and nonhumanoid transformation and everything should be called through it. + /// This is the general purpose function to call if you want to zombify an entity. + /// It handles both humanoid and nonhumanoid transformation and everything should be called through it. /// /// the entity being zombified - /// the entity that zombifies it. Used for data tracking + /// + /// ALRIGHT BIG BOY. YOU'VE COME TO THE LAYER OF THE BEAST. THIS IS YOUR WARNING. + /// This function is the god function for zombie stuff, and it is cursed. I have + /// attempted to label everything thouroughly for your sanity. It has been attempted to be + /// rewritten, but this is how it shall lie eternal. Turn back now. + /// -emo + /// public void ZombifyEntity(EntityUid target) { + //Don't zombfiy zombies if (HasComp(target)) return; + //you're a real zombie now, son. + var zombiecomp = EnsureComp(target); + + ///we need to basically remove all of these because zombies shouldn't + ///get diseases, breath, be thirst, be hungry, or die in space RemComp(target); RemComp(target); RemComp(target); RemComp(target); RemComp(target); + + //funny voice EnsureComp(target).Accent = "zombie"; - var zombiecomp = EnsureComp(target); - //funny add delet go brrr + ///This is needed for stupid entities that fuck up combat mode component + ///in an attempt to make an entity not attack. This is the easiest way to do it. RemComp(target); AddComp(target); + ///This is the actual damage of the zombie. We assign the visual appearance + ///and range here because of stuff we'll find out later var melee = EnsureComp(target); melee.Arc = zombiecomp.AttackArc; melee.ClickArc = zombiecomp.AttackArc; melee.Range = 0.75f; - if (TryComp(target, out var huApComp)) + //We have specific stuff for humanoid zombies because they matter more + if (TryComp(target, out var huApComp)) //huapcomp { + //this bs is done because you can't directly update humanoid appearances var appearance = huApComp.Appearance; _sharedHuApp.UpdateAppearance(target, appearance.WithSkinColor(zombiecomp.SkinColor), huApComp); _sharedHuApp.ForceAppearanceUpdate(target, huApComp); - //lord forgive me for the hardcoded damage + ///This is done here because non-humanoids shouldn't get baller damage + ///lord forgive me for the hardcoded damage DamageSpecifier dspec = new(); dspec.DamageDict.Add("Slash", 13); dspec.DamageDict.Add("Piercing", 7); melee.Damage = dspec; } + //The zombie gets the assigned damage weaknesses and strengths _damageable.SetDamageModifierSetId(target, "Zombie"); + + ///This makes it so the zombie doesn't take bloodloss damage. + ///NOTE: they are supposed to bleed, just not take damage _bloodstream.SetBloodLossThreshold(target, 0f); - _popupSystem.PopupEntity(Loc.GetString("zombie-transform", ("target", target)), target, Filter.Pvs(target)); + //This is specifically here to combat insuls, because frying zombies on grilles is funny as shit. _serverInventory.TryUnequip(target, "gloves", true, true); - if (!HasComp(target)) + //popup + _popupSystem.PopupEntity(Loc.GetString("zombie-transform", ("target", target)), target, Filter.Pvs(target)); + + //Make it sentient if it's an animal or something + if (!HasComp(target)) //this component is cursed and fucks shit up MakeSentientCommand.MakeSentient(target, EntityManager); + //Make the zombie not die in the cold. Good for space zombies if (TryComp(target, out var tempComp)) tempComp.ColdDamage.ClampMax(0); + //Heals the zombie from all the damage it took while human if (TryComp(target, out var damageablecomp)) _damageable.SetAllDamage(damageablecomp, 0); + //gives it the funny "Zombie ___" name. if (TryComp(target, out var meta)) meta.EntityName = Loc.GetString("zombie-name-prefix", ("target", meta.EntityName)); + //He's gotta have a mind var mindcomp = EnsureComp(target); if (mindcomp.Mind != null && mindcomp.Mind.TryGetSession(out var session)) + { + //Zombie role for player manifest + mindcomp.Mind.AddRole(new TraitorRole(mindcomp.Mind, _proto.Index(zombiecomp.ZombieRoleId))); + //Greeting message for new bebe zombers _chatMan.DispatchServerMessage(session, Loc.GetString("zombie-infection-greeting")); + } if (!HasComp(target) && !mindcomp.HasMind) //this specific component gives build test trouble so pop off, ig { + //yet more hardcoding. Visit zombie.ftl for more information. EntityManager.EnsureComponent(target, out var ghostcomp); ghostcomp.RoleName = Loc.GetString("zombie-generic"); ghostcomp.RoleDescription = Loc.GetString("zombie-role-desc"); ghostcomp.RoleRules = Loc.GetString("zombie-role-rules"); } + ///Goes through every hand, drops the items in it, then removes the hand + ///may become the source of various bugs. foreach (var hand in _sharedHands.EnumerateHands(target)) { _sharedHands.SetActiveHand(target, hand); @@ -140,8 +182,8 @@ public void ZombifyEntity(EntityUid target) _sharedHands.RemoveHand(target, hand.Name); } RemComp(target); - EnsureComp(target); + //zombie gamemode stuff RaiseLocalEvent(new EntityZombifiedEvent(target)); } } diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index ceb6590b5717..210ef5a78eb3 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -1,10 +1,10 @@ zombie-title = Zombies -zombie-description = A virus able to create the undead has been unleashed unto the station! Work with your crewmates to contain the outbreak and survive. +zombie-description = A virus able to animate the dead has been unleashed unto the station! Work with your crewmates to contain the outbreak and survive. zombie-not-enough-ready-players = Not enough players readied up for the game! There were {$readyPlayersCount} players readied up out of {$minimumPlayers} needed. Can't start Zombies. zombie-no-one-ready = No players readied up! Can't start Zombies. -zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to infect the crew once you turn into a zombie. +zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to turn once you die. zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. A disk has been automatically teleported inside of it. The code to detonate the device is: {$code}. zombie-end-nuke-armed-event-fail = The nuke was not detonated. diff --git a/Resources/Prototypes/Roles/Antags/zombie.yml b/Resources/Prototypes/Roles/Antags/zombie.yml index d69d8f24ac7b..42924da68108 100644 --- a/Resources/Prototypes/Roles/Antags/zombie.yml +++ b/Resources/Prototypes/Roles/Antags/zombie.yml @@ -1,6 +1,13 @@ - type: antag - id: PatientZero - name: "Patient 0" + id: InitialInfected + name: "Initial Infected" antagonist: true setPreference: false - objective: "Once you turn, infect as many other crew members as possible" \ No newline at end of file + objective: "Once you turn, infect as many other crew members as possible" + +- type: antag + id: Zombie + name: "Zombie" + antagonist: true + setPreference: false + objective: "Turn as many humans as possible into zombies." \ No newline at end of file From 1447f7a472a261c03a8375cfdbf17898c90c1bcc Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Fri, 17 Jun 2022 21:19:30 -0400 Subject: [PATCH 25/40] fixes and shit --- .../GameTicking/Rules/ZombieRuleSystem.cs | 54 +++++++++++-------- .../Zombies/ZombifyOnDeathSystem.cs | 4 +- .../game-presets/preset-zombies.ftl | 12 +++-- Resources/Prototypes/Diseases/zombie.yml | 16 +++++- Resources/Prototypes/game_presets.yml | 3 ++ Resources/Prototypes/zombie_weights.yml | 0 6 files changed, 60 insertions(+), 29 deletions(-) delete mode 100644 Resources/Prototypes/zombie_weights.yml diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index b7ead549d6fa..b2951c9bf5c0 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -2,13 +2,9 @@ using Content.Server.Chat.Managers; using Content.Server.Disease; using Content.Server.GameTicking.Rules.Configurations; -using Content.Server.Nuke; +using Content.Server.Mind.Components; using Content.Server.Players; -using Content.Server.Roles; using Content.Server.RoundEnd; -using Content.Server.Spawners.Components; -using Content.Server.Station.Components; -using Content.Server.Station.Systems; using Content.Server.Traitor; using Content.Server.Zombies; using Content.Shared.CCVar; @@ -16,14 +12,9 @@ using Content.Shared.FixedPoint; using Content.Shared.MobState; using Content.Shared.MobState.Components; -using Content.Shared.Random; -using Content.Shared.Random.Helpers; using Content.Shared.Roles; -using Robust.Server.Maps; using Robust.Server.Player; using Robust.Shared.Configuration; -using Robust.Shared.Map; -using Robust.Shared.Physics.Collision.Shapes; using Robust.Shared.Prototypes; using Robust.Shared.Random; using Robust.Shared.Utility; @@ -36,28 +27,23 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly IRobustRandom _random = default!; [Dependency] private readonly IConfigurationManager _cfg = default!; [Dependency] private readonly IChatManager _chatManager = default!; - [Dependency] private readonly IMapLoader _mapLoader = default!; - [Dependency] private readonly IMapManager _mapManager = default!; [Dependency] private readonly IPlayerManager _playerManager = default!; - [Dependency] private readonly StationSpawningSystem _stationSpawningSystem = default!; - [Dependency] private readonly StationSystem _stationSystem = default!; [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; - [Dependency] private readonly NukeSystem _nukeSystem = default!; - [Dependency] private readonly NukeCodeSystem _nukeCodeSystem = default!; private Dictionary _initialInfected = new(); public override string Prototype => "Zombie"; private const string PatientZeroPrototypeID = "InitialInfected"; - private const string InitialZombieVirusPrototype = "ActiveZombieVirus"; + private const string InitialZombieVirusPrototype = "PassiveZombieVirus"; + + private const int LastSurvivorsThreshold = 6; public override void Initialize() { base.Initialize(); SubscribeLocalEvent(OnStartAttempt); - //SubscribeLocalEvent(OnPlayersSpawning); SubscribeLocalEvent(OnMobStateChanged); SubscribeLocalEvent(OnRoundEndText); SubscribeLocalEvent(OnJobAssigned); @@ -71,7 +57,7 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) return; //this is just the general condition thing used for determining the win/lose text - var percent = GetInfectedPercentage(); + var percent = GetInfectedPercentage(out var livingHumans); if (percent <= 0) ev.AddLine(Loc.GetString("zombie-round-end-amount-none")); @@ -91,6 +77,25 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) ("name", player.Key), ("username", player.Value))); } + + //Gets a bunch of the living players and displays them if they're under a threshold. + if (percent > 0 && livingHumans.Count < LastSurvivorsThreshold) + { + ev.AddLine(""); + ev.AddLine(Loc.GetString("zombie-round-end-survivor-count", ("count", 1))); + foreach (var survivor in livingHumans) + { + var meta = MetaData(survivor); + var username = string.Empty; + if (TryComp(survivor, out var mindcomp)) + if (mindcomp.Mind != null && mindcomp.Mind.Session != null) + username = mindcomp.Mind.Session.Name; + + ev.AddLine(Loc.GetString("zombie-round-end-user-was-survivor", + ("name", meta.EntityName), + ("username", username))); + } + } } private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) @@ -115,7 +120,7 @@ private void OnMobStateChanged(MobStateChangedEvent ev) if (!HasComp(ev.Entity)) return; - var percent = GetInfectedPercentage(); + var percent = GetInfectedPercentage(out var _); if (percent >= 1) _roundEndSystem.EndRound(); @@ -130,7 +135,7 @@ private void OnEntityZombified(EntityZombifiedEvent ev) if (!HasComp(ev.Target)) return; - var percent = GetInfectedPercentage(); + var percent = GetInfectedPercentage(out var _); if (percent >= 1) _roundEndSystem.EndRound(); @@ -168,11 +173,12 @@ public override void Started(GameRuleConfiguration configuration) public override void Ended(GameRuleConfiguration configuration) { } - private FixedPoint2 GetInfectedPercentage() + private FixedPoint2 GetInfectedPercentage(out List livingHumans) { var allPlayers = EntityQuery(); var totalPlayers = new List(); var livingZombies = new List(); + livingHumans = new(); foreach (var ent in allPlayers) { if (ent.Item2.IsAlive()) @@ -181,9 +187,11 @@ private FixedPoint2 GetInfectedPercentage() if (HasComp(ent.Item1.Owner)) livingZombies.Add(ent.Item2.Owner); + else + livingHumans.Add(ent.Item2.Owner); } } - Logger.Debug((livingZombies.Count / totalPlayers.Count).ToString()); + //Logger.Debug((livingZombies.Count / totalPlayers.Count).ToString()); return (FixedPoint2) livingZombies.Count / (FixedPoint2) totalPlayers.Count; } diff --git a/Content.Server/Zombies/ZombifyOnDeathSystem.cs b/Content.Server/Zombies/ZombifyOnDeathSystem.cs index 5580803d3432..0f5f85a8655b 100644 --- a/Content.Server/Zombies/ZombifyOnDeathSystem.cs +++ b/Content.Server/Zombies/ZombifyOnDeathSystem.cs @@ -73,8 +73,8 @@ private void OnDamageChanged(EntityUid uid, ZombifyOnDeathComponent component, M /// /// ALRIGHT BIG BOY. YOU'VE COME TO THE LAYER OF THE BEAST. THIS IS YOUR WARNING. /// This function is the god function for zombie stuff, and it is cursed. I have - /// attempted to label everything thouroughly for your sanity. It has been attempted to be - /// rewritten, but this is how it shall lie eternal. Turn back now. + /// attempted to label everything thouroughly for your sanity. It have attempted to + /// rewrite this, but this is how it shall lie eternal. Turn back now. /// -emo /// public void ZombifyEntity(EntityUid target) diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index 210ef5a78eb3..fb8065e719a0 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -11,8 +11,8 @@ zombie-end-nuke-armed-event-fail = The nuke was not detonated. zombie-end-nuke-armed-event-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. zombie-round-end-initial-count = {$initialCount -> - [one] There was one initial infected. - *[other] There were {$initialCount} initial infected. + [one] There was one initial infected: + *[other] There were {$initialCount} initial infected: } zombie-round-end-user-was-initial = - [color=Plum]{$name}[/color] ([color=gray]{$username}[/color]) was one of the initial infected. @@ -20,4 +20,10 @@ zombie-round-end-amount-none = [color=green]All of the zombies were eradicated![ zombie-round-end-amount-low = [color=green]Almost all of the zombies were exterminated.[/color] zombie-round-end-amount-medium = [color=yellow]{$percent}% of the crew were turned into zombies.[/color] zombie-round-end-amount-high = [color=crimson]{$percent}% of the crew were turned into zombies.[/color] -zombie-round-end-amount-all = [color=darkred]The entire crew became zombies![/color] \ No newline at end of file +zombie-round-end-amount-all = [color=darkred]The entire crew became zombies![/color] + +zombie-round-end-survivor-count = {$count -> + [one] There was only one survivor left: + *[other] There were only {$count} survivors left: +} +zombie-round-end-user-was-survivor = - [color=White]{$name}[/color] ([color=gray]{$username}[/color]) survived the outbreak. \ No newline at end of file diff --git a/Resources/Prototypes/Diseases/zombie.yml b/Resources/Prototypes/Diseases/zombie.yml index cbdca7bbafe5..76564e344855 100644 --- a/Resources/Prototypes/Diseases/zombie.yml +++ b/Resources/Prototypes/Diseases/zombie.yml @@ -23,4 +23,18 @@ cures: - !type:DiseaseReagentCure reagent: Romerol - min: 5 \ No newline at end of file + min: 5 + +- type: disease + id: PassiveZombieVirus + name: Zombie Virus + infectious: false + cureResist: 1 #no cure. Death is your cure. + effects: + - !type:DiseaseHealthChange #roughly procs once a minute, takes 20 minutes to kill. + probability: 0.016 + damage: + types: + Cellular: 5 + - !type:DiseaseAddComponent + comp: ZombifyOnDeath \ No newline at end of file diff --git a/Resources/Prototypes/game_presets.yml b/Resources/Prototypes/game_presets.yml index 3343dd0ec9bb..77d7267f0b6a 100644 --- a/Resources/Prototypes/game_presets.yml +++ b/Resources/Prototypes/game_presets.yml @@ -85,6 +85,9 @@ alias: - zombie - zombies + - Zombies + - zz14 + - zomber name: zombie-title description: zombie-description showInVote: true diff --git a/Resources/Prototypes/zombie_weights.yml b/Resources/Prototypes/zombie_weights.yml deleted file mode 100644 index e69de29bb2d1..000000000000 From 135fb69b30b1bb30cb14b94a0a2a2f1d1e6bb2bc Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sat, 18 Jun 2022 19:56:40 -0400 Subject: [PATCH 26/40] aaaa --- .../Body/Systems/BodyReassembleSystem.cs | 2 +- .../GameTicking/Rules/ZombieRuleSystem.cs | 65 +++++++++++++----- .../Zombies/ZombifyOnDeathSystem.cs | 26 +++---- Content.Shared/Zombies/ZombieEvents.cs | 24 +++++++ .../game-presets/preset-zombies.ftl | 2 + Resources/Prototypes/Diseases/zombie.yml | 5 -- Resources/Prototypes/Roles/Antags/zombie.yml | 2 +- .../Textures/Interface/Actions/meta.json | 15 ++-- .../Interface/Actions/zombie-turn.png | Bin 0 -> 848 bytes 9 files changed, 92 insertions(+), 49 deletions(-) create mode 100644 Content.Shared/Zombies/ZombieEvents.cs create mode 100644 Resources/Textures/Interface/Actions/zombie-turn.png diff --git a/Content.Server/Body/Systems/BodyReassembleSystem.cs b/Content.Server/Body/Systems/BodyReassembleSystem.cs index 03fab94e40b5..eea7d216567e 100644 --- a/Content.Server/Body/Systems/BodyReassembleSystem.cs +++ b/Content.Server/Body/Systems/BodyReassembleSystem.cs @@ -192,7 +192,7 @@ private void UpdateDNAEntry(EntityUid uid, EntityUid body) if (mindcomp.Mind == null) return; - + if (mindcomp.Mind.UserId == null) return; diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index b2951c9bf5c0..bf9ba8a6fd60 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -4,6 +4,8 @@ using Content.Server.GameTicking.Rules.Configurations; using Content.Server.Mind.Components; using Content.Server.Players; +using Content.Server.Popups; +using Content.Server.Preferences.Managers; using Content.Server.RoundEnd; using Content.Server.Traitor; using Content.Server.Zombies; @@ -12,9 +14,12 @@ using Content.Shared.FixedPoint; using Content.Shared.MobState; using Content.Shared.MobState.Components; +using Content.Shared.Preferences; using Content.Shared.Roles; +using Content.Shared.Zombies; using Robust.Server.Player; using Robust.Shared.Configuration; +using Robust.Shared.Player; using Robust.Shared.Prototypes; using Robust.Shared.Random; using Robust.Shared.Utility; @@ -28,8 +33,10 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly IConfigurationManager _cfg = default!; [Dependency] private readonly IChatManager _chatManager = default!; [Dependency] private readonly IPlayerManager _playerManager = default!; + [Dependency] private readonly IServerPreferencesManager _prefs = default!; [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; + [Dependency] private readonly PopupSystem _popup = default!; private Dictionary _initialInfected = new(); @@ -116,28 +123,31 @@ private void OnMobStateChanged(MobStateChangedEvent ev) { if (!Enabled) return; - - if (!HasComp(ev.Entity)) - return; - - var percent = GetInfectedPercentage(out var _); - - if (percent >= 1) - _roundEndSystem.EndRound(); + CheckRoundEnd(ev.Entity); } private void OnEntityZombified(EntityZombifiedEvent ev) { if (!Enabled) return; + CheckRoundEnd(ev.Target); + } + /// + /// The big kahoona function for checking if the round is gonna end + /// + /// depending on this uid, we should care about the round ending + private void CheckRoundEnd(EntityUid target) + { //we only care about players, not monkeys and such. - if (!HasComp(ev.Target)) + if (!HasComp(target)) return; - var percent = GetInfectedPercentage(out var _); + var percent = GetInfectedPercentage(out var num); - if (percent >= 1) + if (num.Count == 1) //only one left + _popup.PopupEntity(Loc.GetString("zombie-alone"), num[0], Filter.Entities(num[0])); + if (percent >= 1) //oops, all zombies _roundEndSystem.EndRound(); } @@ -191,7 +201,6 @@ private FixedPoint2 GetInfectedPercentage(out List livingHumans) livingHumans.Add(ent.Item2.Owner); } } - //Logger.Debug((livingZombies.Count / totalPlayers.Count).ToString()); return (FixedPoint2) livingZombies.Count / (FixedPoint2) totalPlayers.Count; } @@ -199,15 +208,25 @@ private FixedPoint2 GetInfectedPercentage(out List livingHumans) /// Infects the first players with the passive zombie virus. /// Also records their names for the end of round screen. /// + /// + /// The reason this code is written separately is to facilitate + /// allowing this gamemode to be started midround. As such, it doesn't need + /// any information besides just running. + /// private void InfectInitialPlayers() { var allPlayers = _playerManager.ServerSessions.ToList(); var playerList = new List(); + var prefList = new List(); foreach (var player in allPlayers) { if (player.AttachedEntity != null) { playerList.Add(player); + + var pref = (HumanoidCharacterProfile) _prefs.GetPreferences(player.UserId).SelectedCharacter; + if (pref.AntagPreferences.Contains(PatientZeroPrototypeID)) + prefList.Add(player); } } @@ -223,14 +242,23 @@ private void InfectInitialPlayers() for (var i = 0; i < numInfected; i++) { - if (playerList.Count == 0) + IPlayerSession zombie; + if (prefList.Count == 0) { - Logger.InfoS("preset", "Insufficient number of players. stopping selection."); - break; + if(playerList.Count == 0) + { + Logger.InfoS("preset", "Insufficient number of players. stopping selection."); + break; + } + zombie = _random.PickAndTake(playerList); + Logger.InfoS("preset", "Insufficient preferred patient 0, picking at random."); + } + else + { + zombie = _random.PickAndTake(prefList); + playerList.Remove(zombie); + Logger.InfoS("preset", "Selected a patient 0."); } - var zombie = _random.PickAndTake(playerList); - playerList.Remove(zombie); - Logger.InfoS("preset", "Selected a patient 0."); var mind = zombie.Data.ContentData()?.Mind; if (mind == null) @@ -242,6 +270,7 @@ private void InfectInitialPlayers() DebugTools.AssertNotNull(mind.OwnedEntity); mind.AddRole(new TraitorRole(mind, _prototypeManager.Index(PatientZeroPrototypeID))); + var inCharacterName = string.Empty; if (mind.OwnedEntity != null) { diff --git a/Content.Server/Zombies/ZombifyOnDeathSystem.cs b/Content.Server/Zombies/ZombifyOnDeathSystem.cs index 0f5f85a8655b..1877bfcfb571 100644 --- a/Content.Server/Zombies/ZombifyOnDeathSystem.cs +++ b/Content.Server/Zombies/ZombifyOnDeathSystem.cs @@ -26,6 +26,7 @@ using Robust.Shared.Prototypes; using Content.Shared.Roles; using Content.Server.Traitor; +using Content.Shared.Zombies; namespace Content.Server.Zombies { @@ -51,8 +52,9 @@ public override void Initialize() base.Initialize(); SubscribeLocalEvent(OnDamageChanged); + SubscribeLocalEvent(OnZombifySelf); } - + /// /// Handles an entity turning into a zombie when they die or go into crit /// @@ -65,6 +67,11 @@ private void OnDamageChanged(EntityUid uid, ZombifyOnDeathComponent component, M } } + private void OnZombifySelf(EntityUid uid, ZombifyOnDeathComponent component, ZombifySelfActionEvent args) + { + ZombifyEntity(uid); + } + /// /// This is the general purpose function to call if you want to zombify an entity. /// It handles both humanoid and nonhumanoid transformation and everything should be called through it. @@ -187,21 +194,4 @@ public void ZombifyEntity(EntityUid target) RaiseLocalEvent(new EntityZombifiedEvent(target)); } } - - /// - /// Event raised whenever an entity is zombified. - /// Used by the zombie gamemode to track total infections. - /// - public sealed class EntityZombifiedEvent : EventArgs - { - /// - /// The entity that was zombified. - /// - public EntityUid Target; - - public EntityZombifiedEvent(EntityUid target) - { - Target = target; - } - }; } diff --git a/Content.Shared/Zombies/ZombieEvents.cs b/Content.Shared/Zombies/ZombieEvents.cs new file mode 100644 index 000000000000..696bc48759a8 --- /dev/null +++ b/Content.Shared/Zombies/ZombieEvents.cs @@ -0,0 +1,24 @@ +using Content.Shared.Actions.ActionTypes; + +namespace Content.Shared.Zombies; +/// +/// Event raised whenever an entity is zombified. +/// Used by the zombie gamemode to track total infections. +/// +public sealed class EntityZombifiedEvent : EventArgs +{ + /// + /// The entity that was zombified. + /// + public EntityUid Target; + + public EntityZombifiedEvent(EntityUid target) + { + Target = target; + } +}; + +/// +/// Event raised when a player zombifies themself using the "turn" action +/// +public sealed class ZombifySelfActionEvent : InstantAction { }; diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index fb8065e719a0..3244a1765761 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -10,6 +10,8 @@ zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the zombie-end-nuke-armed-event-fail = The nuke was not detonated. zombie-end-nuke-armed-event-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. +zombie-alone = You feel entirely alone. + zombie-round-end-initial-count = {$initialCount -> [one] There was one initial infected: *[other] There were {$initialCount} initial infected: diff --git a/Resources/Prototypes/Diseases/zombie.yml b/Resources/Prototypes/Diseases/zombie.yml index 76564e344855..086685c02d61 100644 --- a/Resources/Prototypes/Diseases/zombie.yml +++ b/Resources/Prototypes/Diseases/zombie.yml @@ -31,10 +31,5 @@ infectious: false cureResist: 1 #no cure. Death is your cure. effects: - - !type:DiseaseHealthChange #roughly procs once a minute, takes 20 minutes to kill. - probability: 0.016 - damage: - types: - Cellular: 5 - !type:DiseaseAddComponent comp: ZombifyOnDeath \ No newline at end of file diff --git a/Resources/Prototypes/Roles/Antags/zombie.yml b/Resources/Prototypes/Roles/Antags/zombie.yml index 42924da68108..3da86c05558b 100644 --- a/Resources/Prototypes/Roles/Antags/zombie.yml +++ b/Resources/Prototypes/Roles/Antags/zombie.yml @@ -2,7 +2,7 @@ id: InitialInfected name: "Initial Infected" antagonist: true - setPreference: false + setPreference: true objective: "Once you turn, infect as many other crew members as possible" - type: antag diff --git a/Resources/Textures/Interface/Actions/meta.json b/Resources/Textures/Interface/Actions/meta.json index 316ef865c008..251c2a881fdf 100644 --- a/Resources/Textures/Interface/Actions/meta.json +++ b/Resources/Textures/Interface/Actions/meta.json @@ -19,11 +19,14 @@ { "name": "disarm" }, - { - "name": "harm" - }, - { - "name": "manifest" - } + { + "name": "harm" + }, + { + "name": "manifest" + }, + { + "name": "zombie-turn" + } ] } diff --git a/Resources/Textures/Interface/Actions/zombie-turn.png b/Resources/Textures/Interface/Actions/zombie-turn.png new file mode 100644 index 0000000000000000000000000000000000000000..b9dfad21118c6ef571be5724d9e3f60c0c022801 GIT binary patch literal 848 zcmV-W1F!svP)Px&3Q0skR9J=WmO)4(R~W~CDbhU*Aw#POF+qh6o(7Me_c#Q4s9yF|_D~oG(iQd~ zc#z=1vn64eoAkP5CAH8gDAYZsdy)`gv9Laji@K~Rl8V;y^^{!3Qxoh1gQe%(Rm8x3oWJ?0-x$O2W6 z8Av7JN*sa8Z@)-(Y65^Kz-w=bue~JzK9A?ALZV0{jzIhO23O-345T0M127)XvwC&` zz}49W`w96HMW9xz$=uvr>S%kHOK*wn%J;n6e#77GzqmTP;Anf7Cka!K7`0kW;JOZ0 zpFNe;XHV~S5)!NReP1RgCmH_o589{gj@`;w9KQRCt*tGhC^F_vlmg%PMJWZq#^yQ4 z-$hs%3oB!>v3U-FQVQSqjiX^KAP52}6bb;8%Vk{Gypdma2$ur%S!4H$LYKu9vJDXftptc=BJ>$oqk(J{O_yZ-sK zw|B8^o3*tylv0e2jCjrB;Ypayf+$+j;&jWDeinH)Xu{&Om&O+PX&Aoe3}A2 z)M8Cq?@c5w!rNN&UE4JzyppX}s{-)tn};6Ow~qDsZ+Mr5pVVPWA`!o|hKRIhLS ac>e*yHDB;g*!YhC0000 Date: Sat, 18 Jun 2022 22:34:11 -0400 Subject: [PATCH 27/40] the finale --- .../GameTicking/Rules/ZombieRuleSystem.cs | 31 ++++++++++++++---- Content.Server/Zombies/ZombieComponent.cs | 10 ++++-- .../Zombies/ZombifyOnDeathSystem.cs | 13 +++----- Content.Shared/Zombies/ZombieEvents.cs | 4 +-- .../Locale/en-US/actions/actions/zombie.ftl | 2 ++ Resources/Prototypes/Actions/types.yml | 7 ++++ .../Catalog/Fills/Backpacks/duffelbag.yml | 16 +++++++++ .../Roles/Jobs/Fun/misc_startinggear.yml | 8 ++--- .../Interface/Actions/zombie-turn.png | Bin 848 -> 858 bytes 9 files changed, 67 insertions(+), 24 deletions(-) create mode 100644 Resources/Locale/en-US/actions/actions/zombie.ftl diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index bf9ba8a6fd60..ae33abacc9fc 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -1,4 +1,5 @@ using System.Linq; +using Content.Server.Actions; using Content.Server.Chat.Managers; using Content.Server.Disease; using Content.Server.GameTicking.Rules.Configurations; @@ -9,6 +10,7 @@ using Content.Server.RoundEnd; using Content.Server.Traitor; using Content.Server.Zombies; +using Content.Shared.Actions.ActionTypes; using Content.Shared.CCVar; using Content.Shared.CharacterAppearance.Components; using Content.Shared.FixedPoint; @@ -37,14 +39,16 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly RoundEndSystem _roundEndSystem = default!; [Dependency] private readonly DiseaseSystem _diseaseSystem = default!; [Dependency] private readonly PopupSystem _popup = default!; + [Dependency] private readonly ActionsSystem _action = default!; + [Dependency] private readonly ZombifyOnDeathSystem _zombify = default!; private Dictionary _initialInfected = new(); public override string Prototype => "Zombie"; + private const string PatientZeroPrototypeID = "InitialInfected"; private const string InitialZombieVirusPrototype = "PassiveZombieVirus"; - - private const int LastSurvivorsThreshold = 6; + private const string ZombifySelfActionPrototype = "TurnUndead"; public override void Initialize() { @@ -56,6 +60,7 @@ public override void Initialize() SubscribeLocalEvent(OnJobAssigned); SubscribeLocalEvent(OnEntityZombified); + SubscribeLocalEvent(OnZombifySelf); } private void OnRoundEndText(RoundEndTextAppendEvent ev) @@ -85,11 +90,12 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) ("username", player.Value))); } - //Gets a bunch of the living players and displays them if they're under a threshold. - if (percent > 0 && livingHumans.Count < LastSurvivorsThreshold) + ///Gets a bunch of the living players and displays them if they're under a threshold. + ///InitialInfected is used for the threshold because it scales with the player count well. + if (percent > 0 && livingHumans.Count < _initialInfected.Count) { ev.AddLine(""); - ev.AddLine(Loc.GetString("zombie-round-end-survivor-count", ("count", 1))); + ev.AddLine(Loc.GetString("zombie-round-end-survivor-count", ("count", livingHumans.Count))); foreach (var survivor in livingHumans) { var meta = MetaData(survivor); @@ -183,6 +189,14 @@ public override void Started(GameRuleConfiguration configuration) public override void Ended(GameRuleConfiguration configuration) { } + private void OnZombifySelf(EntityUid uid, ZombifyOnDeathComponent component, ZombifySelfActionEvent args) + { + _zombify.ZombifyEntity(uid); + + var action = new InstantAction(_prototypeManager.Index(ZombifySelfActionPrototype)); + _action.RemoveAction(uid, action); + } + private FixedPoint2 GetInfectedPercentage(out List livingHumans) { var allPlayers = EntityQuery(); @@ -199,7 +213,7 @@ private FixedPoint2 GetInfectedPercentage(out List livingHumans) livingZombies.Add(ent.Item2.Owner); else livingHumans.Add(ent.Item2.Owner); - } + } } return (FixedPoint2) livingZombies.Count / (FixedPoint2) totalPlayers.Count; } @@ -245,7 +259,7 @@ private void InfectInitialPlayers() IPlayerSession zombie; if (prefList.Count == 0) { - if(playerList.Count == 0) + if (playerList.Count == 0) { Logger.InfoS("preset", "Insufficient number of players. stopping selection."); break; @@ -276,6 +290,9 @@ private void InfectInitialPlayers() { _diseaseSystem.TryAddDisease(mind.OwnedEntity.Value, InitialZombieVirusPrototype); inCharacterName = MetaData(mind.OwnedEntity.Value).EntityName; + + var action = new InstantAction(_prototypeManager.Index(ZombifySelfActionPrototype)); + _action.AddAction(mind.OwnedEntity.Value, action, null); } if (mind.Session != null) diff --git a/Content.Server/Zombies/ZombieComponent.cs b/Content.Server/Zombies/ZombieComponent.cs index 926d74fb372b..0204ac1df8d1 100644 --- a/Content.Server/Zombies/ZombieComponent.cs +++ b/Content.Server/Zombies/ZombieComponent.cs @@ -12,7 +12,7 @@ public sealed class ZombieComponent : Component /// attacks another zombie. longe name /// [ViewVariables] - public float OtherZombieDamageCoefficient = 0.75f; + public float OtherZombieDamageCoefficient = 0.5f; /// /// The baseline infection chance you have if you are completely nude @@ -31,7 +31,13 @@ public sealed class ZombieComponent : Component /// The skin color of the zombie /// [ViewVariables, DataField("skinColor")] - public Color SkinColor = new Color(0.70f, 0.72f, 0.48f, 1); + public Color SkinColor = new(0.45f, 0.51f, 0.29f); + + /// + /// The eye color of the zombie + /// + [ViewVariables, DataField("eyeColor")] + public Color EyeColor = new(0.96f, 0.13f, 0.24f); /// /// The attack arc of the zombie diff --git a/Content.Server/Zombies/ZombifyOnDeathSystem.cs b/Content.Server/Zombies/ZombifyOnDeathSystem.cs index 1877bfcfb571..afcfc0318a4d 100644 --- a/Content.Server/Zombies/ZombifyOnDeathSystem.cs +++ b/Content.Server/Zombies/ZombifyOnDeathSystem.cs @@ -52,7 +52,6 @@ public override void Initialize() base.Initialize(); SubscribeLocalEvent(OnDamageChanged); - SubscribeLocalEvent(OnZombifySelf); } /// @@ -67,11 +66,6 @@ private void OnDamageChanged(EntityUid uid, ZombifyOnDeathComponent component, M } } - private void OnZombifySelf(EntityUid uid, ZombifyOnDeathComponent component, ZombifySelfActionEvent args) - { - ZombifyEntity(uid); - } - /// /// This is the general purpose function to call if you want to zombify an entity. /// It handles both humanoid and nonhumanoid transformation and everything should be called through it. @@ -80,7 +74,7 @@ private void OnZombifySelf(EntityUid uid, ZombifyOnDeathComponent component, Zom /// /// ALRIGHT BIG BOY. YOU'VE COME TO THE LAYER OF THE BEAST. THIS IS YOUR WARNING. /// This function is the god function for zombie stuff, and it is cursed. I have - /// attempted to label everything thouroughly for your sanity. It have attempted to + /// attempted to label everything thouroughly for your sanity. I have attempted to /// rewrite this, but this is how it shall lie eternal. Turn back now. /// -emo /// @@ -121,7 +115,8 @@ public void ZombifyEntity(EntityUid target) { //this bs is done because you can't directly update humanoid appearances var appearance = huApComp.Appearance; - _sharedHuApp.UpdateAppearance(target, appearance.WithSkinColor(zombiecomp.SkinColor), huApComp); + appearance = appearance.WithSkinColor(zombiecomp.SkinColor).WithEyeColor(zombiecomp.EyeColor); + _sharedHuApp.UpdateAppearance(target, appearance, huApComp); _sharedHuApp.ForceAppearanceUpdate(target, huApComp); ///This is done here because non-humanoids shouldn't get baller damage @@ -185,7 +180,7 @@ public void ZombifyEntity(EntityUid target) foreach (var hand in _sharedHands.EnumerateHands(target)) { _sharedHands.SetActiveHand(target, hand); - hand.Container?.EmptyContainer(); + _sharedHands.DoDrop(target, hand); _sharedHands.RemoveHand(target, hand.Name); } RemComp(target); diff --git a/Content.Shared/Zombies/ZombieEvents.cs b/Content.Shared/Zombies/ZombieEvents.cs index 696bc48759a8..7ca2b493c7ef 100644 --- a/Content.Shared/Zombies/ZombieEvents.cs +++ b/Content.Shared/Zombies/ZombieEvents.cs @@ -1,4 +1,4 @@ -using Content.Shared.Actions.ActionTypes; +using Content.Shared.Actions; namespace Content.Shared.Zombies; /// @@ -21,4 +21,4 @@ public EntityZombifiedEvent(EntityUid target) /// /// Event raised when a player zombifies themself using the "turn" action /// -public sealed class ZombifySelfActionEvent : InstantAction { }; +public sealed class ZombifySelfActionEvent : InstantActionEvent { }; diff --git a/Resources/Locale/en-US/actions/actions/zombie.ftl b/Resources/Locale/en-US/actions/actions/zombie.ftl new file mode 100644 index 000000000000..3ae2d928e980 --- /dev/null +++ b/Resources/Locale/en-US/actions/actions/zombie.ftl @@ -0,0 +1,2 @@ +turn-undead-action-name = Turn Undead +turn-undead-action-description = Succumb to your infection and become a zombie. \ No newline at end of file diff --git a/Resources/Prototypes/Actions/types.yml b/Resources/Prototypes/Actions/types.yml index 0269fb0952e5..2b20d17c525e 100644 --- a/Resources/Prototypes/Actions/types.yml +++ b/Resources/Prototypes/Actions/types.yml @@ -7,6 +7,13 @@ serverEvent: !type:ScreamActionEvent checkCanInteract: false +- type: instantAction + id: TurnUndead + name: turn-undead-action-name + description: turn-undead-action-description + icon: Interface/Actions/zombie-turn.png + event: !type:ZombifySelfActionEvent + - type: instantAction id: ToggleLight name: action-name-toggle-light diff --git a/Resources/Prototypes/Catalog/Fills/Backpacks/duffelbag.yml b/Resources/Prototypes/Catalog/Fills/Backpacks/duffelbag.yml index f5154c6824eb..270a4e3bc76a 100644 --- a/Resources/Prototypes/Catalog/Fills/Backpacks/duffelbag.yml +++ b/Resources/Prototypes/Catalog/Fills/Backpacks/duffelbag.yml @@ -13,6 +13,22 @@ - id: Retractor - id: Scalpel +- type: entity + id: ClothingBackpackDuffelCBURN + parent: ClothingBackpackDuffel + name: CBURN duffel bag + description: A duffel bag containing a variety of biological containment equipment. + components: + - type: StorageFill + contents: + - id: WeaponShotgunDoubleBarreled + - id: BoxShotgunFlare + amount: 2 + - id: PillRomerol + amount: 5 + - id: GrenadeFlash + amount: 2 + - type: entity parent: ClothingBackpackDuffelSyndicateMedical id: ClothingBackpackDuffelSyndicateFilledMedical diff --git a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml index a0b6874dd8d4..027b9ff60a61 100644 --- a/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml +++ b/Resources/Prototypes/Roles/Jobs/Fun/misc_startinggear.yml @@ -143,9 +143,9 @@ id: CBURNGear equipment: jumpsuit: ClothingUniformJumpsuitColorBrown - back: ClothingBackpack + back: ClothingBackpackDuffelCBURN mask: ClothingMaskGas - eyes: ClothingEyesGlassesSunglasses + eyes: ClothingEyesGlassesSecurity ears: ClothingHeadsetService gloves: ClothingHandsGlovesFingerless outerClothing: ClothingOuterHardsuitCBURN @@ -156,5 +156,5 @@ suitstorage: YellowOxygenTankFilled belt: ClothingBeltBandolier innerclothingskirt: ClothingUniformJumpsuitColorBrown - satchel: ClothingBackpackSatchel - duffelbag: ClothingBackpackDuffel \ No newline at end of file + satchel: ClothingBackpackDuffelCBURN + duffelbag: ClothingBackpackDuffelCBURN \ No newline at end of file diff --git a/Resources/Textures/Interface/Actions/zombie-turn.png b/Resources/Textures/Interface/Actions/zombie-turn.png index b9dfad21118c6ef571be5724d9e3f60c0c022801..2e7173d4d325bc48a33544e908f7d6f56d59a7ab 100644 GIT binary patch delta 822 zcmV-61Ihf*2HFOYF@F?EL_t(oh3%HXYa2%t#($~}>qN*b#>JROm3>%n4~u;+^pHai zi+Tz^`BH~omIYzoOepA}zra*t(WN-O!Z6LWC-MC}0ezvL*A7h{F{-0_E=?%h=2$0AEdiPPPzHTzdt;&qa?a#EL}h z2ps=X=e*rv=*BSL{{9oH=<#*C!w_)Z?(jS&U#tk!YBgC|SxL0i0iP8jep|lHt7k8f zc8BwJhn6~EDSu`PVxv~83B0X?rTcee>HeK-orKtGeczYa*;$@Gd&HaLH(k4xw3zwi zF5BDNR4Nr?-dHK{eP5JP0GzcPKKCa?{4-y|FzlO-SSg622!NfP9e}O~{nU0n&jbSn=-u~{I*!vF@9*zlYLB7_&+`VR z!YBgGW)lD%PQ6oriHV8sSljhHy{;by)~k*9~Bjcl3NsHHq#{+qdj-mefoTvkA+h%=z9ioGcpWCQq>OTMA;a0+=!GvL$=v~uqu76PkE|T;%rHi$okLw`Eu>@QOo%edZ z-nI1#F~ybdgxYx+hKXJg|EYlYfe%x_zqMGC)_W1Li}146eARXhF|TBgs#O8_^4>jc z+Xi5FcQ=vAWCY;o=!oyu)&RIWKmUF&r48A+v5@?>*U zUN7wJiHJz0TsFE98LKQ53YQWVi^W90Z-aRM22hJ#dwqu6A^-pY07*qoM6N<$f-F9m A;Q#;t delta 812 zcmV+{1JnH42G9nOF@Fk4L_t(oh3%F>NF!Gm$A2l(Jq#g3s|Ybcg$|wukDm891bV1m z_Eh#z7zWZ6_8@qW;K8#cVVIlrx@0A_&?zX?J*In-5Mi;fK8%aHtSFL-*7EgWU&xA^ zywRnw(EnxTee>S``@iq|-Zu~a$ES>_G%Zz-s5C8i<@oGA&VRF06YK+nrRUsL#K3)= zzxI|GkLLl%0#%S1NG0J)9D&Mjzesj!0)QvLYj26Ky(IuXkLRgEqDUl;K>POwSK}89 zq#y7DFdomddUgT8)!7C63HcI5pjNBN+}vF1XnU7SZ;9;6_q^MF!{6<{xH`MwXnU6@ z2~&_5wOUQ!x_=Hv3U-FQVQSqjiX^KAP52}6bb;8%Vk{G&-41G!YBf*Rto?f zPQ6or;o;%VySD3jdR;H{t$}8?}$t#>U35ZJYM~+fIXO@4xNI zZPYS#pZ818Qzi{248v6SnqG5_B5;$WyD8nQ1%G{9`#DY|;5O*IHyVwOty_pG?tCZI z&ciTFb&L2<1$+#AngTx5Voh4_O(ZVD+gkHo+chM-lC4&&0`TqQ$Jn+Fz~0_oDxc2_ zz{$x8Kd!6*@XgH3$Gx0Jm5PXn9333U%X(eX>9lCa`Fvi|>9oA8*X8KoKtx2MO2z0# qWF@R}VPWA`!o|hKRIhLSc>e*yHDB;g*!YhC0000 Date: Sun, 19 Jun 2022 11:00:14 -0400 Subject: [PATCH 28/40] secret mode --- Content.Server/GameTicking/Rules/ZombieRuleSystem.cs | 3 --- Resources/Prototypes/secret_weights.yml | 3 ++- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index ae33abacc9fc..4b815adb284a 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -162,8 +162,6 @@ private void OnStartAttempt(RoundStartAttemptEvent ev) if (!Enabled) return; - //Uncomment this once im done local testing - /* var minPlayers = _cfg.GetCVar(CCVars.ZombieMinPlayers); if (!ev.Forced && ev.Players.Length < minPlayers) { @@ -178,7 +176,6 @@ private void OnStartAttempt(RoundStartAttemptEvent ev) ev.Cancel(); return; } - //*/ } public override void Started(GameRuleConfiguration configuration) diff --git a/Resources/Prototypes/secret_weights.yml b/Resources/Prototypes/secret_weights.yml index 6866e6875c16..cd06d5323fb5 100644 --- a/Resources/Prototypes/secret_weights.yml +++ b/Resources/Prototypes/secret_weights.yml @@ -3,4 +3,5 @@ weights: Extended: 0.25 Nukeops: 0.25 - Traitor: 0.75 \ No newline at end of file + Traitor: 0.75 + Zombie: 0.10 \ No newline at end of file From 1efd8b70b6e00b535f83398235248830ee43187f Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 19 Jun 2022 11:03:40 -0400 Subject: [PATCH 29/40] meta momento --- Resources/Textures/Interface/Actions/meta.json | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Resources/Textures/Interface/Actions/meta.json b/Resources/Textures/Interface/Actions/meta.json index 454f9ab86fa2..f487a8617362 100644 --- a/Resources/Textures/Interface/Actions/meta.json +++ b/Resources/Textures/Interface/Actions/meta.json @@ -19,9 +19,9 @@ { "name": "disarm" }, - { - "name": "harm" - }, + { + "name": "harm" + }, { "name": "manifest" }, @@ -41,4 +41,4 @@ "name": "zombie-turn" } ] -} \ No newline at end of file +} From ea07db28e3456e5fc93a4d2775bffb329850ee87 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Sun, 19 Jun 2022 15:10:08 -0400 Subject: [PATCH 30/40] myassmar --- Content.Server/Zombies/ZombifyOnDeathSystem.cs | 2 ++ Content.Shared/Zombies/ZombieEvents.cs | 1 + Resources/Prototypes/Damage/modifier_sets.yml | 5 ++++- 3 files changed, 7 insertions(+), 1 deletion(-) diff --git a/Content.Server/Zombies/ZombifyOnDeathSystem.cs b/Content.Server/Zombies/ZombifyOnDeathSystem.cs index afcfc0318a4d..bb8d1bbc06d6 100644 --- a/Content.Server/Zombies/ZombifyOnDeathSystem.cs +++ b/Content.Server/Zombies/ZombifyOnDeathSystem.cs @@ -27,6 +27,7 @@ using Content.Shared.Roles; using Content.Server.Traitor; using Content.Shared.Zombies; +using Content.Server.Atmos.Miasma; namespace Content.Server.Zombies { @@ -97,6 +98,7 @@ public void ZombifyEntity(EntityUid target) //funny voice EnsureComp(target).Accent = "zombie"; + EnsureComp(target); ///This is needed for stupid entities that fuck up combat mode component ///in an attempt to make an entity not attack. This is the easiest way to do it. diff --git a/Content.Shared/Zombies/ZombieEvents.cs b/Content.Shared/Zombies/ZombieEvents.cs index 7ca2b493c7ef..08c6e473cce0 100644 --- a/Content.Shared/Zombies/ZombieEvents.cs +++ b/Content.Shared/Zombies/ZombieEvents.cs @@ -1,6 +1,7 @@ using Content.Shared.Actions; namespace Content.Shared.Zombies; + /// /// Event raised whenever an entity is zombified. /// Used by the zombie gamemode to track total infections. diff --git a/Resources/Prototypes/Damage/modifier_sets.yml b/Resources/Prototypes/Damage/modifier_sets.yml index 12f82c79232f..b8ae43c12c22 100644 --- a/Resources/Prototypes/Damage/modifier_sets.yml +++ b/Resources/Prototypes/Damage/modifier_sets.yml @@ -116,8 +116,11 @@ Piercing: 0.9 Shock: 1.5 Cold: 0.2 - Heat: 3.0 + Heat: 2.5 Poison: 0.0 + flatReductions: #offsets rotting damage + Blunt: 0.25 + Cellular: 0.25 # immune to everything except physical and heat damage - type: damageModifierSet From f84389dbb956d0708d266e23c5be515dd0b12529 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 <98561806+EmoGarbage404@users.noreply.github.com> Date: Sun, 19 Jun 2022 22:05:01 -0400 Subject: [PATCH 31/40] Update secret_weights.yml --- Resources/Prototypes/secret_weights.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Resources/Prototypes/secret_weights.yml b/Resources/Prototypes/secret_weights.yml index cd06d5323fb5..fb64d7432504 100644 --- a/Resources/Prototypes/secret_weights.yml +++ b/Resources/Prototypes/secret_weights.yml @@ -4,4 +4,4 @@ Extended: 0.25 Nukeops: 0.25 Traitor: 0.75 - Zombie: 0.10 \ No newline at end of file + Zombie: 0.05 From c9bde3639ce52a2d55417bc51dc292331479f1e6 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 <98561806+EmoGarbage404@users.noreply.github.com> Date: Sun, 19 Jun 2022 22:06:03 -0400 Subject: [PATCH 32/40] Update BodyReassembleSystem.cs --- Content.Server/Body/Systems/BodyReassembleSystem.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Content.Server/Body/Systems/BodyReassembleSystem.cs b/Content.Server/Body/Systems/BodyReassembleSystem.cs index eea7d216567e..03fab94e40b5 100644 --- a/Content.Server/Body/Systems/BodyReassembleSystem.cs +++ b/Content.Server/Body/Systems/BodyReassembleSystem.cs @@ -192,7 +192,7 @@ private void UpdateDNAEntry(EntityUid uid, EntityUid body) if (mindcomp.Mind == null) return; - + if (mindcomp.Mind.UserId == null) return; From d8aa659d8db16bfa13e1b0fc6f81cbe6ec0120fa Mon Sep 17 00:00:00 2001 From: EmoGarbage404 <98561806+EmoGarbage404@users.noreply.github.com> Date: Tue, 21 Jun 2022 11:13:47 -0400 Subject: [PATCH 33/40] Update modifier_sets.yml --- Resources/Prototypes/Damage/modifier_sets.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Resources/Prototypes/Damage/modifier_sets.yml b/Resources/Prototypes/Damage/modifier_sets.yml index b8ae43c12c22..e5e3f6a8c207 100644 --- a/Resources/Prototypes/Damage/modifier_sets.yml +++ b/Resources/Prototypes/Damage/modifier_sets.yml @@ -119,8 +119,8 @@ Heat: 2.5 Poison: 0.0 flatReductions: #offsets rotting damage - Blunt: 0.25 - Cellular: 0.25 + Blunt: 0.3 + Cellular: 0.3 # immune to everything except physical and heat damage - type: damageModifierSet From f0b1ece7918f8f56c884c642de418ffe04d87fed Mon Sep 17 00:00:00 2001 From: EmoGarbage404 <98561806+EmoGarbage404@users.noreply.github.com> Date: Fri, 24 Jun 2022 10:48:08 -0400 Subject: [PATCH 34/40] Update Content.Server/Zombies/ZombieSystem.cs Co-authored-by: Kara --- Content.Server/Zombies/ZombieSystem.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Content.Server/Zombies/ZombieSystem.cs b/Content.Server/Zombies/ZombieSystem.cs index 99a183b2f24c..f8d442b857d4 100644 --- a/Content.Server/Zombies/ZombieSystem.cs +++ b/Content.Server/Zombies/ZombieSystem.cs @@ -41,7 +41,7 @@ private float GetZombieInfectionChance(EntityUid uid, ZombieComponent component) var items = 0f; var total = 0f; - while (enumerator.MoveNext(out var con)) + while (enumerator.MoveNext(out var con)) { total++; if (con.ContainedEntity != null) From 1de475fb73277e5ab343a29f9760a0187e037ef6 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 <98561806+EmoGarbage404@users.noreply.github.com> Date: Fri, 24 Jun 2022 10:48:19 -0400 Subject: [PATCH 35/40] Update Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl Co-authored-by: Kara --- .../Locale/en-US/game-ticking/game-presets/preset-zombies.ftl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index 3244a1765761..dc4a3a38c10c 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -16,7 +16,7 @@ zombie-round-end-initial-count = {$initialCount -> [one] There was one initial infected: *[other] There were {$initialCount} initial infected: } -zombie-round-end-user-was-initial = - [color=Plum]{$name}[/color] ([color=gray]{$username}[/color]) was one of the initial infected. +zombie-round-end-user-was-initial = - [color=plum]{$name}[/color] ([color=gray]{$username}[/color]) was one of the initial infected. zombie-round-end-amount-none = [color=green]All of the zombies were eradicated![/color] zombie-round-end-amount-low = [color=green]Almost all of the zombies were exterminated.[/color] From d418b2e3873bd491a3d21b60090df2d70f2629c6 Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Fri, 24 Jun 2022 11:30:30 -0400 Subject: [PATCH 36/40] mirror reviews 5 minutes --- .../GameTicking/Rules/ZombieRuleSystem.cs | 23 +++++++++---------- Content.Shared/CCVar/CCVars.cs | 8 +++---- Content.Shared/Zombies/ZombieEvents.cs | 2 +- .../game-presets/preset-zombies.ftl | 4 ---- Resources/Locale/en-US/zombies/zombie.ftl | 2 +- 5 files changed, 17 insertions(+), 22 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index 4b815adb284a..a62b1dc79ff3 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -42,7 +42,7 @@ public sealed class ZombieRuleSystem : GameRuleSystem [Dependency] private readonly ActionsSystem _action = default!; [Dependency] private readonly ZombifyOnDeathSystem _zombify = default!; - private Dictionary _initialInfected = new(); + private Dictionary _initialInfectedNames = new(); public override string Prototype => "Zombie"; @@ -82,8 +82,8 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) else ev.AddLine(Loc.GetString("zombie-round-end-amount-all")); - ev.AddLine(Loc.GetString("zombie-round-end-initial-count", ("initialCount", _initialInfected.Count))); - foreach (var player in _initialInfected) + ev.AddLine(Loc.GetString("zombie-round-end-initial-count", ("initialCount", _initialInfectedNames.Count))); + foreach (var player in _initialInfectedNames) { ev.AddLine(Loc.GetString("zombie-round-end-user-was-initial", ("name", player.Key), @@ -92,7 +92,7 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) ///Gets a bunch of the living players and displays them if they're under a threshold. ///InitialInfected is used for the threshold because it scales with the player count well. - if (percent > 0 && livingHumans.Count < _initialInfected.Count) + if (percent > 0 && livingHumans.Count < _initialInfectedNames.Count) { ev.AddLine(""); ev.AddLine(Loc.GetString("zombie-round-end-survivor-count", ("count", livingHumans.Count))); @@ -116,7 +116,7 @@ private void OnJobAssigned(RulePlayerJobsAssignedEvent ev) if (!Enabled) return; - _initialInfected = new(); + _initialInfectedNames = new(); InfectInitialPlayers(); } @@ -150,10 +150,9 @@ private void CheckRoundEnd(EntityUid target) return; var percent = GetInfectedPercentage(out var num); - - if (num.Count == 1) //only one left + if (MathHelper.CloseTo(percent, 1)) //only one left _popup.PopupEntity(Loc.GetString("zombie-alone"), num[0], Filter.Entities(num[0])); - if (percent >= 1) //oops, all zombies + else if (percent >= 1) //oops, all zombies _roundEndSystem.EndRound(); } @@ -194,7 +193,7 @@ private void OnZombifySelf(EntityUid uid, ZombifyOnDeathComponent component, Zom _action.RemoveAction(uid, action); } - private FixedPoint2 GetInfectedPercentage(out List livingHumans) + private float GetInfectedPercentage(out List livingHumans) { var allPlayers = EntityQuery(); var totalPlayers = new List(); @@ -212,7 +211,7 @@ private FixedPoint2 GetInfectedPercentage(out List livingHumans) livingHumans.Add(ent.Item2.Owner); } } - return (FixedPoint2) livingZombies.Count / (FixedPoint2) totalPlayers.Count; + return livingZombies.Count / totalPlayers.Count; } /// @@ -245,7 +244,7 @@ private void InfectInitialPlayers() return; var playersPerInfected = _cfg.GetCVar(CCVars.ZombiePlayersPerInfected); - var maxInfected = _cfg.GetCVar(CCVars.ZombieMaxInfected); + var maxInfected = _cfg.GetCVar(CCVars.ZombieMaxInitialInfected); var numInfected = Math.Max(1, (int) Math.Min( @@ -298,7 +297,7 @@ private void InfectInitialPlayers() //gets the names now in case the players leave. if (inCharacterName != null) - _initialInfected.Add(inCharacterName, mind.Session.Name); + _initialInfectedNames.Add(inCharacterName, mind.Session.Name); // I went all the way to ChatManager.cs and all i got was this lousy T-shirt _chatManager.ChatMessageToOne(Shared.Chat.ChatChannel.Server, Loc.GetString("zombie-patientzero-role-greeting"), diff --git a/Content.Shared/CCVar/CCVars.cs b/Content.Shared/CCVar/CCVars.cs index bb032fb2c2a8..ea5b59a31410 100644 --- a/Content.Shared/CCVar/CCVars.cs +++ b/Content.Shared/CCVar/CCVars.cs @@ -291,13 +291,13 @@ public static readonly CVarDef */ public static readonly CVarDef ZombieMinPlayers = - CVarDef.Create("zombie.min_players", 25); + CVarDef.Create("zombie.min_players", 20); - public static readonly CVarDef ZombieMaxInfected = - CVarDef.Create("zombie.max_infected", 4); + public static readonly CVarDef ZombieMaxInitialInfected = + CVarDef.Create("zombie.max_initial_infected", 6); public static readonly CVarDef ZombiePlayersPerInfected = - CVarDef.Create("zombie.players_per_infected", 7); + CVarDef.Create("zombie.players_per_infected", 10); /* * Pirates diff --git a/Content.Shared/Zombies/ZombieEvents.cs b/Content.Shared/Zombies/ZombieEvents.cs index 08c6e473cce0..835c76389532 100644 --- a/Content.Shared/Zombies/ZombieEvents.cs +++ b/Content.Shared/Zombies/ZombieEvents.cs @@ -3,7 +3,7 @@ namespace Content.Shared.Zombies; /// -/// Event raised whenever an entity is zombified. +/// Event that is broadcast whenever an entity is zombified. /// Used by the zombie gamemode to track total infections. /// public sealed class EntityZombifiedEvent : EventArgs diff --git a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl index dc4a3a38c10c..d7e487ba5216 100644 --- a/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl +++ b/Resources/Locale/en-US/game-ticking/game-presets/preset-zombies.ftl @@ -6,10 +6,6 @@ zombie-no-one-ready = No players readied up! Can't start Zombies. zombie-patientzero-role-greeting = You are patient 0. Hide your infection, get supplies, and be prepared to turn once you die. -zombie-nuke-armed-event = In response to the zombie outbreak, we have armed the nuclear device positioned onboard the station. A disk has been automatically teleported inside of it. The code to detonate the device is: {$code}. -zombie-end-nuke-armed-event-fail = The nuke was not detonated. -zombie-end-nuke-armed-event-success = The nuke was successfully detonated by {$name} ({$username}), stopping the outbreak. - zombie-alone = You feel entirely alone. zombie-round-end-initial-count = {$initialCount -> diff --git a/Resources/Locale/en-US/zombies/zombie.ftl b/Resources/Locale/en-US/zombies/zombie.ftl index 21405eda95f1..f534a962e09a 100644 --- a/Resources/Locale/en-US/zombies/zombie.ftl +++ b/Resources/Locale/en-US/zombies/zombie.ftl @@ -2,6 +2,6 @@ zombie-transform = {CAPITALIZE(THE($target))} turned into a zombie! zombie-infection-greeting = You have become a zombie. Your goal is to seek out the living and to try to infect them. Work together with your fellow zombies to overpower the remaining crewmates. zombie-generic = zombie -zombie-name-prefix = Zombie {$target} +zombie-name-prefix = Zombified {$target} zombie-role-desc = A malevolent creature of the dead. zombie-role-rules = You are an antagonist. Search out the living and bite them in order to infect them and turn them into zombies. Work together with other the zombies to overtake the station. From 92afd63177fafe398b4a5f3ef8ec97bccc7e7ada Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Mon, 4 Jul 2022 12:41:42 -0400 Subject: [PATCH 37/40] sloth review merge pls --- .../GameTicking/Rules/ZombieRuleSystem.cs | 20 +++++++++++-------- Content.Server/Zombies/ZombieSystem.cs | 1 + .../Zombies/ZombifyOnDeathSystem.cs | 2 +- Content.Shared/Zombies/ZombieEvents.cs | 4 ++-- 4 files changed, 16 insertions(+), 11 deletions(-) diff --git a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs index a62b1dc79ff3..f86ad355ef64 100644 --- a/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs +++ b/Content.Server/GameTicking/Rules/ZombieRuleSystem.cs @@ -69,7 +69,7 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) return; //this is just the general condition thing used for determining the win/lose text - var percent = GetInfectedPercentage(out var livingHumans); + var percent = Math.Round(GetInfectedPercentage(out var livingHumans), 2); if (percent <= 0) ev.AddLine(Loc.GetString("zombie-round-end-amount-none")); @@ -92,7 +92,7 @@ private void OnRoundEndText(RoundEndTextAppendEvent ev) ///Gets a bunch of the living players and displays them if they're under a threshold. ///InitialInfected is used for the threshold because it scales with the player count well. - if (percent > 0 && livingHumans.Count < _initialInfectedNames.Count) + if (livingHumans.Count > 0 && livingHumans.Count <= _initialInfectedNames.Count) { ev.AddLine(""); ev.AddLine(Loc.GetString("zombie-round-end-survivor-count", ("count", livingHumans.Count))); @@ -150,9 +150,9 @@ private void CheckRoundEnd(EntityUid target) return; var percent = GetInfectedPercentage(out var num); - if (MathHelper.CloseTo(percent, 1)) //only one left - _popup.PopupEntity(Loc.GetString("zombie-alone"), num[0], Filter.Entities(num[0])); - else if (percent >= 1) //oops, all zombies + if (num.Count == 1) //only one human left. spooky + _popup.PopupEntity(Loc.GetString("zombie-alone"), num[0], Filter.Entities(num[0])); + if (percent >= 1) //oops, all zombies _roundEndSystem.EndRound(); } @@ -195,23 +195,27 @@ private void OnZombifySelf(EntityUid uid, ZombifyOnDeathComponent component, Zom private float GetInfectedPercentage(out List livingHumans) { - var allPlayers = EntityQuery(); + var allPlayers = EntityQuery(true); + var allZombers = GetEntityQuery(); + var totalPlayers = new List(); var livingZombies = new List(); + livingHumans = new(); + foreach (var ent in allPlayers) { if (ent.Item2.IsAlive()) { totalPlayers.Add(ent.Item2.Owner); - if (HasComp(ent.Item1.Owner)) + if (allZombers.HasComponent(ent.Item1.Owner)) livingZombies.Add(ent.Item2.Owner); else livingHumans.Add(ent.Item2.Owner); } } - return livingZombies.Count / totalPlayers.Count; + return ((float) livingZombies.Count) / (float) totalPlayers.Count; } /// diff --git a/Content.Server/Zombies/ZombieSystem.cs b/Content.Server/Zombies/ZombieSystem.cs index f8d442b857d4..c9bd2351a3bc 100644 --- a/Content.Server/Zombies/ZombieSystem.cs +++ b/Content.Server/Zombies/ZombieSystem.cs @@ -44,6 +44,7 @@ private float GetZombieInfectionChance(EntityUid uid, ZombieComponent component) while (enumerator.MoveNext(out var con)) { total++; + if (con.ContainedEntity != null) items++; } diff --git a/Content.Server/Zombies/ZombifyOnDeathSystem.cs b/Content.Server/Zombies/ZombifyOnDeathSystem.cs index bb8d1bbc06d6..51b181f3b2b9 100644 --- a/Content.Server/Zombies/ZombifyOnDeathSystem.cs +++ b/Content.Server/Zombies/ZombifyOnDeathSystem.cs @@ -86,7 +86,7 @@ public void ZombifyEntity(EntityUid target) return; //you're a real zombie now, son. - var zombiecomp = EnsureComp(target); + var zombiecomp = AddComp(target); ///we need to basically remove all of these because zombies shouldn't ///get diseases, breath, be thirst, be hungry, or die in space diff --git a/Content.Shared/Zombies/ZombieEvents.cs b/Content.Shared/Zombies/ZombieEvents.cs index 835c76389532..9fa0e3c728f8 100644 --- a/Content.Shared/Zombies/ZombieEvents.cs +++ b/Content.Shared/Zombies/ZombieEvents.cs @@ -6,12 +6,12 @@ namespace Content.Shared.Zombies; /// Event that is broadcast whenever an entity is zombified. /// Used by the zombie gamemode to track total infections. /// -public sealed class EntityZombifiedEvent : EventArgs +public readonly struct EntityZombifiedEvent { /// /// The entity that was zombified. /// - public EntityUid Target; + public readonly EntityUid Target; public EntityZombifiedEvent(EntityUid target) { From 1b52a866f9eeb277796ae787d8fc89945b9f5eef Mon Sep 17 00:00:00 2001 From: EmoGarbage404 Date: Tue, 5 Jul 2022 22:34:28 -0400 Subject: [PATCH 38/40] make infection slots not shit --- Content.Server/Zombies/ZombieSystem.cs | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/Content.Server/Zombies/ZombieSystem.cs b/Content.Server/Zombies/ZombieSystem.cs index c9bd2351a3bc..7675dd46336e 100644 --- a/Content.Server/Zombies/ZombieSystem.cs +++ b/Content.Server/Zombies/ZombieSystem.cs @@ -39,10 +39,20 @@ private float GetZombieInfectionChance(EntityUid uid, ZombieComponent component) if (!_inv.TryGetContainerSlotEnumerator(uid, out var enumerator, inventoryComponent)) return baseChance; + //Hardcoded, ACK + List validInfectionBlockingSlots = new() + { + "shoes", "jumpsuit", "outerClothing", "gloves", + "neck", "mask", "eyes", "head" + }; + var items = 0f; var total = 0f; while (enumerator.MoveNext(out var con)) { + if (!validInfectionBlockingSlots.Contains(con.ID)) + continue; + total++; if (con.ContainedEntity != null) @@ -53,6 +63,7 @@ private float GetZombieInfectionChance(EntityUid uid, ZombieComponent component) var min = component.MinZombieInfectionChance; //gets a value between the max and min based on how many items the entity is wearing float chance = (max-min) * ((total - items)/total) + min; + Logger.Debug(chance.ToString()); return chance; } From c671dfd913e296bfc9fcd2e2b22ae4940097f421 Mon Sep 17 00:00:00 2001 From: Nemanja <98561806+EmoGarbage404@users.noreply.github.com> Date: Tue, 5 Jul 2022 22:41:44 -0400 Subject: [PATCH 39/40] Update ZombieSystem.cs --- Content.Server/Zombies/ZombieSystem.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/Content.Server/Zombies/ZombieSystem.cs b/Content.Server/Zombies/ZombieSystem.cs index 7675dd46336e..efdbdea144ff 100644 --- a/Content.Server/Zombies/ZombieSystem.cs +++ b/Content.Server/Zombies/ZombieSystem.cs @@ -63,7 +63,6 @@ private float GetZombieInfectionChance(EntityUid uid, ZombieComponent component) var min = component.MinZombieInfectionChance; //gets a value between the max and min based on how many items the entity is wearing float chance = (max-min) * ((total - items)/total) + min; - Logger.Debug(chance.ToString()); return chance; } From 6ba29aa497ff2beaf861807db30d89b00c51aada Mon Sep 17 00:00:00 2001 From: metalgearsloth Date: Wed, 6 Jul 2022 13:34:01 +1000 Subject: [PATCH 40/40] Explicit flags --- Content.Server/Zombies/ZombieSystem.cs | 26 +++++++++---------- .../Inventory/InventorySystem.Equip.cs | 1 - 2 files changed, 13 insertions(+), 14 deletions(-) diff --git a/Content.Server/Zombies/ZombieSystem.cs b/Content.Server/Zombies/ZombieSystem.cs index efdbdea144ff..902b58f255e7 100644 --- a/Content.Server/Zombies/ZombieSystem.cs +++ b/Content.Server/Zombies/ZombieSystem.cs @@ -11,6 +11,7 @@ using Content.Server.Popups; using Robust.Shared.Player; using Content.Server.Inventory; +using Robust.Shared.Prototypes; namespace Content.Server.Zombies { @@ -20,8 +21,9 @@ public sealed class ZombieSystem : EntitySystem [Dependency] private readonly BloodstreamSystem _bloodstream = default!; [Dependency] private readonly ZombifyOnDeathSystem _zombify = default!; [Dependency] private readonly ServerInventorySystem _inv = default!; + [Dependency] private readonly IPrototypeManager _protoManager = default!; [Dependency] private readonly IRobustRandom _robustRandom = default!; - [Dependency] private readonly ILogManager _logManager = default!; + public override void Initialize() { base.Initialize(); @@ -36,23 +38,21 @@ private float GetZombieInfectionChance(EntityUid uid, ZombieComponent component) if (!TryComp(uid, out var inventoryComponent)) return baseChance; - if (!_inv.TryGetContainerSlotEnumerator(uid, out var enumerator, inventoryComponent)) - return baseChance; - - //Hardcoded, ACK - List validInfectionBlockingSlots = new() - { - "shoes", "jumpsuit", "outerClothing", "gloves", - "neck", "mask", "eyes", "head" - }; + var enumerator = + new InventorySystem.ContainerSlotEnumerator(uid, inventoryComponent.TemplateId, _protoManager, _inv, + SlotFlags.FEET | + SlotFlags.HEAD | + SlotFlags.EYES | + SlotFlags.GLOVES | + SlotFlags.MASK | + SlotFlags.NECK | + SlotFlags.INNERCLOTHING | + SlotFlags.OUTERCLOTHING); var items = 0f; var total = 0f; while (enumerator.MoveNext(out var con)) { - if (!validInfectionBlockingSlots.Contains(con.ID)) - continue; - total++; if (con.ContainedEntity != null) diff --git a/Content.Shared/Inventory/InventorySystem.Equip.cs b/Content.Shared/Inventory/InventorySystem.Equip.cs index 88498a3ffe86..6dc5270a0e74 100644 --- a/Content.Shared/Inventory/InventorySystem.Equip.cs +++ b/Content.Shared/Inventory/InventorySystem.Equip.cs @@ -25,7 +25,6 @@ public abstract partial class InventorySystem [Dependency] private readonly MovementSpeedModifierSystem _movementSpeed = default!; [Dependency] private readonly SharedInteractionSystem _interactionSystem = default!; [Dependency] private readonly SharedContainerSystem _containerSystem = default!; - [Dependency] private readonly ActionBlockerSystem _actionBlockerSystem = default!; [Dependency] private readonly SharedHandsSystem _handsSystem = default!; [Dependency] private readonly IGameTiming _gameTiming = default!; [Dependency] private readonly INetManager _netMan = default!;