From a1d8454cd289a5d2fc2a4e004685952c0dad3afc Mon Sep 17 00:00:00 2001 From: pacable <77161122+pxc1984@users.noreply.github.com> Date: Wed, 31 Jul 2024 03:47:30 +0300 Subject: [PATCH] =?UTF-8?q?=D0=A4=D0=B8=D0=BA=D1=81=20=D0=B7=D0=BE=D0=BC?= =?UTF-8?q?=D0=B1=D0=B5=D0=B9=20(#258)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * фикс зомби Signed-off-by: JDtrimble * cleanup Signed-off-by: JDtrimble * review changes от вигерса Signed-off-by: JDtrimble * вернул реген физы Signed-off-by: JDtrimble * надеюсь? Signed-off-by: JDtrimble * в 10 меньше структурного. теперь укрепленное окно ломается не мгновенно Signed-off-by: JDtrimble * апдейт текстурок Signed-off-by: JDtrimble * Update ZombieComponent.cs * Update ZombieComponent.cs --------- Signed-off-by: JDtrimble Co-authored-by: Vigers Ray <60344369+VigersRay@users.noreply.github.com> --- .../Zombies/ZombieSystem.Transform.cs | 2 +- Content.Server/Zombies/ZombieSystem.cs | 59 +++++++++++++++++- Content.Shared/Zombies/ZombieComponent.cs | 28 +++++++-- Resources/Prototypes/Damage/modifier_sets.yml | 6 +- Resources/Prototypes/Voice/auto_emotes.yml | 2 +- .../_Sunrise/Actions/zombie_actions.yml | 4 +- .../Textures/_Sunrise/Zombie/Actions/jump.png | Bin 0 -> 2119 bytes .../_Sunrise/Zombie/Actions/the_look.png | Bin 0 -> 2348 bytes 8 files changed, 87 insertions(+), 14 deletions(-) create mode 100644 Resources/Textures/_Sunrise/Zombie/Actions/jump.png create mode 100644 Resources/Textures/_Sunrise/Zombie/Actions/the_look.png diff --git a/Content.Server/Zombies/ZombieSystem.Transform.cs b/Content.Server/Zombies/ZombieSystem.Transform.cs index 0a4cd689cea..d8a8d626f7b 100644 --- a/Content.Server/Zombies/ZombieSystem.Transform.cs +++ b/Content.Server/Zombies/ZombieSystem.Transform.cs @@ -186,7 +186,7 @@ public void ZombifyEntity(EntityUid target, MobStateComponent? mobState = null) { { "Slash", 15 }, { "Piercing", 15 }, - { "Structural", 150 } // Sunrise-Edit + { "Structural", 15 } // Sunrise-Edit } }; melee.Damage = dspec; diff --git a/Content.Server/Zombies/ZombieSystem.cs b/Content.Server/Zombies/ZombieSystem.cs index 1f002c76b7a..c20b280c16e 100644 --- a/Content.Server/Zombies/ZombieSystem.cs +++ b/Content.Server/Zombies/ZombieSystem.cs @@ -1,9 +1,11 @@ using System.Linq; +using System.Text.RegularExpressions; // Sunrise using Content.Server.Actions; using Content.Server.Body.Systems; using Content.Server.Chat; using Content.Server.Chat.Systems; using Content.Server.Emoting.Systems; +using Content.Server.Pinpointer; // Sunrise using Content.Server.Speech.EntitySystems; using Content.Shared.Bed.Sleep; using Content.Shared.Cloning; @@ -20,6 +22,7 @@ using Content.Shared.Throwing; using Content.Shared.Weapons.Melee.Events; using Content.Shared.Zombies; +using Robust.Server.GameObjects; // Sunrise using Robust.Shared.Prototypes; using Robust.Shared.Random; using Robust.Shared.Timing; @@ -44,6 +47,8 @@ public sealed partial class ZombieSystem : SharedZombieSystem [Dependency] private readonly ThrowingSystem _throwing = default!; [Dependency] private readonly ActionsSystem _action = default!; [Dependency] private readonly SharedStunSystem _stun = default!; + [Dependency] private readonly NavMapSystem _navMap = default!; // Sunrise-Zombies + [Dependency] private readonly TransformSystem _transform = default!; // Sunrise-Zombies public const SlotFlags ProtectiveSlots = SlotFlags.FEET | @@ -91,6 +96,9 @@ private void OnThrowDoHit(EntityUid uid, ZombieComponent component, ThrowDoHitEv return; if (!_mobState.IsAlive(args.Target)) return; + if (_timing.CurTime - component.LastThrowHit < component.ThrowHitDelay) + return; + component.LastThrowHit = _timing.CurTime; _stun.TryParalyze(args.Target, TimeSpan.FromSeconds(component.ParalyzeTime), false); _damageable.TryChangeDamage(args.Target, component.Damage, origin: args.Thrown); @@ -101,12 +109,54 @@ private void OnFlair(EntityUid uid, ZombieComponent component, ZombieFlairAction if (args.Handled) return; - _popup.PopupEntity("Мне было лень это делать, напишите админам, пускай скажут вам где выжившие.", - uid, uid, PopupType.LargeCaution); + var zombieXform = Transform(uid); + EntityUid? nearestUid = default!; + TransformComponent? nearestXform = default!; + float? minDistance = null; + var query = AllEntityQuery(); + while (query.MoveNext(out var targetUid, out var humanoidAppearanceComponent)) + { + // Зомби не должны чувствовать тех, у кого иммунитет к ним. + if (HasComp(targetUid) || HasComp(targetUid)) + continue; + var xform = Transform(targetUid); + + // Почему бы и нет, оптимизация наху + var distance = Math.Abs(zombieXform.Coordinates.X - xform.Coordinates.X) + + Math.Abs(zombieXform.Coordinates.Y - xform.Coordinates.Y); + + if (distance > component.MaxFlairDistance) + continue; + + if (minDistance == null || nearestUid == null || minDistance > distance) + { + nearestUid = targetUid; + minDistance = distance; + nearestXform = xform; + } + } + + if (nearestUid == null || nearestUid == default!) + { + _popup.PopupEntity($"Ближайших выживших не найдено.", uid, uid, PopupType.LargeCaution); + } + else + { + _popup.PopupEntity($"Ближайший выживший находится {RemoveColorTags(_navMap.GetNearestBeaconString(nearestUid.Value))}", uid, uid, PopupType.LargeCaution); + } args.Handled = true; } + private string RemoveColorTags(string input) + { + // Регулярное выражение для поиска тэгов [color=...] и [/color] + var pattern = @"\[\s*\/?\s*color(?:=[^\]]*)?\]"; + // Заменяем найденные тэги на пустую строку + var result = Regex.Replace(input, pattern, string.Empty, RegexOptions.IgnoreCase); + return result; + } + private void OnJump(EntityUid uid, ZombieComponent component, ZombieJumpActionEvent args) { if (args.Handled) @@ -125,6 +175,11 @@ private void OnJump(EntityUid uid, ZombieComponent component, ZombieJumpActionEv var mapCoords = args.Target.ToMap(EntityManager); var direction = mapCoords.Position - xform.MapPosition.Position; + if (direction.Length() > component.MaxThrow) + { + direction = direction.Normalized() * component.MaxThrow; + } + _throwing.TryThrow(uid, direction, 7F, uid, 10F); _chatSystem.TryEmoteWithChat(uid, "ZombieGroan"); } diff --git a/Content.Shared/Zombies/ZombieComponent.cs b/Content.Shared/Zombies/ZombieComponent.cs index 6414640574c..1f69f47a8d4 100644 --- a/Content.Shared/Zombies/ZombieComponent.cs +++ b/Content.Shared/Zombies/ZombieComponent.cs @@ -31,7 +31,7 @@ public sealed partial class ZombieComponent : Component public float MinZombieInfectionChance = 0.6f; // Sunrise-Edit [ViewVariables(VVAccess.ReadWrite)] - public float ZombieMovementSpeedBuff = 1.3f; // Sunrise-Edit + public float ZombieMovementSpeedBuff = 1f; // Sunrise-Edit /// /// The skin color of the zombie @@ -100,9 +100,9 @@ public sealed partial class ZombieComponent : Component { DamageDict = new () { - { "Blunt", -2.5 }, // Sunrise-Edit - { "Slash", -2.5 }, // Sunrise-Edit - { "Piercing", -2.5 }, // Sunrise-Edit + { "Blunt", -5 }, // Sunrise-Edit + { "Slash", -5 }, // Sunrise-Edit + { "Piercing", -5 }, // Sunrise-Edit { "Heat", -0.02 }, { "Shock", -0.02 } } @@ -112,7 +112,7 @@ public sealed partial class ZombieComponent : Component /// A multiplier applied to when the entity is in critical condition. /// [DataField("passiveHealingCritMultiplier")] - public float PassiveHealingCritMultiplier = 5f; // Sunrise-Edit + public float PassiveHealingCritMultiplier = 2f; // Sunrise-Edit /// /// Healing given when a zombie bites a living being. @@ -170,5 +170,23 @@ public sealed partial class ZombieComponent : Component { "Slash", 30 }, }, }; + + /// + /// Нельзя пролететь через толпу и всех переубивать + /// + [DataField] + public TimeSpan? LastThrowHit; + + [DataField] + public TimeSpan ThrowHitDelay = TimeSpan.Zero(); + + [DataField] + public float MaxThrow = 10f; + + /// + /// Зомби не должны чувствовать очень далеко. + /// + [DataField] + public float MaxFlairDistance = 500f; // Sunrise-End } diff --git a/Resources/Prototypes/Damage/modifier_sets.yml b/Resources/Prototypes/Damage/modifier_sets.yml index 6f22ea2de95..b6cb089935d 100644 --- a/Resources/Prototypes/Damage/modifier_sets.yml +++ b/Resources/Prototypes/Damage/modifier_sets.yml @@ -198,9 +198,9 @@ - type: damageModifierSet id: Zombie #Blunt resistant and immune to biological threats, but can be hacked apart and burned coefficients: - Blunt: 0.1 - Piercing: 0.1 - Cold: 0.1 + Blunt: 0.2 # Sunrise-edit + Piercing: 0.2 # Surnise-edit + Cold: 0.2 # Sunrise-edit Heat: 1.25 Poison: 0.0 Radiation: 0.0 diff --git a/Resources/Prototypes/Voice/auto_emotes.yml b/Resources/Prototypes/Voice/auto_emotes.yml index 5b136f480ab..bf6752ec209 100644 --- a/Resources/Prototypes/Voice/auto_emotes.yml +++ b/Resources/Prototypes/Voice/auto_emotes.yml @@ -3,7 +3,7 @@ id: ZombieGroan emote: Scream interval: 5.0 - chance: 0.8 # Sunrise-Edit + chance: 0.5 # Sunrise-Edit если ставить меньше, то от спама звуками голова болит withChat: false # Cluwne - type: autoEmote diff --git a/Resources/Prototypes/_Sunrise/Actions/zombie_actions.yml b/Resources/Prototypes/_Sunrise/Actions/zombie_actions.yml index 354a3364db8..3b28af5a0e6 100644 --- a/Resources/Prototypes/_Sunrise/Actions/zombie_actions.yml +++ b/Resources/Prototypes/_Sunrise/Actions/zombie_actions.yml @@ -4,7 +4,7 @@ components: - type: WorldTargetAction useDelay: 15 - icon: _Sunrise/Zombie/Actions/test.png # TODO: Спрайты + icon: _Sunrise/Zombie/Actions/jump.png itemIconStyle: NoItem checkCanAccess: false range: 200 @@ -16,6 +16,6 @@ components: - type: InstantAction useDelay: 15 - icon: _Sunrise/Zombie/Actions/test.png # TODO: Спрайты + icon: _Sunrise/Zombie/Actions/the_look.png itemIconStyle: NoItem event: !type:ZombieFlairActionEvent diff --git a/Resources/Textures/_Sunrise/Zombie/Actions/jump.png b/Resources/Textures/_Sunrise/Zombie/Actions/jump.png new file mode 100644 index 0000000000000000000000000000000000000000..500cabba859fd2341e5925b9951a6a6509936072 GIT binary patch literal 2119 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