AzerothCore 3.3.5a
OpenSource WoW Emulator
Loading...
Searching...
No Matches
KillRewarder Class Reference

#include "KillRewarder.h"

Public Member Functions

 KillRewarder (Player *killer, Unit *victim, bool isBattleGround)
 
void Reward ()
 

Private Member Functions

void _InitXP (Player *player)
 
void _InitGroupData ()
 
void _RewardHonor (Player *player)
 
void _RewardXP (Player *player, float rate)
 
void _RewardReputation (Player *player, float rate)
 
void _RewardKillCredit (Player *player)
 
void _RewardPlayer (Player *player, bool isDungeon)
 
void _RewardGroup ()
 

Private Attributes

Player_killer
 
Unit_victim
 
Group_group
 
float _groupRate
 
Player_maxNotGrayMember
 
uint32 _count
 
uint32 _aliveSumLevel
 
uint32 _sumLevel
 
uint32 _xp
 
bool _isFullXP
 
uint8 _maxLevel
 
bool _isBattleGround
 
bool _isPvP
 

Detailed Description

Constructor & Destructor Documentation

◆ KillRewarder()

KillRewarder::KillRewarder ( Player killer,
Unit victim,
bool  isBattleGround 
)
65 :
66// 1. Initialize internal variables to default values.
67 _killer(killer), _victim(victim), _group(killer->GetGroup()),
68 _groupRate(1.0f), _maxNotGrayMember(nullptr), _count(0), _aliveSumLevel(0), _sumLevel(0), _xp(0),
69 _isFullXP(false), _maxLevel(0), _isBattleGround(isBattleGround), _isPvP(false)
70{
71 // mark the credit as pvp if victim is player
72 if (victim->GetTypeId() == TYPEID_PLAYER)
73 _isPvP = true;
74 // or if its owned by player and its not a vehicle
75 else if (victim->GetCharmerOrOwnerGUID().IsPlayer())
76 _isPvP = !victim->IsVehicle();
77
79}
@ TYPEID_PLAYER
Definition: ObjectGuid.h:38
TypeID GetTypeId() const
Definition: Object.h:121
bool IsPlayer() const
Definition: ObjectGuid.h:170
uint8 _maxLevel
Definition: KillRewarder.h:55
uint32 _count
Definition: KillRewarder.h:50
float _groupRate
Definition: KillRewarder.h:48
uint32 _xp
Definition: KillRewarder.h:53
uint32 _aliveSumLevel
Definition: KillRewarder.h:51
uint32 _sumLevel
Definition: KillRewarder.h:52
Player * _maxNotGrayMember
Definition: KillRewarder.h:49
Unit * _victim
Definition: KillRewarder.h:46
Player * _killer
Definition: KillRewarder.h:45
bool _isBattleGround
Definition: KillRewarder.h:56
Group * _group
Definition: KillRewarder.h:47
void _InitGroupData()
Definition: KillRewarder.cpp:81
bool _isFullXP
Definition: KillRewarder.h:54
bool _isPvP
Definition: KillRewarder.h:57
Group * GetGroup()
Definition: Player.h:2418
bool IsVehicle() const
Definition: Unit.h:1416
ObjectGuid GetCharmerOrOwnerGUID() const
Definition: Unit.h:1830

References _InitGroupData(), _isPvP, Unit::GetCharmerOrOwnerGUID(), Object::GetTypeId(), ObjectGuid::IsPlayer(), Unit::IsVehicle(), and TYPEID_PLAYER.

Member Function Documentation

◆ _InitGroupData()

