2 * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 #ifndef __BATTLEGROUND_H
20 #define __BATTLEGROUND_H
23 #include "SharedDefines.h"
31 struct WorldSafeLocsEntry
;
33 enum BattleGroundSounds
35 SOUND_HORDE_WINS
= 8454,
36 SOUND_ALLIANCE_WINS
= 8455,
40 enum BattleGroundQuests
42 SPELL_WS_QUEST_REWARD
= 43483,
43 SPELL_AB_QUEST_REWARD
= 43484,
44 SPELL_AV_QUEST_REWARD
= 43475,
45 SPELL_AV_QUEST_KILLED_BOSS
= 23658,
46 SPELL_EY_QUEST_REWARD
= 43477,
47 SPELL_AB_QUEST_REWARD_4_BASES
= 24061,
48 SPELL_AB_QUEST_REWARD_5_BASES
= 24064
51 enum BattleGroundMarks
53 SPELL_WS_MARK_LOSER
= 24950,
54 SPELL_WS_MARK_WINNER
= 24951,
55 SPELL_AB_MARK_LOSER
= 24952,
56 SPELL_AB_MARK_WINNER
= 24953,
57 SPELL_AV_MARK_LOSER
= 24954,
58 SPELL_AV_MARK_WINNER
= 24955,
59 ITEM_EY_MARK_OF_HONOR
= 29024
62 enum BattleGroundMarksCount
64 ITEM_WINNER_COUNT
= 3,
68 enum BattleGroundSpells
70 SPELL_WAITING_FOR_RESURRECT
= 2584, // Waiting to Resurrect
71 SPELL_SPIRIT_HEAL_CHANNEL
= 22011, // Spirit Heal Channel
72 SPELL_SPIRIT_HEAL
= 22012, // Spirit Heal
73 SPELL_RESURRECTION_VISUAL
= 24171, // Resurrection Impact Visual
74 SPELL_ARENA_PREPARATION
= 32727, // use this one, 32728 not correct
75 SPELL_ALLIANCE_GOLD_FLAG
= 32724,
76 SPELL_ALLIANCE_GREEN_FLAG
= 32725,
77 SPELL_HORDE_GOLD_FLAG
= 35774,
78 SPELL_HORDE_GREEN_FLAG
= 35775,
79 SPELL_PREPARATION
= 44521, // Preparation
80 SPELL_SPIRIT_HEAL_MANA
= 44535, // Spirit Heal
81 SPELL_RECENTLY_DROPPED_FLAG
= 42792, // Recently Dropped Flag
82 SPELL_AURA_PLAYER_INACTIVE
= 43681 // Inactive
85 enum BattleGroundTimeIntervals
87 RESURRECTION_INTERVAL
= 30000, // ms
88 REMIND_INTERVAL
= 30000, // ms
89 INVITE_ACCEPT_WAIT_TIME
= 80000, // ms
90 TIME_TO_AUTOREMOVE
= 120000, // ms
91 MAX_OFFLINE_TIME
= 300000, // ms
92 START_DELAY0
= 120000, // ms
93 START_DELAY1
= 60000, // ms
94 START_DELAY2
= 30000, // ms
95 START_DELAY3
= 15000, // ms used only in arena
96 RESPAWN_ONE_DAY
= 86400, // secs
97 RESPAWN_IMMEDIATELY
= 0, // secs
98 BUFF_RESPAWN_TIME
= 180, // secs
99 BG_HONOR_SCORE_TICKS
= 330 // points
102 enum BattleGroundBuffObjects
104 BG_OBJECTID_SPEEDBUFF_ENTRY
= 179871,
105 BG_OBJECTID_REGENBUFF_ENTRY
= 179904,
106 BG_OBJECTID_BERSERKERBUFF_ENTRY
= 179905
109 const uint32 Buff_Entries
[3] = { BG_OBJECTID_SPEEDBUFF_ENTRY
, BG_OBJECTID_REGENBUFF_ENTRY
, BG_OBJECTID_BERSERKERBUFF_ENTRY
};
111 enum BattleGroundStatus
114 STATUS_WAIT_QUEUE
= 1,
115 STATUS_WAIT_JOIN
= 2,
116 STATUS_IN_PROGRESS
= 3,
117 STATUS_WAIT_LEAVE
= 4 // custom
120 struct BattleGroundPlayer
122 uint32 LastOnlineTime
; // for tracking and removing offline players from queue after 5 minutes
123 uint32 Team
; // Player's team
126 struct BattleGroundObjectInfo
128 BattleGroundObjectInfo() : object(NULL
), timer(0), spellid(0) {}
135 // handle the queue types and bg types separately to enable joining queue for different sized arenas at the same time
136 enum BattleGroundQueueTypeId
138 BATTLEGROUND_QUEUE_NONE
= 0,
139 BATTLEGROUND_QUEUE_AV
= 1,
140 BATTLEGROUND_QUEUE_WS
= 2,
141 BATTLEGROUND_QUEUE_AB
= 3,
142 BATTLEGROUND_QUEUE_EY
= 4,
143 BATTLEGROUND_QUEUE_SA
= 5,
144 BATTLEGROUND_QUEUE_2v2
= 6,
145 BATTLEGROUND_QUEUE_3v3
= 7,
146 BATTLEGROUND_QUEUE_5v5
= 8,
151 SCORE_KILLING_BLOWS
= 1,
153 SCORE_HONORABLE_KILLS
= 3,
154 SCORE_BONUS_HONOR
= 4,
155 //EY, but in MSG_PVP_LOG_DATA opcode!
156 SCORE_DAMAGE_DONE
= 5,
157 SCORE_HEALING_DONE
= 6,
159 SCORE_FLAG_CAPTURES
= 7,
160 SCORE_FLAG_RETURNS
= 8,
162 SCORE_BASES_ASSAULTED
= 9,
163 SCORE_BASES_DEFENDED
= 10,
165 SCORE_GRAVEYARDS_ASSAULTED
= 11,
166 SCORE_GRAVEYARDS_DEFENDED
= 12,
167 SCORE_TOWERS_ASSAULTED
= 13,
168 SCORE_TOWERS_DEFENDED
= 14,
169 SCORE_MINES_CAPTURED
= 15,
170 SCORE_LEADERS_KILLED
= 16,
171 SCORE_SECONDARY_OBJECTIVES
= 17
172 // TODO : implement them
182 enum BattleGroundType
184 TYPE_BATTLEGROUND
= 3,
188 enum BattleGroundWinner
195 enum BattleGroundTeamId
197 BG_TEAM_ALLIANCE
= 0,
201 enum BattleGroundJoinError
204 BG_JOIN_ERR_OFFLINE_MEMBER
= 1,
205 BG_JOIN_ERR_GROUP_TOO_MANY
= 2,
206 BG_JOIN_ERR_MIXED_FACTION
= 3,
207 BG_JOIN_ERR_MIXED_LEVELS
= 4,
208 BG_JOIN_ERR_MIXED_ARENATEAM
= 5,
209 BG_JOIN_ERR_GROUP_MEMBER_ALREADY_IN_QUEUE
= 6,
210 BG_JOIN_ERR_GROUP_DESERTER
= 7,
211 BG_JOIN_ERR_ALL_QUEUES_USED
= 8,
212 BG_JOIN_ERR_GROUP_NOT_ENOUGH
= 9
215 class BattleGroundScore
218 BattleGroundScore() : KillingBlows(0), HonorableKills(0), Deaths(0), DamageDone(0), HealingDone(0), BonusHonor(0) {};
219 virtual ~BattleGroundScore() //virtual destructor is used when deleting score from scores map
224 uint32 HonorableKills
;
231 This class is used to:
232 1. Add player to battleground
233 2. Remove player from battleground
234 3. some certain cases, same for all battlegrounds
235 4. It has properties same for all battlegrounds
239 friend class BattleGroundMgr
;
244 /*BattleGround(const BattleGround& bg);*/
245 virtual ~BattleGround();
246 virtual void Update(uint32 diff
); // must be implemented in BG subclass of BG specific update code, but must in begginning call parent version
247 virtual bool SetupBattleGround() // must be implemented in BG subclass
251 virtual void Reset(); // resets all common properties for battlegrounds, must be implemented and called in BG subclass
255 char const* GetName() const { return m_Name
; }
256 BattleGroundTypeId
GetTypeID() const { return m_TypeID
; }
257 uint32
GetQueueId() const { return m_QueueId
; }
258 uint32
GetInstanceID() const { return m_InstanceID
; }
259 uint32
GetStatus() const { return m_Status
; }
260 uint32
GetStartTime() const { return m_StartTime
; }
261 uint32
GetEndTime() const { return m_EndTime
; }
262 uint32
GetLastResurrectTime() const { return m_LastResurrectTime
; }
263 uint32
GetMaxPlayers() const { return m_MaxPlayers
; }
264 uint32
GetMinPlayers() const { return m_MinPlayers
; }
266 uint32
GetMinLevel() const { return m_LevelMin
; }
267 uint32
GetMaxLevel() const { return m_LevelMax
; }
269 uint32
GetMaxPlayersPerTeam() const { return m_MaxPlayersPerTeam
; }
270 uint32
GetMinPlayersPerTeam() const { return m_MinPlayersPerTeam
; }
272 int GetStartDelayTime() const { return m_StartDelayTime
; }
273 uint8
GetArenaType() const { return m_ArenaType
; }
274 uint8
GetWinner() const { return m_Winner
; }
275 uint32
GetBattlemasterEntry() const;
278 void SetName(char const* Name
) { m_Name
= Name
; }
279 void SetTypeID(BattleGroundTypeId TypeID
) { m_TypeID
= TypeID
; }
280 void SetQueueId(uint32 ID
) { m_QueueId
= ID
; }
281 void SetInstanceID(uint32 InstanceID
) { m_InstanceID
= InstanceID
; }
282 void SetStatus(uint32 Status
) { m_Status
= Status
; }
283 void SetStartTime(uint32 Time
) { m_StartTime
= Time
; }
284 void SetEndTime(uint32 Time
) { m_EndTime
= Time
; }
285 void SetLastResurrectTime(uint32 Time
) { m_LastResurrectTime
= Time
; }
286 void SetMaxPlayers(uint32 MaxPlayers
) { m_MaxPlayers
= MaxPlayers
; }
287 void SetMinPlayers(uint32 MinPlayers
) { m_MinPlayers
= MinPlayers
; }
288 void SetLevelRange(uint32 min
, uint32 max
) { m_LevelMin
= min
; m_LevelMax
= max
; }
289 void SetRated(bool state
) { m_IsRated
= state
; }
290 void SetArenaType(uint8 type
) { m_ArenaType
= type
; }
291 void SetArenaorBGType(bool _isArena
) { m_IsArena
= _isArena
; }
292 void SetWinner(uint8 winner
) { m_Winner
= winner
; }
294 void ModifyStartDelayTime(int diff
) { m_StartDelayTime
-= diff
; }
295 void SetStartDelayTime(int Time
) { m_StartDelayTime
= Time
; }
297 void SetMaxPlayersPerTeam(uint32 MaxPlayers
) { m_MaxPlayersPerTeam
= MaxPlayers
; }
298 void SetMinPlayersPerTeam(uint32 MinPlayers
) { m_MinPlayersPerTeam
= MinPlayers
; }
300 void AddToBGFreeSlotQueue(); //this queue will be useful when more battlegrounds instances will be available
301 void RemoveFromBGFreeSlotQueue(); //this method could delete whole BG instance, if another free is available
303 void DecreaseInvitedCount(uint32 team
) { (team
== ALLIANCE
) ? --m_InvitedAlliance
: --m_InvitedHorde
; }
304 void IncreaseInvitedCount(uint32 team
) { (team
== ALLIANCE
) ? ++m_InvitedAlliance
: ++m_InvitedHorde
; }
305 uint32
GetInvitedCount(uint32 team
) const
307 if( team
== ALLIANCE
)
308 return m_InvitedAlliance
;
310 return m_InvitedHorde
;
312 bool HasFreeSlotsForTeam(uint32 Team
) const;
313 bool HasFreeSlots() const;
314 uint32
GetFreeSlotsForTeam(uint32 Team
) const;
316 bool isArena() const { return m_IsArena
; }
317 bool isBattleGround() const { return !m_IsArena
; }
318 bool isRated() const { return m_IsRated
; }
320 typedef std::map
<uint64
, BattleGroundPlayer
> BattleGroundPlayerMap
;
321 BattleGroundPlayerMap
const& GetPlayers() const { return m_Players
; }
322 uint32
GetPlayersSize() const { return m_Players
.size(); }
323 uint32
GetRemovedPlayersSize() const { return m_RemovedPlayers
.size(); }
325 std::map
<uint64
, BattleGroundScore
*>::const_iterator
GetPlayerScoresBegin() const { return m_PlayerScores
.begin(); }
326 std::map
<uint64
, BattleGroundScore
*>::const_iterator
GetPlayerScoresEnd() const { return m_PlayerScores
.end(); }
327 uint32
GetPlayerScoresSize() const { return m_PlayerScores
.size(); }
329 uint32
GetReviveQueueSize() const { return m_ReviveQueue
.size(); }
331 void AddPlayerToResurrectQueue(uint64 npc_guid
, uint64 player_guid
);
332 void RemovePlayerFromResurrectQueue(uint64 player_guid
);
334 void StartBattleGround();
337 void SetMapId(uint32 MapID
) { m_MapId
= MapID
; }
338 uint32
GetMapId() const { return m_MapId
; }
340 void SetTeamStartLoc(uint32 TeamID
, float X
, float Y
, float Z
, float O
);
341 void GetTeamStartLoc(uint32 TeamID
, float &X
, float &Y
, float &Z
, float &O
) const
343 uint8 idx
= GetTeamIndexByTeamId(TeamID
);
344 X
= m_TeamStartLocX
[idx
];
345 Y
= m_TeamStartLocY
[idx
];
346 Z
= m_TeamStartLocZ
[idx
];
347 O
= m_TeamStartLocO
[idx
];
350 /* Packet Transfer */
351 // method that should fill worldpacket with actual world states (not yet implemented for all battlegrounds!)
352 virtual void FillInitialWorldStates(WorldPacket
& /*data*/) {}
353 void SendPacketToTeam(uint32 TeamID
, WorldPacket
*packet
, Player
*sender
= NULL
, bool self
= true);
354 void SendPacketToAll(WorldPacket
*packet
);
355 void PlaySoundToTeam(uint32 SoundID
, uint32 TeamID
);
356 void PlaySoundToAll(uint32 SoundID
);
357 void CastSpellOnTeam(uint32 SpellID
, uint32 TeamID
);
358 void RewardHonorToTeam(uint32 Honor
, uint32 TeamID
);
359 void RewardReputationToTeam(uint32 faction_id
, uint32 Reputation
, uint32 TeamID
);
360 void RewardMark(Player
*plr
,uint32 count
);
361 void SendRewardMarkByMail(Player
*plr
,uint32 mark
, uint32 count
);
362 void RewardQuest(Player
*plr
);
363 void UpdateWorldState(uint32 Field
, uint32 Value
);
364 void UpdateWorldStateForPlayer(uint32 Field
, uint32 Value
, Player
*Source
);
365 void EndBattleGround(uint32 winner
);
366 void BlockMovement(Player
*plr
);
368 void SendMessageToAll(char const* text
);
369 void SendMessageToAll(int32 entry
);
372 Group
*GetBgRaid(uint32 TeamID
) const { return TeamID
== ALLIANCE
? m_BgRaids
[BG_TEAM_ALLIANCE
] : m_BgRaids
[BG_TEAM_HORDE
]; }
373 void SetBgRaid(uint32 TeamID
, Group
*bg_raid
);
375 virtual void UpdatePlayerScore(Player
*Source
, uint32 type
, uint32 value
);
377 uint8
GetTeamIndexByTeamId(uint32 Team
) const { return Team
== ALLIANCE
? BG_TEAM_ALLIANCE
: BG_TEAM_HORDE
; }
378 uint32
GetPlayersCountByTeam(uint32 Team
) const { return m_PlayersCount
[GetTeamIndexByTeamId(Team
)]; }
379 uint32
GetAlivePlayersCountByTeam(uint32 Team
) const; // used in arenas to correctly handle death in spirit of redemption / last stand etc. (killer = killed) cases
380 void UpdatePlayersCountByTeam(uint32 Team
, bool remove
)
383 --m_PlayersCount
[GetTeamIndexByTeamId(Team
)];
385 ++m_PlayersCount
[GetTeamIndexByTeamId(Team
)];
388 // used for rated arena battles
389 void SetArenaTeamIdForTeam(uint32 Team
, uint32 ArenaTeamId
) { m_ArenaTeamIds
[GetTeamIndexByTeamId(Team
)] = ArenaTeamId
; }
390 uint32
GetArenaTeamIdForTeam(uint32 Team
) const { return m_ArenaTeamIds
[GetTeamIndexByTeamId(Team
)]; }
391 void SetArenaTeamRatingChangeForTeam(uint32 Team
, int32 RatingChange
) { m_ArenaTeamRatingChanges
[GetTeamIndexByTeamId(Team
)] = RatingChange
; }
392 int32
GetArenaTeamRatingChangeForTeam(uint32 Team
) const { return m_ArenaTeamRatingChanges
[GetTeamIndexByTeamId(Team
)]; }
394 /* Triggers handle */
395 // must be implemented in BG subclass
396 virtual void HandleAreaTrigger(Player
* /*Source*/, uint32
/*Trigger*/) {}
397 // must be implemented in BG subclass if need AND call base class generic code
398 virtual void HandleKillPlayer(Player
*player
, Player
*killer
);
400 /* Battleground events */
401 /* these functions will return true event is possible, but false if player is bugger */
402 virtual void EventPlayerDroppedFlag(Player
* /*player*/) {}
403 virtual void EventPlayerClickedOnFlag(Player
* /*player*/, GameObject
* /*target_obj*/) {}
404 virtual void EventPlayerCapturedFlag(Player
* /*player*/) {}
407 virtual WorldSafeLocsEntry
const* GetClosestGraveYard(float /*x*/, float /*y*/, float /*z*/, uint32
/*team*/) { return NULL
; }
409 virtual void AddPlayer(Player
*plr
); // must be implemented in BG subclass
411 void AddOrSetPlayerToCorrectBgGroup(Player
*plr
, uint64 plr_guid
, uint32 team
);
413 virtual void RemovePlayerAtLeave(uint64 guid
, bool Transport
, bool SendPacket
);
414 // can be extended in in BG subclass
416 void HandleTriggerBuff(uint64
const& go_guid
);
418 // TODO: make this protected:
419 typedef std::vector
<uint64
> BGObjects
;
420 typedef std::vector
<uint64
> BGCreatures
;
421 BGObjects m_BgObjects
;
422 BGCreatures m_BgCreatures
;
423 void SpawnBGObject(uint32 type
, uint32 respawntime
);
424 bool AddObject(uint32 type
, uint32 entry
, float x
, float y
, float z
, float o
, float rotation0
, float rotation1
, float rotation2
, float rotation3
, uint32 respawnTime
= 0);
425 // void SpawnBGCreature(uint32 type, uint32 respawntime);
426 Creature
* AddCreature(uint32 entry
, uint32 type
, uint32 teamval
, float x
, float y
, float z
, float o
, uint32 respawntime
= 0);
427 bool DelCreature(uint32 type
);
428 bool DelObject(uint32 type
);
429 bool AddSpiritGuide(uint32 type
, float x
, float y
, float z
, float o
, uint32 team
);
431 void DoorOpen(uint32 type
);
432 void DoorClose(uint32 type
);
433 const char *GetMangosString(int32 entry
);
435 virtual bool HandlePlayerUnderMap(Player
* plr
) {return false;}
437 // since arenas can be AvA or Hvh, we have to get the "temporary" team of a player
438 uint32
GetPlayerTeam(uint64 guid
);
439 bool IsPlayerInBattleGround(uint64 guid
);
440 void PlayerRelogin(Player
* plr
);
442 void SetDeleteThis() {m_SetDeleteThis
= true;}
445 //this method is called, when BG cannot spawn its own spirit guide, or something is wrong, It correctly ends BattleGround
450 std::map
<uint64
, BattleGroundScore
*> m_PlayerScores
;
451 // must be implemented in BG subclass
452 virtual void RemovePlayer(Player
* /*player*/, uint64
/*guid*/) {}
454 /* Player lists, those need to be accessible by inherited classes */
455 BattleGroundPlayerMap m_Players
;
456 // Spirit Guide guid + Player list GUIDS
457 std::map
<uint64
, std::vector
<uint64
> > m_ReviveQueue
;
460 this is important variable used for invitation messages
468 BattleGroundTypeId m_TypeID
;
469 uint32 m_InstanceID
; //BattleGround Instance's GUID!
473 uint32 m_LastResurrectTime
;
475 uint8 m_ArenaType
; // 2=2v2, 3=3v3, 5=5v5
476 bool m_InBGFreeSlotQueue
; // used to make sure that BG is only once inserted into the BattleGroundMgr.BGFreeSlotQueue[bgTypeId] deque
477 bool m_SetDeleteThis
; // used for safe deletion of the bg after end / all players leave
478 // this variable is not used .... it can be found in many other ways... but to store it in BG object instance is useless
479 //uint8 m_BattleGroundType; // 3=BG, 4=arena
480 //instead of uint8 (in previous line) is bool used
482 uint8 m_Winner
; // 0=alliance, 1=horde, 2=none
483 int32 m_StartDelayTime
;
484 bool m_IsRated
; // is this battle rated?
485 bool m_PrematureCountDown
;
486 uint32 m_PrematureCountDownTimer
;
490 std::vector
<uint64
> m_ResurrectQueue
; // Player GUID
491 std::map
<uint64
, uint8
> m_RemovedPlayers
; // uint8 is remove type (0 - bgqueue, 1 - bg, 2 - resurrect queue)
493 /* Invited counters are useful for player invitation to BG - do not allow, if BG is started to one faction to have 2 more players than another faction */
494 /* Invited counters will be changed only when removing already invited player from queue, removing player from battleground and inviting player to BG */
495 /* Invited players counters*/
496 uint32 m_InvitedAlliance
;
497 uint32 m_InvitedHorde
;
500 Group
*m_BgRaids
[2]; // 0 - alliance, 1 - horde
502 /* Players count by team */
503 uint32 m_PlayersCount
[2];
505 /* Arena team ids by team */
506 uint32 m_ArenaTeamIds
[2];
508 int32 m_ArenaTeamRatingChanges
[2];
513 uint32 m_MaxPlayersPerTeam
;
515 uint32 m_MinPlayersPerTeam
;
520 float m_TeamStartLocX
[2];
521 float m_TeamStartLocY
[2];
522 float m_TeamStartLocZ
[2];
523 float m_TeamStartLocO
[2];