void WorldSession::HandleBattlemasterJoinArena(WorldPacket & recv_data) { sLog->outDebug(LOG_FILTER_NETWORKIO, "WORLD: CMSG_BATTLEMASTER_JOIN_ARENA"); //recv_data.hexlike(); uint8 arenaslot; // 2v2, 3v3 or 5v5 Group * grp = NULL; bool isRated = true, asGroup = true; recv_data >> arenaslot; // ignore if we already in BG or BG queue if (_player->InBattleground()) return; uint8 arenatype = 0; uint32 arenaRating = 0; uint32 matchmakerRating = 0; switch(arenaslot) { case 0: arenatype = ARENA_TYPE_2v2; break; case 1: arenatype = ARENA_TYPE_3v3; break; case 2: arenatype = ARENA_TYPE_5v5; break; default: sLog->outError("Unknown arena slot %u at HandleBattlemasterJoinArena()", arenaslot); return; } //check existance Battleground* bg = sBattlegroundMgr->GetBattlegroundTemplate(BATTLEGROUND_AA); if (!bg) { sLog->outError("Battleground: template bg (all arenas) not found"); return; } if (sDisableMgr->IsDisabledFor(DISABLE_TYPE_BATTLEGROUND, BATTLEGROUND_AA, NULL)) { ChatHandler(this).PSendSysMessage(LANG_ARENA_DISABLED); return; } BattlegroundTypeId bgTypeId = bg->GetTypeID(); BattlegroundQueueTypeId bgQueueTypeId = BattlegroundMgr::BGQueueTypeId(bgTypeId, arenatype); PvPDifficultyEntry const* bracketEntry = GetBattlegroundBracketByLevel(bg->GetMapId(), _player->getLevel()); if (!bracketEntry) return; GroupJoinBattlegroundResult err = ERR_GROUP_JOIN_BATTLEGROUND_FAIL; if (!asGroup) { // check if already in queue if (_player->GetBattlegroundQueueIndex(bgQueueTypeId) < PLAYER_MAX_BATTLEGROUND_QUEUES) //player is already in this queue return; // check if has free queue slots if (!_player->HasFreeBattlegroundQueueId()) return; } else { grp = _player->GetGroup(); // no group found, error if (!grp) return; if (grp->GetLeaderGUID() != _player->GetGUID()) return; err = grp->CanJoinBattlegroundQueue(bg, bgQueueTypeId, arenatype, arenatype, (bool)isRated, arenaslot); } uint32 ateamId = 0; if (isRated) { ateamId = _player->GetArenaTeamId(arenaslot); // check real arenateam existence only here (if it was moved to group->CanJoin .. () then we would ahve to get it twice) ArenaTeam * at = sObjectMgr->GetArenaTeamById(ateamId); if (!at) { _player->GetSession()->SendNotInArenaTeamPacket(arenatype); return; } // get the team rating for queueing arenaRating = at->GetRating(); matchmakerRating = at->GetAverageMMR(grp); // the arenateam id must match for everyone in the group if (arenaRating <= 0) arenaRating = 1; } BattlegroundQueue &bgQueue = sBattlegroundMgr->m_BattlegroundQueues[bgQueueTypeId]; if (asGroup) { uint32 avgTime = 0; if (err > 0) { sLog->outDebug(LOG_FILTER_BATTLEGROUND, "Battleground: arena join as group start"); if (isRated) { sLog->outDebug(LOG_FILTER_BATTLEGROUND, "Battleground: arena team id %u, leader %s queued with matchmaker rating %u for type %u", _player->GetArenaTeamId(arenaslot), _player->GetName(), matchmakerRating, arenatype); bg->SetRated(true); } else bg->SetRated(false); GroupQueueInfo * ginfo = bgQueue.AddGroup(_player, grp, bgTypeId, bracketEntry, arenatype, isRated, false, arenaRating, matchmakerRating, ateamId); avgTime = bgQueue.GetAverageQueueWaitTime(ginfo, bracketEntry->GetBracketId()); } for (GroupReference *itr = grp->GetFirstMember(); itr != NULL; itr = itr->next()) { Player *member = itr->getSource(); if (!member) continue; WorldPacket data; if (err <= 0) { sBattlegroundMgr->BuildGroupJoinedBattlegroundPacket(&data, err); member->GetSession()->SendPacket(&data); continue; } // add to queue uint32 queueSlot = member->AddBattlegroundQueueId(bgQueueTypeId); // send status packet (in queue) sBattlegroundMgr->BuildBattlegroundStatusPacket(&data, bg, queueSlot, STATUS_WAIT_QUEUE, avgTime, 0, arenatype); member->GetSession()->SendPacket(&data); sBattlegroundMgr->BuildGroupJoinedBattlegroundPacket(&data, err); member->GetSession()->SendPacket(&data); sLog->outDebug(LOG_FILTER_BATTLEGROUND, "Battleground: player joined queue for arena as group bg queue type %u bg type %u: GUID %u, NAME %s", bgQueueTypeId, bgTypeId, member->GetGUIDLow(), member->GetName()); } } else { GroupQueueInfo * ginfo = bgQueue.AddGroup(_player, NULL, bgTypeId, bracketEntry, arenatype, isRated, false, arenaRating, matchmakerRating, ateamId); uint32 avgTime = bgQueue.GetAverageQueueWaitTime(ginfo, bracketEntry->GetBracketId()); uint32 queueSlot = _player->AddBattlegroundQueueId(bgQueueTypeId); WorldPacket data; // send status packet (in queue) sBattlegroundMgr->BuildBattlegroundStatusPacket(&data, bg, queueSlot, STATUS_WAIT_QUEUE, avgTime, 0, arenatype); SendPacket(&data); sLog->outDebug(LOG_FILTER_BATTLEGROUND, "Battleground: player joined queue for arena, skirmish, bg queue type %u bg type %u: GUID %u, NAME %s", bgQueueTypeId, bgTypeId, _player->GetGUIDLow(), _player->GetName()); } sBattlegroundMgr->ScheduleQueueUpdate(matchmakerRating, arenatype, bgQueueTypeId, bgTypeId, bracketEntry->GetBracketId()); }
bool JoinQueueArena(Player* player, Creature* me, bool isRated, uint8 arenatype) { if (!player || !me) return false; if (sWorld->getIntConfig(CONFIG_SOLO_3V3_MIN_LEVEL) > player->getLevel()) return false; uint64 guid = player->GetGUID(); uint8 arenaslot = ArenaTeam::GetSlotByType(ARENA_TEAM_5v5); uint32 arenaRating = 0; uint32 matchmakerRating = 0; // ignore if we already in BG or BG queue if (player->InBattleground() || player->InBattlegroundQueue()) return false; //check existance Battleground* bg = sBattlegroundMgr->GetBattlegroundTemplate(BATTLEGROUND_AA); if (!bg) return false; if (DisableMgr::IsDisabledFor(DISABLE_TYPE_BATTLEGROUND, BATTLEGROUND_AA, NULL)) { ChatHandler(player->GetSession()).PSendSysMessage(LANG_ARENA_DISABLED); return false; } BattlegroundTypeId bgTypeId = bg->GetTypeID(); BattlegroundQueueTypeId bgQueueTypeId = BattlegroundMgr::BGQueueTypeId(bgTypeId, arenatype); PvPDifficultyEntry const* bracketEntry = GetBattlegroundBracketByLevel(bg->GetMapId(), player->getLevel()); if (!bracketEntry) return false; // check if already in queue if (player->GetBattlegroundQueueIndex(bgQueueTypeId) < PLAYER_MAX_BATTLEGROUND_QUEUES) //player is already in this queue return false; // check if has free queue slots if (!player->HasFreeBattlegroundQueueId()) return false; uint32 ateamId = 0; if (isRated) { ateamId = player->GetArenaTeamId(arenaslot); ArenaTeam* at = sArenaTeamMgr->GetArenaTeamById(ateamId); if (!at) { player->GetSession()->SendNotInArenaTeamPacket(arenatype); return false; } // get the team rating for queueing arenaRating = at->GetRating(); matchmakerRating = at->GetAverageMMR(); // the arenateam id must match for everyone in the group if (arenaRating <= 0) arenaRating = 1; } //BattlegroundQueue &bgQueue = sBattlegroundMgr->GetBattlegroundQueue(bgQueueTypeId); BattlegroundQueue &bgQueue = sBattlegroundMgr->m_BattlegroundQueues[bgQueueTypeId]; bg->SetRated(isRated); GroupQueueInfo* ginfo = bgQueue.AddGroup(player, NULL, bgTypeId, bracketEntry, arenatype, isRated, false, arenaRating, matchmakerRating, ateamId); uint32 avgTime = bgQueue.GetAverageQueueWaitTime(ginfo, bracketEntry->GetBracketId()); uint32 queueSlot = player->AddBattlegroundQueueId(bgQueueTypeId); WorldPacket data; // send status packet (in queue) sBattlegroundMgr->BuildBattlegroundStatusPacket(&data, bg, queueSlot, STATUS_WAIT_QUEUE, avgTime, 0, arenatype, 0); player->GetSession()->SendPacket(&data); sBattlegroundMgr->ScheduleQueueUpdate(matchmakerRating, arenatype, bgQueueTypeId, bgTypeId, bracketEntry->GetBracketId()); return true; }
bool JoinQueueArena(Player* player, Creature* me, bool isRated) { if (!player || !me) return false; if (sWorld->getIntConfig(CONFIG_ARENA_1V1_MIN_LEVEL) > player->getLevel()) return false; ObjectGuid guid = player->GetGUID(); uint8 arenaslot = RatedInfo::GetRatedSlotByType(RATED_TYPE_5v5); RatedType ratedType = RATED_TYPE_5v5; uint32 arenaRating = 0; uint32 matchmakerRating = 0; // ignore if we already in BG or BG queue if (player->InBattleground()) return false; //check existance Battleground* bg = sBattlegroundMgr->GetBattlegroundTemplate(BATTLEGROUND_AA); if (!bg) { TC_LOG_ERROR("Arena", "Battleground: template bg (all arenas) not found"); return false; } if (DisableMgr::IsDisabledFor(DISABLE_TYPE_BATTLEGROUND, BATTLEGROUND_AA, NULL)) { ChatHandler(player->GetSession()).PSendSysMessage(LANG_ARENA_DISABLED); return false; } BattlegroundTypeId bgTypeId = bg->GetTypeID(); BattlegroundQueueTypeId bgQueueTypeId = BattlegroundMgr::BGQueueTypeId(bgTypeId, ratedType); PvPDifficultyEntry const* bracketEntry = GetBattlegroundBracketByLevel(bg->GetMapId(), player->getLevel()); if (!bracketEntry) return false; GroupJoinBattlegroundResult err = ERR_GROUP_JOIN_BATTLEGROUND_DESERTERS; // check if already in queue if (player->GetBattlegroundQueueIndex(bgQueueTypeId) < PLAYER_MAX_BATTLEGROUND_QUEUES) //player is already in this queue return false; // check if has free queue slots if (!player->HasFreeBattlegroundQueueId()) return false; uint32 ateamId = 0; if (isRated) { ateamId = player->GetArenaTeamId(arenaslot); RatedInfo* at = sRatedMgr->GetRatedInfo(ateamId); // get the team rating for queueing arenaRating = at->GetMatchMakerRating(); matchmakerRating = arenaRating; // the arenateam id must match for everyone in the group if (arenaRating <= 0) arenaRating = 1; } BattlegroundQueue &bgQueue = sBattlegroundMgr->GetBattlegroundQueue(bgQueueTypeId); bg->SetRated(isRated); GroupQueueInfo* ginfo = bgQueue.AddGroup(player, NULL, bgTypeId, bracketEntry, ratedType, isRated, false, arenaRating, matchmakerRating); uint32 avgTime = bgQueue.GetAverageQueueWaitTime(ginfo, bracketEntry->GetBracketId()); uint32 queueSlot = player->AddBattlegroundQueueId(bgQueueTypeId); WorldPacket data; // send status packet (in queue) sBattlegroundMgr->BuildBattlegroundStatusPacket(&data, bg, player, queueSlot, STATUS_WAIT_QUEUE, avgTime, 0, ratedType); player->GetSession()->SendPacket(&data); sBattlegroundMgr->ScheduleQueueUpdate(matchmakerRating, ratedType, bgQueueTypeId, bgTypeId, bracketEntry->GetBracketId()); return true; }
bool ChallengeMgr::InviteGroupsToArena(Player *leader1, Player *leader2, ArenaChallengeType type) { uint8 arenatype = (type == ARENA_CHALLENGE_TYPE_1v1) ? ARENA_CHALLENGE_TYPE_2v2 : type; uint32 matchmakerRating = 0; //check existance Battleground* bg = sBattlegroundMgr->GetBattlegroundTemplate(BATTLEGROUND_AA); if (!bg) { sLog->outError("Battleground: template bg (all arenas) not found"); return false; } BattlegroundTypeId bgTypeId = bg->GetTypeID(); BattlegroundQueueTypeId bgQueueTypeId = BattlegroundMgr::BGQueueTypeId(bgTypeId, arenatype); PvPDifficultyEntry const* bracketEntry = GetBattlegroundBracketByLevel(bg->GetMapId(), 80); if (!bracketEntry) return false; GroupQueueInfo *group1, *group2; if (type == ARENA_CHALLENGE_TYPE_1v1) { group1 = CreateGroupQueueInfo(leader1, bgTypeId, arenatype); group2 = CreateGroupQueueInfo(leader2, bgTypeId, arenatype); } else { group1 = CreateGroupQueueInfo(leader1->GetGroup(), bgTypeId, arenatype); group2 = CreateGroupQueueInfo(leader2->GetGroup(), bgTypeId, arenatype); } if (!group1 || !group2) return false; for (std::map<uint64, PlayerQueueInfo*>::iterator itr = group1->Players.begin(); itr != group1->Players.end(); ++itr) { Player *player = ObjectAccessor::FindPlayer(itr->first); if (!player) return false; if (!CanInvitePlayer(player, bgQueueTypeId)) return false; } for (std::map<uint64, PlayerQueueInfo*>::iterator itr = group2->Players.begin(); itr != group2->Players.end(); ++itr) { Player *player = ObjectAccessor::FindPlayer(itr->first); if (!player) return false; if (!CanInvitePlayer(player, bgQueueTypeId)) return false; } sBattlegroundMgr->ScheduleQueueUpdate(matchmakerRating, arenatype, bgQueueTypeId, bgTypeId, bracketEntry->GetBracketId()); Battleground *arena = sBattlegroundMgr->CreateNewBattleground(bgTypeId, bracketEntry, arenatype, true); arena->SetRated(false); if (type == ARENA_CHALLENGE_TYPE_1v1) arena->Set1vs1(true); for (std::map<uint64, PlayerQueueInfo*>::iterator itr = group1->Players.begin(); itr != group1->Players.end(); ++itr) { Player *player = ObjectAccessor::FindPlayer(itr->first); if (!player) return false; uint32 queueSlot = player->AddBattlegroundQueueId(bgQueueTypeId); WorldPacket data; // send status packet (in queue) sBattlegroundMgr->BuildBattlegroundStatusPacket(&data, bg, queueSlot, STATUS_WAIT_QUEUE, 0, 0, arenatype); player->GetSession()->SendPacket(&data); player->challengeData->bg = arena; player->challengeData->ginfo = CreateGroupQueueInfo(player, bgTypeId, arenatype); player->challengeData->ginfo->IsInvitedToBGInstanceGUID = arena->GetInstanceID(); player->challengeData->ginfo->Team = ALLIANCE; } for (std::map<uint64, PlayerQueueInfo*>::iterator itr = group2->Players.begin(); itr != group2->Players.end(); ++itr) { Player *player = ObjectAccessor::FindPlayer(itr->first); if (!player) return false; uint32 queueSlot = player->AddBattlegroundQueueId(bgQueueTypeId); WorldPacket data; // send status packet (in queue) sBattlegroundMgr->BuildBattlegroundStatusPacket(&data, bg, queueSlot, STATUS_WAIT_QUEUE, 0, 0, arenatype); player->GetSession()->SendPacket(&data); player->challengeData->bg = arena; player->challengeData->ginfo = CreateGroupQueueInfo(player, bgTypeId, arenatype); player->challengeData->ginfo->IsInvitedToBGInstanceGUID = arena->GetInstanceID(); player->challengeData->ginfo->Team = HORDE; } InviteGroupToArena(group1, arena, ALLIANCE); InviteGroupToArena(group2, arena, HORDE); arena->StartBattleground(); if (!sBattlegroundMgr->HasBattleground(arena)) sBattlegroundMgr->AddBattleground(group1->IsInvitedToBGInstanceGUID, bgTypeId, arena); return true; }
void WorldSession::HandleBattlemasterJoinArena(WorldPacket& recvData) { TC_LOG_DEBUG("network", "WORLD: CMSG_BATTLEMASTER_JOIN_ARENA"); ObjectGuid guid; // arena Battlemaster guid uint8 arenaslot; // 2v2, 3v3 or 5v5 uint8 asGroup; // asGroup uint8 isRated; // isRated Group* grp = nullptr; recvData >> guid >> arenaslot >> asGroup >> isRated; // ignore if we already in BG or BG queue if (_player->InBattleground()) return; Creature* unit = GetPlayer()->GetNPCIfCanInteractWith(guid, UNIT_NPC_FLAG_BATTLEMASTER); if (!unit) return; uint8 arenatype = 0; uint32 arenaRating = 0; uint32 matchmakerRating = 0; switch (arenaslot) { case 0: arenatype = ARENA_TYPE_2v2; break; case 1: arenatype = ARENA_TYPE_3v3; break; case 2: arenatype = ARENA_TYPE_5v5; break; default: TC_LOG_ERROR("network", "Unknown arena slot %u at HandleBattlemasterJoinArena()", arenaslot); return; } //check existance Battleground* bg = sBattlegroundMgr->GetBattlegroundTemplate(BATTLEGROUND_AA); if (!bg) { TC_LOG_ERROR("network", "Battleground: template bg (all arenas) not found"); return; } if (DisableMgr::IsDisabledFor(DISABLE_TYPE_BATTLEGROUND, BATTLEGROUND_AA, nullptr)) { ChatHandler(this).PSendSysMessage(LANG_ARENA_DISABLED); return; } BattlegroundTypeId bgTypeId = bg->GetTypeID(); BattlegroundQueueTypeId bgQueueTypeId = BattlegroundMgr::BGQueueTypeId(bgTypeId, arenatype); PvPDifficultyEntry const* bracketEntry = GetBattlegroundBracketByLevel(bg->GetMapId(), _player->getLevel()); if (!bracketEntry) return; GroupJoinBattlegroundResult err = ERR_GROUP_JOIN_BATTLEGROUND_FAIL; if (!asGroup) { if (_player->isUsingLfg()) { // player is using dungeon finder or raid finder WorldPacket data; sBattlegroundMgr->BuildGroupJoinedBattlegroundPacket(&data, ERR_LFG_CANT_USE_BATTLEGROUND); _player->SendDirectMessage(&data); return; } // check if already in queue if (_player->GetBattlegroundQueueIndex(bgQueueTypeId) < PLAYER_MAX_BATTLEGROUND_QUEUES) //player is already in this queue return; // check if has free queue slots if (!_player->HasFreeBattlegroundQueueId()) return; } else { grp = _player->GetGroup(); // no group found, error if (!grp) return; if (grp->GetLeaderGUID() != _player->GetGUID()) return; err = grp->CanJoinBattlegroundQueue(bg, bgQueueTypeId, arenatype, arenatype, isRated != 0, arenaslot); } uint32 ateamId = 0; if (isRated) { ateamId = _player->GetArenaTeamId(arenaslot); // check real arenateam existence only here (if it was moved to group->CanJoin .. () then we would ahve to get it twice) ArenaTeam* at = sArenaTeamMgr->GetArenaTeamById(ateamId); if (!at) { _player->GetSession()->SendNotInArenaTeamPacket(arenatype); return; } // get the team rating for queueing arenaRating = at->GetRating(); matchmakerRating = at->GetAverageMMR(grp); // the arenateam id must match for everyone in the group if (arenaRating <= 0) arenaRating = 1; } BattlegroundQueue &bgQueue = sBattlegroundMgr->GetBattlegroundQueue(bgQueueTypeId); if (asGroup) { uint32 avgTime = 0; if (err > 0) { TC_LOG_DEBUG("bg.battleground", "Battleground: arena join as group start"); if (isRated) { TC_LOG_DEBUG("bg.battleground", "Battleground: arena team id %u, leader %s queued with matchmaker rating %u for type %u", _player->GetArenaTeamId(arenaslot), _player->GetName().c_str(), matchmakerRating, arenatype); bg->SetRated(true); } else bg->SetRated(false); GroupQueueInfo* ginfo = bgQueue.AddGroup(_player, grp, bgTypeId, bracketEntry, arenatype, isRated != 0, false, arenaRating, matchmakerRating, ateamId); avgTime = bgQueue.GetAverageQueueWaitTime(ginfo, bracketEntry->GetBracketId()); } for (GroupReference* itr = grp->GetFirstMember(); itr != nullptr; itr = itr->next()) { Player* member = itr->GetSource(); if (!member) continue; WorldPacket data; if (err <= 0) { sBattlegroundMgr->BuildGroupJoinedBattlegroundPacket(&data, err); member->SendDirectMessage(&data); continue; } // add to queue uint32 queueSlot = member->AddBattlegroundQueueId(bgQueueTypeId); // send status packet (in queue) sBattlegroundMgr->BuildBattlegroundStatusPacket(&data, bg, queueSlot, STATUS_WAIT_QUEUE, avgTime, 0, arenatype, 0); member->SendDirectMessage(&data); sBattlegroundMgr->BuildGroupJoinedBattlegroundPacket(&data, err); member->SendDirectMessage(&data); TC_LOG_DEBUG("bg.battleground", "Battleground: player joined queue for arena as group bg queue type %u bg type %u: GUID %u, NAME %s", bgQueueTypeId, bgTypeId, member->GetGUID().GetCounter(), member->GetName().c_str()); } } else { GroupQueueInfo* ginfo = bgQueue.AddGroup(_player, nullptr, bgTypeId, bracketEntry, arenatype, isRated != 0, false, arenaRating, matchmakerRating, ateamId); uint32 avgTime = bgQueue.GetAverageQueueWaitTime(ginfo, bracketEntry->GetBracketId()); uint32 queueSlot = _player->AddBattlegroundQueueId(bgQueueTypeId); WorldPacket data; // send status packet (in queue) sBattlegroundMgr->BuildBattlegroundStatusPacket(&data, bg, queueSlot, STATUS_WAIT_QUEUE, avgTime, 0, arenatype, 0); SendPacket(&data); TC_LOG_DEBUG("bg.battleground", "Battleground: player joined queue for arena, skirmish, bg queue type %u bg type %u: GUID %u, NAME %s", bgQueueTypeId, bgTypeId, _player->GetGUID().GetCounter(), _player->GetName().c_str()); } sBattlegroundMgr->ScheduleQueueUpdate(matchmakerRating, arenatype, bgQueueTypeId, bgTypeId, bracketEntry->GetBracketId()); }