Skip to content

feat(Core/Unit): Add OnStopCombatHook#25215

Open
DoubledaCoder wants to merge 4 commits intoazerothcore:masterfrom
DoubledaCoder:master
Open

feat(Core/Unit): Add OnStopCombatHook#25215
DoubledaCoder wants to merge 4 commits intoazerothcore:masterfrom
DoubledaCoder:master

Conversation

@DoubledaCoder
Copy link
Copy Markdown

A hook to allow for custom logic to apply when combat ends for all unit types.

Changes Proposed:

This PR proposes changes to:
The UnitScript to include a new hook for custom logic to be applied when combat finishes. The hook is for a custom module i've adapted and expanded from a patch which synchronises the creature level to the player level. My issue is that there was no appropriate unit script hook for when combat finishes that allows for custom logic onto creatures.

OnEnterCombat is the initial trigger hook to sync the level, OnDamage hook is the trigger I've used which limits griefing and facilitates multi-level combat, however when combat ends e.g. leash, evade, the creature would return to the initial coordinates at whatever level it was set to. So if a Lv80 ran through a starting zone and aggroed 10 mobs, a lv5 entering that area would be swarmed (even though OnEnterCombat means they will sync to the correct level) death would be hard to avoid. With this hook, regardless of the reason, when combat is being cleared, the creature resets to within its level template bounds.

AI-assisted Pull Requests

Copilot was only used as an assistant. All code has been tested in the context of the Playerbot fork.

Tests Performed:

Playerbots were running for 1 hour with Free for all PVP active and the mod-mob-sync-level active doing quests etc. I also ran the below test to specifically check whether the hook is successfully triggered using the mod.

How to Test the Changes:

  1. Install the mod-mob-sync-level
  2. Using a GM character attack a creature that is 10 or so lower levels than the character so it switches it level then:
    a. run away from the creature until it resets
    b. kill it and wait to see what occurs on respawn
    c. fly up into the air so it cannot attack you
    d. go into an out of bounds area the creature cannot reach

You can help by testing PRs and writing your feedback here on the PR's page on GitHub. Follow the instructions here:

http://www.azerothcore.org/wiki/How-to-test-a-PR

REMEMBER: when testing a PR that changes something generic (i.e. a part of code that handles more than one specific thing), the tester should not only check that the PR does its job (e.g. fixing spell XXX) but especially check that the PR does not cause any regression (i.e. introducing new bugs).

For example: if a PR fixes spell X by changing a part of code that handles spells X, Y, and Z, we should not only test X, but we should test Y and Z as well.

A hook to allow for custom logic to apply when combat ends for all unit types.
@github-actions github-actions bot added CORE Related to the core file-cpp Used to trigger the matrix build labels Mar 25, 2026
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds a new UnitScript hook intended to let modules run custom logic when a Unit stops combat (e.g., for resetting mob-sync level changes after evade/leash/death scenarios).

Changes:

  • Introduces OnUnitStopCombat(Unit*) in ScriptMgr / UnitScript (enum + virtual hook + dispatcher).
  • Calls the new hook from Unit::CombatStop().

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 1 comment.

File Description
src/server/game/Scripting/ScriptMgr.h Exposes ScriptMgr::OnUnitStopCombat(Unit*) in the UnitScript section.
src/server/game/Scripting/ScriptDefines/UnitScript.h Adds a new UnitHook entry and a new UnitScript::OnUnitStopCombat(Unit*) virtual hook.
src/server/game/Scripting/ScriptDefines/UnitScript.cpp Implements ScriptMgr::OnUnitStopCombat(Unit*) using CALL_ENABLED_HOOKS.
src/server/game/Entities/Unit/Unit.cpp Invokes the new hook from Unit::CombatStop().
Comments suppressed due to low confidence (1)

src/server/game/Entities/Unit/Unit.cpp:7475

  • OnUnitStopCombat is invoked at the very start of Unit::CombatStop(), before the unit has actually stopped attacking / cleared attackers / updated combat state. This means scripts observing IsInCombat() (or attacker lists) inside the hook will still see the pre-stop state, and the hook also won’t fire for the common “combat ended naturally” path driven by CombatManager::UpdateOwnerCombatState() (which calls AtExitCombat() without calling CombatStop()). Consider moving this hook to the point where combat truly transitions to out-of-combat (e.g., after combat state is cleared, or in Unit::AtExitCombat() / the combat-manager state transition).
    sScriptMgr->OnUnitStopCombat(this);
    if (includingCast && IsNonMeleeSpellCast(false))
        InterruptNonMeleeSpells(false);

    AttackStop();

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

copilot check
As suggested by Copilot, better to put at the end so the state is not in combat when the hook triggers. Not useful for my module logic but I can see how that would be broadly beneficial.
@sudlud sudlud requested a review from Copilot March 29, 2026 06:17
@sudlud sudlud changed the title OnStopCombatHook feat(Core/Unit): Add OnStopCombatHook Mar 29, 2026
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 4 out of 4 changed files in this pull request and generated 1 comment.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

CORE Related to the core file-cpp Used to trigger the matrix build

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants