Core/Mechanics: refactor XP (and in fact, honor/reputation/kill credit) rewarding routine and get rid of copy/pasted code.
This commit is contained in:
@@ -1949,91 +1949,8 @@ void Battleground::SetBracket(PvPDifficultyEntry const* bracketEntry)
|
||||
SetLevelRange(bracketEntry->minLevel,bracketEntry->maxLevel);
|
||||
}
|
||||
|
||||
void Battleground::RewardXPAtKill(Player* plr, Player* victim)
|
||||
void Battleground::RewardXPAtKill(Player* killer, Player* victim)
|
||||
{
|
||||
if (!sWorld->getBoolConfig(CONFIG_BG_XP_FOR_KILL) || !plr || !victim)
|
||||
return;
|
||||
|
||||
uint32 xp = 0;
|
||||
Player* member_with_max_level = NULL;
|
||||
Player* not_gray_member_with_max_level = NULL;
|
||||
|
||||
if (Group *pGroup = plr->GetGroup())//should be always in a raid group while in any bg
|
||||
{
|
||||
uint32 count = 0;
|
||||
uint32 sum_level = 0;
|
||||
for (GroupReference *itr = pGroup->GetFirstMember(); itr != NULL; itr = itr->next())
|
||||
{
|
||||
Player* member = itr->getSource();
|
||||
if (!member || !member->isAlive()) // only for alive
|
||||
continue;
|
||||
|
||||
if (!member->IsAtGroupRewardDistance(victim)) // at req. distance
|
||||
continue;
|
||||
|
||||
++count;
|
||||
sum_level += member->getLevel();
|
||||
if (!member_with_max_level || member_with_max_level->getLevel() < member->getLevel())
|
||||
member_with_max_level = member;
|
||||
|
||||
uint32 gray_level = Trinity::XP::GetGrayLevel(member->getLevel());
|
||||
if (victim->getLevel() > gray_level && (!not_gray_member_with_max_level
|
||||
|| not_gray_member_with_max_level->getLevel() < member->getLevel()))
|
||||
not_gray_member_with_max_level = member;
|
||||
}
|
||||
|
||||
if (member_with_max_level)
|
||||
{
|
||||
xp = !not_gray_member_with_max_level ? 0 : Trinity::XP::Gain(not_gray_member_with_max_level, victim);
|
||||
|
||||
if (!xp)
|
||||
return;
|
||||
|
||||
float group_rate = 1.0f;
|
||||
|
||||
for (GroupReference *itr = pGroup->GetFirstMember(); itr != NULL; itr = itr->next())
|
||||
{
|
||||
Player* pGroupGuy = itr->getSource();
|
||||
if (!pGroupGuy)
|
||||
continue;
|
||||
|
||||
if (!pGroupGuy->IsAtGroupRewardDistance(victim))
|
||||
continue; // member (alive or dead) or his corpse at req. distance
|
||||
|
||||
float rate = group_rate * float(pGroupGuy->getLevel()) / sum_level;
|
||||
|
||||
// XP updated only for alive group member
|
||||
if (pGroupGuy->isAlive() && not_gray_member_with_max_level && pGroupGuy->getLevel() <= not_gray_member_with_max_level->getLevel())
|
||||
{
|
||||
uint32 itr_xp = (member_with_max_level == not_gray_member_with_max_level) ? uint32(xp * rate) : uint32((xp * rate / 2) + 1);
|
||||
|
||||
// handle SPELL_AURA_MOD_XP_PCT auras
|
||||
Unit::AuraEffectList const& ModXPPctAuras = plr->GetAuraEffectsByType(SPELL_AURA_MOD_XP_PCT);
|
||||
for (Unit::AuraEffectList::const_iterator i = ModXPPctAuras.begin(); i != ModXPPctAuras.end(); ++i)
|
||||
AddPctN(itr_xp, (*i)->GetAmount());
|
||||
|
||||
pGroupGuy->GiveXP(itr_xp, victim);
|
||||
if (Pet* pet = pGroupGuy->GetPet())
|
||||
pet->GivePetXP(itr_xp / 2);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else//should be always in a raid group while in any BG, but you never know...
|
||||
{
|
||||
xp = Trinity::XP::Gain(plr, victim);
|
||||
|
||||
if (!xp)
|
||||
return;
|
||||
|
||||
// handle SPELL_AURA_MOD_XP_PCT auras
|
||||
Unit::AuraEffectList const& ModXPPctAuras = plr->GetAuraEffectsByType(SPELL_AURA_MOD_XP_PCT);
|
||||
for (Unit::AuraEffectList::const_iterator i = ModXPPctAuras.begin(); i != ModXPPctAuras.end(); ++i)
|
||||
AddPctN(xp, (*i)->GetAmount());
|
||||
|
||||
plr->GiveXP(xp, victim);
|
||||
|
||||
if (Pet* pet = plr->GetPet())
|
||||
pet->GivePetXP(xp);
|
||||
}
|
||||
if (sWorld->getBoolConfig(CONFIG_BG_XP_FOR_KILL) && killer && victim)
|
||||
killer->RewardPlayerAndGroupAtKill(victim, true);
|
||||
}
|
||||
|
||||
@@ -584,7 +584,7 @@ class Battleground
|
||||
/* virtual score-array - get's used in bg-subclasses */
|
||||
int32 m_TeamScores[BG_TEAMS_COUNT];
|
||||
|
||||
void RewardXPAtKill(Player* plr, Player* victim);
|
||||
void RewardXPAtKill(Player* killer, Player* victim);
|
||||
bool CanAwardArenaPoints() const { return m_LevelMin >= BG_AWARD_ARENA_POINTS_MIN_LEVEL; }
|
||||
|
||||
protected:
|
||||
|
||||
Reference in New Issue
Block a user