/* * This file is part of the TrinityCore Project. See AUTHORS file for Copyright information * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 2 of the License, or (at your * option) any later version. * * This program is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for * more details. * * You should have received a copy of the GNU General Public License along * with this program. If not, see . */ #ifndef CreatureTextMgrImpl_h__ #define CreatureTextMgrImpl_h__ #include "CreatureTextMgr.h" #include "CellImpl.h" #include "Group.h" #include "GridNotifiers.h" #include "World.h" #include "WorldSession.h" template class CreatureTextLocalizer { public: CreatureTextLocalizer(Builder const& builder, ChatMsg msgType) : _builder(builder), _msgType(msgType) { _packetCache.resize(TOTAL_LOCALES, nullptr); } ~CreatureTextLocalizer() { for (size_t i = 0; i < _packetCache.size(); ++i) { if (_packetCache[i]) delete _packetCache[i]->first; delete _packetCache[i]; } } void operator()(Player const* player) const { LocaleConstant loc_idx = player->GetSession()->GetSessionDbLocaleIndex(); WorldPacket* messageTemplate; size_t whisperGUIDpos; // create if not cached yet if (!_packetCache[loc_idx]) { messageTemplate = new WorldPacket(); whisperGUIDpos = _builder(messageTemplate, loc_idx); _packetCache[loc_idx] = new std::pair(messageTemplate, whisperGUIDpos); } else { messageTemplate = _packetCache[loc_idx]->first; whisperGUIDpos = _packetCache[loc_idx]->second; } WorldPacket data(*messageTemplate); switch (_msgType) { case CHAT_MSG_MONSTER_WHISPER: case CHAT_MSG_RAID_BOSS_WHISPER: data.put(whisperGUIDpos, player->GetGUID().GetRawValue()); break; default: break; } player->SendDirectMessage(&data); } private: mutable std::vector*> _packetCache; Builder const& _builder; ChatMsg _msgType; }; template void CreatureTextMgr::SendChatPacket(WorldObject* source, Builder const& builder, ChatMsg msgType, WorldObject const* whisperTarget /*= nullptr*/, CreatureTextRange range /*= TEXT_RANGE_NORMAL*/, Team team /*= TEAM_OTHER*/, bool gmOnly /*= false*/) const { if (!source) return; CreatureTextLocalizer localizer(builder, msgType); switch (msgType) { case CHAT_MSG_MONSTER_PARTY: { if (!whisperTarget) return; if (Player const* whisperPlayer = whisperTarget->ToPlayer()) if (Group const* group = whisperPlayer->GetGroup()) group->BroadcastWorker(localizer); return; } case CHAT_MSG_MONSTER_WHISPER: case CHAT_MSG_RAID_BOSS_WHISPER: { if (range == TEXT_RANGE_NORMAL) // ignores team and gmOnly { if (!whisperTarget || whisperTarget->GetTypeId() != TYPEID_PLAYER) return; localizer(const_cast(whisperTarget->ToPlayer())); return; } break; } default: break; } switch (range) { case TEXT_RANGE_AREA: { uint32 areaId = source->GetAreaId(); Map::PlayerList const& players = source->GetMap()->GetPlayers(); for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr) if (itr->GetSource()->GetAreaId() == areaId && (!team || Team(itr->GetSource()->GetTeam()) == team) && (!gmOnly || itr->GetSource()->IsGameMaster())) localizer(itr->GetSource()); return; } case TEXT_RANGE_ZONE: { uint32 zoneId = source->GetZoneId(); Map::PlayerList const& players = source->GetMap()->GetPlayers(); for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr) if (itr->GetSource()->GetZoneId() == zoneId && (!team || Team(itr->GetSource()->GetTeam()) == team) && (!gmOnly || itr->GetSource()->IsGameMaster())) localizer(itr->GetSource()); return; } case TEXT_RANGE_MAP: { Map::PlayerList const& players = source->GetMap()->GetPlayers(); for (Map::PlayerList::const_iterator itr = players.begin(); itr != players.end(); ++itr) if ((!team || Team(itr->GetSource()->GetTeam()) == team) && (!gmOnly || itr->GetSource()->IsGameMaster())) localizer(itr->GetSource()); return; } case TEXT_RANGE_WORLD: { SessionMap const& smap = sWorld->GetAllSessions(); for (SessionMap::const_iterator iter = smap.begin(); iter != smap.end(); ++iter) if (Player* player = iter->second->GetPlayer()) if ((!team || Team(player->GetTeam()) == team) && (!gmOnly || player->IsGameMaster())) localizer(player); return; } case TEXT_RANGE_NORMAL: default: break; } float dist = GetRangeForChatType(msgType); Trinity::PlayerDistWorker> worker(source, dist, localizer); Cell::VisitWorldObjects(source, worker, dist); } #endif // CreatureTextMgrImpl_h__