From b4f2e6f8f7f2a06b45d7beec8a6f32d07586bebb Mon Sep 17 00:00:00 2001 From: Andrew <47818697+Nyeriah@users.noreply.github.com> Date: Sat, 4 Jul 2026 15:10:51 -0300 Subject: [PATCH] fix(Core/Creature): stop mid-fight summons and proximity aggro from preferring totems/pets over players (#26457) Co-authored-by: Claude Fable 5 --- src/server/game/Entities/Creature/Creature.cpp | 5 +++++ src/server/game/Entities/Object/Object.cpp | 5 +++-- src/server/game/Grids/Notifiers/GridNotifiers.cpp | 13 +++++++++++++ src/server/game/Grids/Notifiers/GridNotifiers.h | 4 +++- 4 files changed, 24 insertions(+), 3 deletions(-) diff --git a/src/server/game/Entities/Creature/Creature.cpp b/src/server/game/Entities/Creature/Creature.cpp index 8d3612cbf4..60acd2781d 100644 --- a/src/server/game/Entities/Creature/Creature.cpp +++ b/src/server/game/Entities/Creature/Creature.cpp @@ -1925,6 +1925,11 @@ bool Creature::CanStartAttack(Unit const* who, bool force) const if (!_IsTargetAcceptable(who)) return false; + // Totems never pull proximity aggro; they are only attacked in response + // to threat they generate themselves (e.g. Searing Totem) + if (who->IsTotem()) + return false; + if (IsNeutralToAll() || !IsWithinDistInMap(who, GetAggroRange(who) + m_CombatDistance, true, false, false)) return false; } diff --git a/src/server/game/Entities/Object/Object.cpp b/src/server/game/Entities/Object/Object.cpp index 8a0eebffce..7ff045e0b6 100644 --- a/src/server/game/Entities/Object/Object.cpp +++ b/src/server/game/Entities/Object/Object.cpp @@ -2337,8 +2337,9 @@ TempSummon* Map::SummonCreature(uint32 entry, Position const& pos, SummonPropert summon->InitSummon(); - // call MoveInLineOfSight for nearby creatures - Acore::AIRelocationNotifier notifier(*summon); + // call MoveInLineOfSight for nearby players and creatures; players are visited + // first (grid typelist order) so aggressive summons prefer them over pets/totems + Acore::AIRelocationNotifier notifier(*summon, true); Cell::VisitObjects(summon, notifier, GetVisibilityRange()); return summon; diff --git a/src/server/game/Grids/Notifiers/GridNotifiers.cpp b/src/server/game/Grids/Notifiers/GridNotifiers.cpp index 28f87f2863..e38c8030c9 100644 --- a/src/server/game/Grids/Notifiers/GridNotifiers.cpp +++ b/src/server/game/Grids/Notifiers/GridNotifiers.cpp @@ -186,6 +186,19 @@ void AIRelocationNotifier::Visit(CreatureMapType& m) } } +void AIRelocationNotifier::Visit(PlayerMapType& m) +{ + if (!includePlayers) + return; + + Creature* creature = i_unit.ToCreature(); + if (!creature || creature->IsMoveInLineOfSightStrictlyDisabled()) + return; + + for (PlayerMapType::iterator iter = m.begin(); iter != m.end(); ++iter) + CreatureUnitRelocationWorker(creature, iter->GetSource()); +} + // Uses visibility map void MessageDistDeliverer::Visit(VisiblePlayersMap const& m) { diff --git a/src/server/game/Grids/Notifiers/GridNotifiers.h b/src/server/game/Grids/Notifiers/GridNotifiers.h index 8484eb3b57..1f078197f6 100644 --- a/src/server/game/Grids/Notifiers/GridNotifiers.h +++ b/src/server/game/Grids/Notifiers/GridNotifiers.h @@ -91,9 +91,11 @@ namespace Acore { Unit& i_unit; bool isCreature; - explicit AIRelocationNotifier(Unit& unit) : i_unit(unit), isCreature(unit.IsCreature()) {} + bool includePlayers; + explicit AIRelocationNotifier(Unit& unit, bool includePlayers = false) : i_unit(unit), isCreature(unit.IsCreature()), includePlayers(includePlayers) {} template void Visit(GridRefMgr&) {} void Visit(CreatureMapType&); + void Visit(PlayerMapType&); }; enum class TeamFilter