void KillRewarder::_InitGroupData ( )
private
82{
83 if (_group)
84 {
85 // 2. In case when player is in group, initialize variables necessary for group calculations:
86 for (GroupReference* itr = _group->GetFirstMember(); itr != nullptr; itr = itr->next())
87 if (Player* member = itr->GetSource())
88 if ((_killer == member || member->IsAtGroupRewardDistance(_victim)))
89 {
90 const uint8 lvl = member->GetLevel();
91 if (member->IsAlive())
92 {
93 // 2.1. _count - number of alive group members within reward distance;
94 ++_count;
95 // 2.2. _aliveSumLevel - sum of levels of alive group members within reward distance;
96 _aliveSumLevel += lvl;
97 // 2.3. _maxLevel - maximum level of alive group member within reward distance;
98 if (_maxLevel < lvl)
99 {
100 _maxLevel = lvl;
101 }
102 // 2.4. _maxNotGrayMember - maximum level of alive group member within reward distance,
103 // for whom victim is not gray;
104 uint32 grayLevel = Acore::XP::GetGrayLevel(lvl);
105 if (_victim->GetLevel() > grayLevel && (!_maxNotGrayMember || _maxNotGrayMember->GetLevel() < lvl))
106 {
107 _maxNotGrayMember = member;
108 }
109 }
110 // 2.5. _sumLevel - sum of levels of group members within reward distance;
111 _sumLevel += lvl;
112 }
113 // 2.6. _isFullXP - flag identifying that for all group members victim is not gray,
114 // so 100% XP will be rewarded (50% otherwise).
116 }
117 else
118 _count = 1;
119}
std::uint8_t uint8
Definition: Define.h:110
std::uint32_t uint32
Definition: Define.h:108
uint8 GetGrayLevel(uint8 pl_level)
Definition: Formulas.h:41
Definition: Player.h:1046
bool IsAtGroupRewardDistance(WorldObject const *pRewardSource) const
Definition: Player.cpp:12655
uint8 GetLevel() const
Definition: Unit.h:1420
GroupReference * GetFirstMember()
Definition: Group.h:242
Definition: GroupReference.h:27
GroupReference * next()
Definition: GroupReference.h:36

References _aliveSumLevel, _count, _group, _isFullXP, _killer, _maxLevel, _maxNotGrayMember, _sumLevel, _victim, Group::GetFirstMember(), Acore::XP::GetGrayLevel(), Unit::GetLevel(), Player::IsAtGroupRewardDistance(), and GroupReference::next().

Referenced by KillRewarder().

◆ _InitXP()

void KillRewarder::_InitXP ( Player player)
private
122{
123 // Get initial value of XP for kill.
124 // XP is given:
125 // * on battlegrounds;
126 // * otherwise, not in PvP;
127 // * not if killer is on vehicle.
128 if (_victim && (_isBattleGround || (!_isPvP && !_killer->GetVehicle())))
130
131 if (_xp && !_isBattleGround && _victim) // pussywizard: npcs with relatively low hp give lower exp
132 if (_victim->GetTypeId() == TYPEID_UNIT)
134 if (ct->ModHealth <= 0.75f && ct->ModHealth >= 0.0f)
135 _xp = uint32(_xp * ct->ModHealth);
136}
@ TYPEID_UNIT
Definition: ObjectGuid.h:37
uint32 Gain(Player *player, Unit *unit, bool isBattleGround=false)
Definition: Formulas.cpp:71
CreatureTemplate const * GetCreatureTemplate() const
Definition: Creature.h:197
Definition: CreatureData.h:176
Creature * ToCreature()
Definition: Object.h:197
Vehicle * GetVehicle() const
Definition: Unit.h:2354

References _isBattleGround, _isPvP, _killer, _victim, _xp, Acore::XP::Gain(), Creature::GetCreatureTemplate(), Object::GetTypeId(), Unit::GetVehicle(), Object::ToCreature(), and TYPEID_UNIT.

Referenced by _RewardGroup(), and Reward().

◆ _RewardGroup()

