mirror of
https://github.com/azerothcore/azerothcore-wotlk.git
synced 2025-11-10 21:04:26 +08:00
feat(Scripts): Add hooks to allow modules to override arena rating updates
Add two new ArenaScript hooks to prevent module conflicts: - OnBeforeArenaTeamMemberUpdate: Allows modules to skip core's MemberWon/MemberLost rating calculations by returning true - CanSaveArenaStatsForMember: Allows modules to prevent core from writing to character_arena_stats table by returning false Hook locations: - Arena.cpp: Wrap MemberWon/MemberLost calls (lines 358, 366) - ArenaTeam.cpp: Wrap character_arena_stats DB write (line 969) Use case: Modules implementing alternative rating systems (like Glicko-2) can now completely override core arena ratings without database conflicts or redundant calculations. When hooks return default values (false/true respectively), core behavior is unchanged, maintaining backward compatibility.
This commit is contained in:
parent
3ad5e97206
commit
758b74e805
@ -355,12 +355,18 @@ void Arena::EndBattleground(TeamId winnerTeamId)
|
||||
player->CastSpell(player, SPELL_LAST_MAN_STANDING, true);
|
||||
}
|
||||
|
||||
winnerArenaTeam->MemberWon(player, loserMatchmakerRating, winnerMatchmakerChange);
|
||||
if (!sScriptMgr->OnBeforeArenaTeamMemberUpdate(winnerArenaTeam, player, true, loserMatchmakerRating, winnerMatchmakerChange))
|
||||
{
|
||||
winnerArenaTeam->MemberWon(player, loserMatchmakerRating, winnerMatchmakerChange);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
loserArenaTeam->MemberLost(player, winnerMatchmakerRating, loserMatchmakerChange);
|
||||
if (!sScriptMgr->OnBeforeArenaTeamMemberUpdate(loserArenaTeam, player, false, winnerMatchmakerRating, loserMatchmakerChange))
|
||||
{
|
||||
loserArenaTeam->MemberLost(player, winnerMatchmakerRating, loserMatchmakerChange);
|
||||
}
|
||||
|
||||
// Arena lost => reset the win_rated_arena having the "no_lose" condition
|
||||
player->ResetAchievementCriteria(ACHIEVEMENT_CRITERIA_CONDITION_NO_LOSE, 0);
|
||||
|
||||
@ -966,12 +966,15 @@ void ArenaTeam::SaveToDB(bool forceMemberSave)
|
||||
stmt->SetData(6, itr->Guid.GetCounter());
|
||||
trans->Append(stmt);
|
||||
|
||||
stmt = CharacterDatabase.GetPreparedStatement(CHAR_REP_CHARACTER_ARENA_STATS);
|
||||
stmt->SetData(0, itr->Guid.GetCounter());
|
||||
stmt->SetData(1, GetSlot());
|
||||
stmt->SetData(2, itr->MatchMakerRating);
|
||||
stmt->SetData(3, itr->MaxMMR);
|
||||
trans->Append(stmt);
|
||||
if (sScriptMgr->CanSaveArenaStatsForMember(this, itr->Guid))
|
||||
{
|
||||
stmt = CharacterDatabase.GetPreparedStatement(CHAR_REP_CHARACTER_ARENA_STATS);
|
||||
stmt->SetData(0, itr->Guid.GetCounter());
|
||||
stmt->SetData(1, GetSlot());
|
||||
stmt->SetData(2, itr->MatchMakerRating);
|
||||
stmt->SetData(3, itr->MaxMMR);
|
||||
trans->Append(stmt);
|
||||
}
|
||||
}
|
||||
|
||||
CharacterDatabase.CommitTransaction(trans);
|
||||
|
||||
@ -44,6 +44,16 @@ void ScriptMgr::OnArenaStart(Battleground* bg)
|
||||
CALL_ENABLED_HOOKS(ArenaScript, ARENAHOOK_ON_ARENA_START, script->OnArenaStart(bg));
|
||||
}
|
||||
|
||||
bool ScriptMgr::OnBeforeArenaTeamMemberUpdate(ArenaTeam* team, Player* player, bool won, uint32 opponentMatchmakerRating, int32 matchmakerChange)
|
||||
{
|
||||
CALL_ENABLED_BOOLEAN_HOOKS(ArenaScript, ARENAHOOK_ON_BEFORE_TEAM_MEMBER_UPDATE, script->OnBeforeArenaTeamMemberUpdate(team, player, won, opponentMatchmakerRating, matchmakerChange));
|
||||
}
|
||||
|
||||
bool ScriptMgr::CanSaveArenaStatsForMember(ArenaTeam* team, ObjectGuid playerGuid)
|
||||
{
|
||||
CALL_ENABLED_BOOLEAN_HOOKS(ArenaScript, ARENAHOOK_CAN_SAVE_ARENA_STATS_FOR_MEMBER, !script->CanSaveArenaStatsForMember(team, playerGuid));
|
||||
}
|
||||
|
||||
ArenaScript::ArenaScript(const char* name, std::vector<uint16> enabledHooks)
|
||||
: ScriptObject(name, ARENAHOOK_END)
|
||||
{
|
||||
|
||||
@ -29,6 +29,8 @@ enum ArenaHook
|
||||
ARENAHOOK_CAN_SAVE_TO_DB,
|
||||
ARENAHOOK_ON_BEFORE_CHECK_WIN_CONDITION,
|
||||
ARENAHOOK_ON_ARENA_START,
|
||||
ARENAHOOK_ON_BEFORE_TEAM_MEMBER_UPDATE,
|
||||
ARENAHOOK_CAN_SAVE_ARENA_STATS_FOR_MEMBER,
|
||||
ARENAHOOK_END
|
||||
};
|
||||
|
||||
@ -51,6 +53,10 @@ public:
|
||||
[[nodiscard]] virtual bool CanSaveToDB(ArenaTeam* /*team*/) { return true; }
|
||||
|
||||
virtual void OnArenaStart(Battleground* /* bg */) { };
|
||||
|
||||
[[nodiscard]] virtual bool OnBeforeArenaTeamMemberUpdate(ArenaTeam* /*team*/, Player* /*player*/, bool /*won*/, uint32 /*opponentMatchmakerRating*/, int32 /*matchmakerChange*/) { return false; }
|
||||
|
||||
[[nodiscard]] virtual bool CanSaveArenaStatsForMember(ArenaTeam* /*team*/, ObjectGuid /*playerGuid*/) { return true; }
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
@ -660,6 +660,8 @@ public: /* ArenaScript */
|
||||
bool CanSaveToDB(ArenaTeam* team);
|
||||
bool OnBeforeArenaCheckWinConditions(Battleground* const bg);
|
||||
void OnArenaStart(Battleground* const bg);
|
||||
bool OnBeforeArenaTeamMemberUpdate(ArenaTeam* team, Player* player, bool won, uint32 opponentMatchmakerRating, int32 matchmakerChange);
|
||||
bool CanSaveArenaStatsForMember(ArenaTeam* team, ObjectGuid playerGuid);
|
||||
|
||||
public: /* MiscScript */
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user