From 1ea98d4f51d7079dd0ccec0d2ca653396fb793d6 Mon Sep 17 00:00:00 2001 From: Hondacrx Date: Sun, 25 May 2025 10:39:42 -0400 Subject: [PATCH] Core/Creature: Implement aggro grace period Port From (https://github.com/TrinityCore/TrinityCore/commit/26d1337461114506ca57e2265d3dc5e96fd08f82) --- Source/Game/AI/CoreAI/CreatureAI.cs | 2 +- .../Game/Entities/Creature/Creature.Fields.cs | 2 ++ Source/Game/Entities/Creature/Creature.cs | 15 +++++++++++ Source/Game/Maps/GridNotifiers.cs | 25 +++++++++++++++++++ 4 files changed, 43 insertions(+), 1 deletion(-) diff --git a/Source/Game/AI/CoreAI/CreatureAI.cs b/Source/Game/AI/CoreAI/CreatureAI.cs index 5e368c626..c9a08204a 100644 --- a/Source/Game/AI/CoreAI/CreatureAI.cs +++ b/Source/Game/AI/CoreAI/CreatureAI.cs @@ -102,7 +102,7 @@ namespace Game.AI if (me.IsEngaged()) return; - if (me.HasReactState(ReactStates.Aggressive) && me.CanStartAttack(who, false)) + if (me.HasReactState(ReactStates.Aggressive) && me.CanStartAttack(who, false) && (me.IsAggroGracePeriodExpired() || me.GetMap().Instanceable())) me.EngageWithTarget(who); } diff --git a/Source/Game/Entities/Creature/Creature.Fields.cs b/Source/Game/Entities/Creature/Creature.Fields.cs index 20660ee13..ce057dfbb 100644 --- a/Source/Game/Entities/Creature/Creature.Fields.cs +++ b/Source/Game/Entities/Creature/Creature.Fields.cs @@ -69,6 +69,8 @@ namespace Game.Entities bool triggerJustAppeared; bool m_respawnCompatibilityMode; + bool _aggroGracePeriodExpired; + public uint[] m_spells = new uint[SharedConst.MaxCreatureSpells]; // Timers diff --git a/Source/Game/Entities/Creature/Creature.cs b/Source/Game/Entities/Creature/Creature.cs index 1b81073a9..922ddf2b1 100644 --- a/Source/Game/Entities/Creature/Creature.cs +++ b/Source/Game/Entities/Creature/Creature.cs @@ -638,6 +638,16 @@ namespace Game.Entities // Creatures with CREATURE_STATIC_FLAG_2_FORCE_PARTY_MEMBERS_INTO_COMBAT periodically force party members into combat ForcePartyMembersIntoCombat(); + + // creatures should only attack surroundings initially after heartbeat has passed or until attacked + if (!_aggroGracePeriodExpired) + { + _aggroGracePeriodExpired = true; + + // trigger MoveInLineOfSight + CreatureAggroGracePeriodExpiredNotifier notifier = new(this); + Cell.VisitAllObjects(this, notifier, GetVisibilityRange()); + } } public void Regenerate(PowerType power) @@ -1080,6 +1090,8 @@ namespace Game.Entities { base.AtEngage(target); + _aggroGracePeriodExpired = true; + GetThreatManager().ResetUpdateTimer(); if (!HasFlag(CreatureStaticFlags2.AllowMountedCombat)) @@ -1680,6 +1692,8 @@ namespace Game.Entities void SetInteractSpellId(int interactSpellId) { SetUpdateFieldValue(m_values.ModifyValue(m_unitData).ModifyValue(m_unitData.InteractSpellID), interactSpellId); } + public bool IsAggroGracePeriodExpired() { return _aggroGracePeriodExpired; } + public void OverrideSparringHealthPct(List healthPct) { _sparringHealthPct = healthPct.SelectRandom(); @@ -2148,6 +2162,7 @@ namespace Game.Entities ai.Reset(); triggerJustAppeared = true; + _aggroGracePeriodExpired = false; uint poolid = GetCreatureData() != null ? GetCreatureData().poolId : 0; if (poolid != 0) diff --git a/Source/Game/Maps/GridNotifiers.cs b/Source/Game/Maps/GridNotifiers.cs index 7e8aa34c2..ce664b896 100644 --- a/Source/Game/Maps/GridNotifiers.cs +++ b/Source/Game/Maps/GridNotifiers.cs @@ -360,6 +360,31 @@ namespace Game.Maps bool isCreature; } + public class CreatureAggroGracePeriodExpiredNotifier : Notifier + { + Creature i_creature; + + public CreatureAggroGracePeriodExpiredNotifier(Creature c) + { + i_creature = c; + } + + public override void Visit(IList objs) + { + foreach (var creature in objs) + { + CreatureUnitRelocationWorker(creature, i_creature); + CreatureUnitRelocationWorker(i_creature, creature); + } + } + + public override void Visit(IList objs) + { + foreach (var player in objs) + CreatureUnitRelocationWorker(i_creature, player); + } + } + public class PacketSenderRef : IDoWork { ServerPacket Data;