void KillRewarder::_RewardGroup ( )
private
228{
229 if (_maxLevel)
230 {
232 // 3.1.1. Initialize initial XP amount based on maximum level of group member,
233 // for whom victim is not gray.
235 // To avoid unnecessary calculations and calls,
236 // proceed only if XP is not ZERO or player is not on battleground
237 // (battleground rewards only XP, that's why).
238 if (!_isBattleGround || _xp)
239 {
240 const bool isDungeon = !_isPvP && sMapStore.LookupEntry(_killer->GetMapId())->IsDungeon();
241 if (!_isBattleGround)
242 {
243 // 3.1.2. Alter group rate if group is in raid (not for battlegrounds).
244 const bool isRaid = !_isPvP && sMapStore.LookupEntry(_killer->GetMapId())->IsRaid() && _group->isRaidGroup();
246 }
247
248 // 3.1.3. Reward each group member (even dead or corpse) within reward distance.
249 for (GroupReference* itr = _group->GetFirstMember(); itr != nullptr; itr = itr->next())
250 {
251 if (Player* member = itr->GetSource())
252 {
253 if (_killer == member || member->IsAtGroupRewardDistance(_victim))
254 {
255 _RewardPlayer(member, isDungeon);
256 // Xinef: only count players
257 //if (_victim->GetTypeId() == TYPEID_PLAYER)
258 // member->UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL, 1, 0, _victim);
259 }
260 }
261 }
262 }
263 }
264}
DBCStorage< MapEntry > sMapStore(MapEntryfmt)
float xp_in_group_rate(uint32 count, bool isRaid)
Definition: Formulas.h:114
uint32 GetMapId() const
Definition: Position.h:276
void _RewardPlayer(Player *player, bool isDungeon)
Definition: KillRewarder.cpp:194
void _InitXP(Player *player)
Definition: KillRewarder.cpp:121
bool isRaidGroup() const
Definition: Group.cpp:2210

References _count, _group, _groupRate, _InitXP(), _isBattleGround, _isPvP, _killer, _maxLevel, _maxNotGrayMember, _RewardPlayer(), _victim, _xp, Group::GetFirstMember(), WorldLocation::GetMapId(), Player::IsAtGroupRewardDistance(), Group::isRaidGroup(), GroupReference::next(), sMapStore, and Acore::XP::xp_in_group_rate().

Referenced by Reward().

◆ _RewardHonor()

void KillRewarder::_RewardHonor ( Player player)
private
139{
140 // Rewarded player must be alive.
141 if (player->IsAlive())
142 player->RewardHonor(_victim, _count, -1);
143}
bool RewardHonor(Unit *victim, uint32 groupsize, int32 honor=-1, bool awardXP=true)
Definition: Player.cpp:5967
bool IsAlive() const
Definition: Unit.h:1808

References _count, _victim, Unit::IsAlive(), and Player::RewardHonor().

Referenced by _RewardPlayer().

◆ _RewardKillCredit()

void KillRewarder::_RewardKillCredit ( Player player)
private
184{
185 // 4.4. Give kill credit (player must not be in group, or he must be alive or without corpse).
186 if (!_group || player->IsAlive() || !player->GetCorpse())
187 if (Creature* target = _victim->ToCreature())
188 {
189 player->KilledMonster(target->GetCreatureTemplate(), target->GetGUID());
190 player->UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_KILL_CREATURE_TYPE, target->GetCreatureType(), 1, target);
191 }
192}
@ ACHIEVEMENT_CRITERIA_TYPE_KILL_CREATURE_TYPE
Definition: DBCEnums.h:194
Definition: Creature.h:46
void UpdateAchievementCriteria(AchievementCriteriaTypes type, uint32 miscValue1=0, uint32 miscValue2=0, Unit *unit=nullptr)
Definition: PlayerUpdates.cpp:2128
void KilledMonster(CreatureTemplate const *cInfo, ObjectGuid guid)
Definition: PlayerQuest.cpp:1899
Corpse * GetCorpse() const
Definition: Player.cpp:4607

References _group, _victim, ACHIEVEMENT_CRITERIA_TYPE_KILL_CREATURE_TYPE, Player::GetCorpse(), Unit::IsAlive(), Player::KilledMonster(), Object::ToCreature(), and Player::UpdateAchievementCriteria().

Referenced by _RewardPlayer().

◆ _RewardPlayer()

void KillRewarder::_RewardPlayer ( Player player,
bool  isDungeon 
)
private
195{
196 // 4. Reward player.
197 if (!_isBattleGround)
198 {
199 // 4.1. Give honor (player must be alive and not on BG).
200 _RewardHonor(player);
201 // 4.1.1 Send player killcredit for quests with PlayerSlain
203 player->KilledPlayerCredit();
204 }
205 // Give XP only in PvE or in battlegrounds.
206 // Give reputation and kill credit only in PvE.
207 if (!_isPvP || _isBattleGround)
208 {
209 float xpRate = _group ? _groupRate * float(player->GetLevel()) / _aliveSumLevel : /*Personal rate is 100%.*/ 1.0f; // Group rate depends on the sum of levels.
210 float reputationRate = _group ? _groupRate * float(player->GetLevel()) / _sumLevel : /*Personal rate is 100%.*/ 1.0f; // Group rate depends on the sum of levels.
211 sScriptMgr->OnRewardKillRewarder(player, isDungeon, xpRate); // Personal rate is 100%.
212
213 if (_xp)
214 {
215 // 4.2. Give XP.
216 _RewardXP(player, xpRate);
217 }
218 if (!_isBattleGround)
219 {
220 // If killer is in dungeon then all members receive full reputation at kill.
221 _RewardReputation(player, isDungeon ? 1.0f : reputationRate);
222 _RewardKillCredit(player);
223 }
224 }
225}
#define sScriptMgr
Definition: ScriptMgr.h:2702
void _RewardHonor(Player *player)
Definition: KillRewarder.cpp:138
void _RewardReputation(Player *player, float rate)
Definition: KillRewarder.cpp:176
void _RewardXP(Player *player, float rate)
Definition: KillRewarder.cpp:145
void _RewardKillCredit(Player *player)
Definition: KillRewarder.cpp:183
void KilledPlayerCredit(uint16 count=1)
Definition: PlayerQuest.cpp:1979

References _aliveSumLevel, _group, _groupRate, _isBattleGround, _isPvP, _RewardHonor(), _RewardKillCredit(), _RewardReputation(), _RewardXP(), _sumLevel, _victim, _xp, Unit::GetLevel(), Object::GetTypeId(), Player::KilledPlayerCredit(), sScriptMgr, and TYPEID_PLAYER.

Referenced by _RewardGroup(), and Reward().

◆ _RewardReputation()

void KillRewarder::_RewardReputation ( Player player,
float  rate 
)
private
177{
178 // 4.3. Give reputation (player must not be on BG).
179 // Even dead players and corpses are rewarded.
180 player->RewardReputation(_victim, rate);
181}
void RewardReputation(Unit *victim, float rate)
Definition: Player.cpp:5850

References _victim, and Player::RewardReputation().

Referenced by _RewardPlayer().

◆ _RewardXP()

void KillRewarder::_RewardXP ( Player player,
float  rate 
)
private
146{
147 uint32 xp(_xp);
148 if (_group)
149 {
150 // 4.2.1. If player is in group, adjust XP:
151 // * set to 0 if player's level is more than maximum level of not gray member;
152 // * cut XP in half if _isFullXP is false.
153 if (_maxNotGrayMember && player->IsAlive() &&
154 _maxNotGrayMember->GetLevel() >= player->GetLevel())
155 xp = _isFullXP ?
156 uint32(xp * rate) : // Reward FULL XP if all group members are not gray.
157 uint32(xp * rate / 2) + 1; // Reward only HALF of XP if some of group members are gray.
158 else
159 xp = 0;
160 }
161 if (xp)
162 {
163 // 4.2.2. Apply auras modifying rewarded XP (SPELL_AURA_MOD_XP_PCT).
165 for (Unit::AuraEffectList::const_iterator i = auras.begin(); i != auras.end(); ++i)
166 AddPct(xp, (*i)->GetAmount());
167
168 // 4.2.3. Give XP to player.
169 player->GiveXP(xp, _victim, _groupRate);
170 if (Pet* pet = player->GetPet())
171 // 4.2.4. If player has pet, reward pet with XP (100% for single player, 50% for group case).
172 pet->GivePetXP(_group ? xp / 2 : xp);
173 }
174}
T AddPct(T &base, U pct)
Definition: Util.h:67
@ SPELL_AURA_MOD_XP_PCT
Definition: SpellAuraDefines.h:263
Definition: Pet.h:40
Pet * GetPet() const
Definition: Player.cpp:8784
void GiveXP(uint32 xp, Unit *victim, float group_rate=1.0f, bool isLFGReward=false)
Definition: Player.cpp:2341
AuraEffectList const & GetAuraEffectsByType(AuraType type) const
Definition: Unit.h:1967
std::list< AuraEffect * > AuraEffectList
Definition: Unit.h:1306

References _group, _groupRate, _isFullXP, _maxNotGrayMember, _victim, _xp, AddPct(), Unit::GetAuraEffectsByType(), Unit::GetLevel(), Player::GetPet(), Player::GiveXP(), Unit::IsAlive(), and SPELL_AURA_MOD_XP_PCT.

Referenced by _RewardPlayer().

◆ Reward()

void KillRewarder::Reward ( )
267{
268 // 3. Reward killer (and group, if necessary).
269 if (_group)
270 // 3.1. If killer is in group, reward group.
271 _RewardGroup();
272 else
273 {
274 // 3.2. Reward single killer (not group case).
275 // 3.2.1. Initialize initial XP amount based on killer's level.
277 // To avoid unnecessary calculations and calls,
278 // proceed only if XP is not ZERO or player is not on battleground
279 // (battleground rewards only XP, that's why).
280 if (!_isBattleGround || _xp)
281 // 3.2.2. Reward killer.
282 if (_killer->IsInMap(_victim)) // pussywizard: killer may be on other map (crashfix), when killing in a group same map is required, so its not a problem
283 _RewardPlayer(_killer, false);
284 }
285
286 // 5. Credit instance encounter.
287 if (Creature* victim = _victim->ToCreature())
288 if (victim->IsDungeonBoss())
289 if (Map* map = _victim->FindMap())
290 map->UpdateEncounterState(ENCOUNTER_CREDIT_KILL_CREATURE, _victim->GetEntry(), _victim);
291}
@ ENCOUNTER_CREDIT_KILL_CREATURE
Definition: Map.h:307
uint32 GetEntry() const
Definition: Object.h:109
Map * FindMap() const
Definition: Object.h:518
bool IsInMap(WorldObject const *obj) const
Definition: Object.cpp:1285
void _RewardGroup()
Definition: KillRewarder.cpp:227
Definition: Map.h:312

References _group, _InitXP(), _isBattleGround, _killer, _RewardGroup(), _RewardPlayer(), _victim, _xp, ENCOUNTER_CREDIT_KILL_CREATURE, WorldObject::FindMap(), Object::GetEntry(), WorldObject::IsInMap(), and Object::ToCreature().

Referenced by Player::RewardPlayerAndGroupAtKill().

Member Data Documentation

◆ _aliveSumLevel

uint32 KillRewarder::_aliveSumLevel
private

Referenced by _InitGroupData(), and _RewardPlayer().

◆ _count

uint32 KillRewarder::_count
private

◆ _group

Group* KillRewarder::_group
private

◆ _groupRate

float KillRewarder::_groupRate
private

◆ _isBattleGround

bool KillRewarder::_isBattleGround
private

◆ _isFullXP

bool KillRewarder::_isFullXP
private

Referenced by _InitGroupData(), and _RewardXP().

◆ _isPvP

bool KillRewarder::_isPvP
private

◆ _killer

Player* KillRewarder::_killer
private

◆ _maxLevel

uint8 KillRewarder::_maxLevel
private

Referenced by _InitGroupData(), and _RewardGroup().

◆ _maxNotGrayMember

Player* KillRewarder::_maxNotGrayMember
private

◆ _sumLevel

uint32 KillRewarder::_sumLevel
private

Referenced by _InitGroupData(), and _RewardPlayer().

◆ _victim

◆ _xp

uint32 KillRewarder::_xp
private