Rewrite much of the GM ticket system
* Extract storage and manipulation of tickets to TicketMgr (from ObjectMgr) * Extract ticket commands to TicketCommands.cpp * Adds support for sending GM responses and GM surveys. * Fix structure of several ticket-related packets. * Add support for understanding lag reports. * Thanks Zor for some of the packet structures, and Cyrax for some sniffs * Please report any issues encountered via the tracker. --HG-- branch : trunk
This commit is contained in:
@@ -907,7 +907,7 @@ bool AuthSocket::_HandleXferResume()
|
||||
uint64 start;
|
||||
socket().recv_skip(1);
|
||||
socket().recv((char*)&start,sizeof(start));
|
||||
fseek(pPatch, start, 0);
|
||||
fseek(pPatch, long(start), 0);
|
||||
|
||||
ACE_Based::Thread u(new PatcherRunnable(this));
|
||||
return true;
|
||||
|
||||
@@ -45,6 +45,7 @@ file(GLOB_RECURSE sources_Server Server/*.cpp Server/*.h)
|
||||
file(GLOB_RECURSE sources_Skills Skills/*.cpp Skills/*.h)
|
||||
file(GLOB_RECURSE sources_Spells Spells/*.cpp Spells/*.h)
|
||||
file(GLOB_RECURSE sources_Tools Tools/*.cpp Tools/*.h)
|
||||
file(GLOB_RECURSE sources_Tickets Tickets/*.cpp Tickets/*.h)
|
||||
file(GLOB_RECURSE sources_Weather Weather/*.cpp Weather/*.h)
|
||||
file(GLOB_RECURSE sources_World World/*.cpp World/*.h)
|
||||
|
||||
@@ -92,6 +93,7 @@ set(game_STAT_SRCS
|
||||
${sources_Skills}
|
||||
${sources_Spells}
|
||||
${sources_Tools}
|
||||
${sources_Tickets}
|
||||
${sources_Weather}
|
||||
${sources_World}
|
||||
)
|
||||
@@ -181,6 +183,7 @@ include_directories(
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/Spells
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/Spells/Auras
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/Tools
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/Tickets
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/Weather
|
||||
${CMAKE_CURRENT_SOURCE_DIR}/World
|
||||
${CMAKE_SOURCE_DIR}/src/server/scripts/PrecompiledHeaders
|
||||
|
||||
@@ -659,6 +659,13 @@ ChatCommand * ChatHandler::getCommandTable()
|
||||
{ NULL, 0, false, NULL, "", NULL }
|
||||
};
|
||||
|
||||
static ChatCommand ticketResponseCommandTable[] =
|
||||
{
|
||||
{ "append", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketResponseAppendCommand, "", NULL },
|
||||
{ "appendln", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketResponseAppendLnCommand, "", NULL },
|
||||
{ NULL, 0, false, NULL, "", NULL }
|
||||
};
|
||||
|
||||
static ChatCommand ticketCommandTable[] =
|
||||
{
|
||||
{ "list", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketListCommand, "", NULL },
|
||||
@@ -667,10 +674,15 @@ ChatCommand * ChatHandler::getCommandTable()
|
||||
{ "viewid", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketGetByIdCommand, "", NULL },
|
||||
{ "close", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketCloseByIdCommand, "", NULL },
|
||||
{ "closedlist", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketListClosedCommand, "", NULL },
|
||||
{ "escalatedlist", SEC_GAMEMASTER, false, &ChatHandler::HandleGMTicketListEscalatedCommand, "", NULL },
|
||||
{ "delete", SEC_ADMINISTRATOR, false, &ChatHandler::HandleGMTicketDeleteByIdCommand, "", NULL },
|
||||
{ "assign", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketAssignToCommand, "", NULL },
|
||||
{ "unassign", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketUnAssignCommand, "", NULL },
|
||||
{ "assign", SEC_GAMEMASTER, false, &ChatHandler::HandleGMTicketAssignToCommand, "", NULL },
|
||||
{ "unassign", SEC_GAMEMASTER, false, &ChatHandler::HandleGMTicketUnAssignCommand, "", NULL },
|
||||
{ "comment", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketCommentCommand, "", NULL },
|
||||
{ "togglesystem", SEC_ADMINISTRATOR, false, &ChatHandler::HandleToggleGMTicketSystem, "", NULL },
|
||||
{ "escalate", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketEscalateCommand, "", NULL },
|
||||
{ "response", SEC_MODERATOR, false, NULL, "", ticketResponseCommandTable },
|
||||
{ "complete", SEC_MODERATOR, false, &ChatHandler::HandleGMTicketCompleteCommand, "", NULL },
|
||||
{ NULL, 0, false, NULL, "", NULL }
|
||||
};
|
||||
|
||||
|
||||
@@ -566,6 +566,7 @@ class ChatHandler
|
||||
bool HandleGMTicketListCommand(const char* args);
|
||||
bool HandleGMTicketListOnlineCommand(const char* args);
|
||||
bool HandleGMTicketListClosedCommand(const char* args);
|
||||
bool HandleGMTicketListEscalatedCommand(const char* args);
|
||||
bool HandleGMTicketGetByIdCommand(const char* args);
|
||||
bool HandleGMTicketGetByNameCommand(const char* args);
|
||||
bool HandleGMTicketCloseByIdCommand(const char* args);
|
||||
@@ -574,6 +575,11 @@ class ChatHandler
|
||||
bool HandleGMTicketCommentCommand(const char* args);
|
||||
bool HandleGMTicketDeleteByIdCommand(const char* args);
|
||||
bool HandleGMTicketReloadCommand(const char*);
|
||||
bool HandleToggleGMTicketSystem(const char* args);
|
||||
bool HandleGMTicketEscalateCommand(const char* args);
|
||||
bool HandleGMTicketCompleteCommand(const char* args);
|
||||
bool HandleGMTicketResponseAppendCommand(const char* args);
|
||||
bool HandleGMTicketResponseAppendLnCommand(const char* args);
|
||||
|
||||
bool HandleMaxSkillCommand(const char* args);
|
||||
bool HandleSetSkillCommand(const char* args);
|
||||
|
||||
@@ -24,6 +24,7 @@
|
||||
#include "WorldSession.h"
|
||||
#include "World.h"
|
||||
#include "ObjectMgr.h"
|
||||
#include "TicketMgr.h"
|
||||
#include "Player.h"
|
||||
#include "AccountMgr.h"
|
||||
#include "Opcodes.h"
|
||||
@@ -288,377 +289,6 @@ bool ChatHandler::HandleGMChatCommand(const char* args)
|
||||
return false;
|
||||
}
|
||||
|
||||
std::string ChatHandler::PGetParseString(int32 entry, ...)
|
||||
{
|
||||
const char *format = GetTrinityString(entry);
|
||||
va_list ap;
|
||||
char str [1024];
|
||||
va_start(ap, entry);
|
||||
vsnprintf(str,1024,format, ap);
|
||||
va_end(ap);
|
||||
return (std::string)str;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketListCommand(const char* /*args*/)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETSHOWLIST);
|
||||
for (GmTicketList::iterator itr = sObjectMgr.m_GMTicketList.begin(); itr != sObjectMgr.m_GMTicketList.end(); ++itr)
|
||||
{
|
||||
if ((*itr)->closed != 0)
|
||||
continue;
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, (*itr)->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, (*itr)->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - (*itr)->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - (*itr)->timestamp, true, false)).c_str());
|
||||
if (sObjectMgr.GetPlayerNameByGUID((*itr)->assignedToGM, gmname))
|
||||
{
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
}
|
||||
SendSysMessage(ss.str().c_str());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketListOnlineCommand(const char* /*args*/)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETSHOWONLINELIST);
|
||||
for (GmTicketList::iterator itr = sObjectMgr.m_GMTicketList.begin(); itr != sObjectMgr.m_GMTicketList.end(); ++itr)
|
||||
{
|
||||
if ((*itr)->closed != 0 || !sObjectMgr.GetPlayer((*itr)->playerGuid))
|
||||
continue;
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, (*itr)->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, (*itr)->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - (*itr)->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - (*itr)->timestamp, true, false)).c_str());
|
||||
if (sObjectMgr.GetPlayerNameByGUID((*itr)->assignedToGM, gmname))
|
||||
{
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
}
|
||||
SendSysMessage(ss.str().c_str());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketListClosedCommand(const char* /*args*/)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETSHOWCLOSEDLIST);
|
||||
for (GmTicketList::iterator itr = sObjectMgr.m_GMTicketList.begin(); itr != sObjectMgr.m_GMTicketList.end(); ++itr)
|
||||
{
|
||||
if ((*itr)->closed == 0)
|
||||
continue;
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, (*itr)->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, (*itr)->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - (*itr)->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - (*itr)->timestamp, true, false)).c_str());
|
||||
if (sObjectMgr.GetPlayerNameByGUID((*itr)->assignedToGM, gmname))
|
||||
{
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
}
|
||||
SendSysMessage(ss.str().c_str());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketGetByIdCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
uint64 tguid = atoi(args);
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicket(tguid);
|
||||
if (!ticket || ticket->closed != 0)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - ticket->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - ticket->timestamp, true, false)).c_str());
|
||||
if (sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname))
|
||||
{
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
}
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTMESSAGE, ticket->message.c_str());
|
||||
if (ticket->comment != "")
|
||||
{
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTCOMMENT, ticket->comment.c_str());
|
||||
}
|
||||
SendSysMessage(ss.str().c_str());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketGetByNameCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
std::string name = (char*)args;
|
||||
normalizePlayerName(name);
|
||||
|
||||
Player *plr = sObjectMgr.GetPlayer(name.c_str());
|
||||
if (!plr)
|
||||
{
|
||||
SendSysMessage(LANG_NO_PLAYERS_FOUND);
|
||||
return true;
|
||||
}
|
||||
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicketByPlayer(plr->GetGUID());
|
||||
if (!ticket)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - ticket->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - ticket->timestamp, true, false)).c_str());
|
||||
if (sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname))
|
||||
{
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
}
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTMESSAGE, ticket->message.c_str());
|
||||
if (ticket->comment != "")
|
||||
{
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTCOMMENT, ticket->comment.c_str());
|
||||
}
|
||||
SendSysMessage(ss.str().c_str());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketCloseByIdCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
uint64 tguid = atoi(args);
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicket(tguid);
|
||||
if (!ticket || ticket->closed != 0)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
if (ticket && ticket->assignedToGM != 0 && ticket->assignedToGM != m_session->GetPlayer()->GetGUID())
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETCANNOTCLOSE, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETCLOSED, m_session->GetPlayer()->GetName());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
Player *plr = sObjectMgr.GetPlayer(ticket->playerGuid);
|
||||
sObjectMgr.RemoveGMTicket(ticket, m_session->GetPlayer()->GetGUID());
|
||||
|
||||
if (!plr || !plr->IsInWorld())
|
||||
return true;
|
||||
|
||||
// send abandon ticket
|
||||
WorldPacket data(SMSG_GMTICKET_DELETETICKET, 4);
|
||||
data << uint32(9);
|
||||
plr->GetSession()->SendPacket(&data);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketAssignToCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
char* tguid = strtok((char*)args, " ");
|
||||
uint64 ticketGuid = atoi(tguid);
|
||||
char* targetgm = strtok(NULL, " ");
|
||||
|
||||
if (!targetgm)
|
||||
return false;
|
||||
|
||||
std::string targm = targetgm;
|
||||
if (!normalizePlayerName(targm))
|
||||
return false;
|
||||
|
||||
Player *cplr = m_session->GetPlayer();
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicket(ticketGuid);
|
||||
|
||||
if (!ticket || ticket->closed != 0)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
uint64 tarGUID = sObjectMgr.GetPlayerGUIDByName(targm.c_str());
|
||||
uint64 accid = sObjectMgr.GetPlayerAccountIdByGUID(tarGUID);
|
||||
uint32 gmlevel = sAccountMgr.GetSecurity(accid, realmID);
|
||||
|
||||
if (!tarGUID || gmlevel == SEC_PLAYER)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETASSIGNERROR_A);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (ticket->assignedToGM == tarGUID)
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETASSIGNERROR_B, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string gmname;
|
||||
sObjectMgr.GetPlayerNameByGUID(tarGUID, gmname);
|
||||
if (ticket->assignedToGM != 0 && ticket->assignedToGM != cplr->GetGUID())
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETALREADYASSIGNED, ticket->guid, gmname.c_str());
|
||||
return true;
|
||||
}
|
||||
|
||||
ticket->assignedToGM = tarGUID;
|
||||
sObjectMgr.AddOrUpdateGMTicket(*ticket);
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketUnAssignCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
uint64 ticketGuid = atoi(args);
|
||||
Player *cplr = m_session->GetPlayer();
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicket(ticketGuid);
|
||||
|
||||
if (!ticket|| ticket->closed != 0)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
if (ticket->assignedToGM == 0)
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETNOTASSIGNED, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string gmname;
|
||||
sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname);
|
||||
Player *plr = sObjectMgr.GetPlayer(ticket->assignedToGM);
|
||||
if (plr && plr->IsInWorld() && plr->GetSession()->GetSecurity() > cplr->GetSession()->GetSecurity())
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETUNASSIGNSECURITY);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTUNASSIGNED, cplr->GetName());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
ticket->assignedToGM = 0;
|
||||
sObjectMgr.AddOrUpdateGMTicket(*ticket);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketCommentCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
char* tguid = strtok((char*)args, " ");
|
||||
uint64 ticketGuid = atoi(tguid);
|
||||
char* comment = strtok(NULL, "\n");
|
||||
|
||||
if (!comment)
|
||||
return false;
|
||||
|
||||
Player *cplr = m_session->GetPlayer();
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicket(ticketGuid);
|
||||
|
||||
if (!ticket || ticket->closed != 0)
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
if (ticket->assignedToGM != 0 && ticket->assignedToGM != cplr->GetGUID())
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETALREADYASSIGNED, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string gmname;
|
||||
sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname);
|
||||
ticket->comment = comment;
|
||||
sObjectMgr.AddOrUpdateGMTicket(*ticket);
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
if (sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname))
|
||||
{
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
}
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTADDCOMMENT, cplr->GetName(), ticket->comment.c_str());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketDeleteByIdCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
uint64 ticketGuid = atoi(args);
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicket(ticketGuid);
|
||||
|
||||
if (!ticket)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
if (ticket->closed == 0)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETCLOSEFIRST);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETDELETED, m_session->GetPlayer()->GetName());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
Player *plr = sObjectMgr.GetPlayer(ticket->playerGuid);
|
||||
sObjectMgr.RemoveGMTicket(ticket, -1, true);
|
||||
if (plr && plr->IsInWorld())
|
||||
{
|
||||
// Force abandon ticket
|
||||
WorldPacket data(SMSG_GMTICKET_DELETETICKET, 4);
|
||||
data << uint32(9);
|
||||
plr->GetSession()->SendPacket(&data);
|
||||
}
|
||||
|
||||
ticket = NULL;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketReloadCommand(const char*)
|
||||
{
|
||||
sObjectMgr.LoadGMTickets();
|
||||
return true;
|
||||
}
|
||||
|
||||
//Enable\Dissable Invisible mode
|
||||
bool ChatHandler::HandleGMVisibleCommand(const char* args)
|
||||
{
|
||||
|
||||
@@ -138,48 +138,6 @@ bool ChatHandler::HandleUnmuteCommand(const char* args)
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGoTicketCommand(const char * args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
char *cstrticket_id = strtok((char*)args, " ");
|
||||
|
||||
if (!cstrticket_id)
|
||||
return false;
|
||||
|
||||
uint64 ticket_id = atoi(cstrticket_id);
|
||||
if (!ticket_id)
|
||||
return false;
|
||||
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicket(ticket_id);
|
||||
if (!ticket)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
float x, y, z;
|
||||
int mapid;
|
||||
|
||||
x = ticket->pos_x;
|
||||
y = ticket->pos_y;
|
||||
z = ticket->pos_z;
|
||||
mapid = ticket->map;
|
||||
|
||||
Player* _player = m_session->GetPlayer();
|
||||
if (_player->isInFlight())
|
||||
{
|
||||
_player->GetMotionMaster()->MovementExpired();
|
||||
_player->CleanupAfterTaxiFlight();
|
||||
}
|
||||
else
|
||||
_player->SaveRecallPosition();
|
||||
|
||||
_player->TeleportTo(mapid, x, y, z, 1, 0);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGoTriggerCommand(const char* args)
|
||||
{
|
||||
Player* _player = m_session->GetPlayer();
|
||||
|
||||
@@ -0,0 +1,596 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "Common.h"
|
||||
#include "DatabaseEnv.h"
|
||||
#include "WorldPacket.h"
|
||||
#include "WorldSession.h"
|
||||
#include "ObjectMgr.h"
|
||||
#include "TicketMgr.h"
|
||||
#include "AccountMgr.h"
|
||||
#include "Chat.h"
|
||||
#include "Player.h"
|
||||
|
||||
std::string ChatHandler::PGetParseString(int32 entry, ...)
|
||||
{
|
||||
const char *format = GetTrinityString(entry);
|
||||
va_list ap;
|
||||
char str [1024];
|
||||
va_start(ap, entry);
|
||||
vsnprintf(str,1024,format, ap);
|
||||
va_end(ap);
|
||||
return (std::string)str;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketListCommand(const char* /*args*/)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETSHOWLIST);
|
||||
for (GmTicketList::iterator itr = sTicketMgr.m_GMTicketList.begin(); itr != sTicketMgr.m_GMTicketList.end(); ++itr)
|
||||
{
|
||||
if ((*itr)->closed != 0 || (*itr)->completed)
|
||||
continue;
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, (*itr)->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, (*itr)->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - (*itr)->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - (*itr)->timestamp, true, false)).c_str());
|
||||
|
||||
if (sObjectMgr.GetPlayerNameByGUID((*itr)->assignedToGM, gmname))
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
|
||||
SendSysMessage(ss.str().c_str());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketListOnlineCommand(const char* /*args*/)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETSHOWONLINELIST);
|
||||
for (GmTicketList::iterator itr = sTicketMgr.m_GMTicketList.begin(); itr != sTicketMgr.m_GMTicketList.end(); ++itr)
|
||||
{
|
||||
if ((*itr)->closed != 0 || (*itr)->completed || !sObjectMgr.GetPlayer((*itr)->playerGuid))
|
||||
continue;
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, (*itr)->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, (*itr)->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - (*itr)->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - (*itr)->timestamp, true, false)).c_str());
|
||||
if (sObjectMgr.GetPlayerNameByGUID((*itr)->assignedToGM, gmname))
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
SendSysMessage(ss.str().c_str());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketListClosedCommand(const char* /*args*/)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETSHOWCLOSEDLIST);
|
||||
for (GmTicketList::iterator itr = sTicketMgr.m_GMTicketList.begin(); itr != sTicketMgr.m_GMTicketList.end(); ++itr)
|
||||
{
|
||||
if ((*itr)->closed == 0)
|
||||
continue;
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, (*itr)->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, (*itr)->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - (*itr)->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - (*itr)->timestamp, true, false)).c_str());
|
||||
if (sObjectMgr.GetPlayerNameByGUID((*itr)->assignedToGM, gmname))
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
|
||||
SendSysMessage(ss.str().c_str());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketListEscalatedCommand(const char* args)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETSHOWESCALATEDLIST);
|
||||
for (GmTicketList::iterator itr = sTicketMgr.m_GMTicketList.begin(); itr != sTicketMgr.m_GMTicketList.end(); ++itr)
|
||||
{
|
||||
if (!((*itr)->escalated == TICKET_IN_ESCALATION_QUEUE) || (*itr)->closed != 0)
|
||||
continue;
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, (*itr)->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, (*itr)->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - (*itr)->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - (*itr)->timestamp, true, false)).c_str());
|
||||
SendSysMessage(ss.str().c_str());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketGetByIdCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
uint64 tguid = atoi(args);
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(tguid);
|
||||
if (!ticket || ticket->closed != 0 || ticket->completed)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
ticket->viewed = true;
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - ticket->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - ticket->timestamp, true, false)).c_str());
|
||||
|
||||
if (sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname))
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTMESSAGE, ticket->message.c_str());
|
||||
|
||||
if (strlen(ticket->comment.c_str()) != 0)
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTCOMMENT, ticket->comment.c_str());
|
||||
|
||||
SendSysMessage(ss.str().c_str());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketGetByNameCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
std::string name = (char*)args;
|
||||
normalizePlayerName(name);
|
||||
|
||||
Player *plr = sObjectMgr.GetPlayer(name.c_str());
|
||||
if (!plr)
|
||||
{
|
||||
SendSysMessage(LANG_NO_PLAYERS_FOUND);
|
||||
return true;
|
||||
}
|
||||
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicketByPlayer(plr->GetGUID());
|
||||
if (!ticket)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
ticket->viewed = true;
|
||||
|
||||
std::string gmname;
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGECREATE, (secsToTimeString(time(NULL) - ticket->createtime, true, false)).c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTAGE, (secsToTimeString(time(NULL) - ticket->timestamp, true, false)).c_str());
|
||||
|
||||
if (sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname))
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTMESSAGE, ticket->message.c_str());
|
||||
|
||||
if (strlen(ticket->comment.c_str()) != 0)
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTCOMMENT, ticket->comment.c_str());
|
||||
|
||||
SendSysMessage(ss.str().c_str());
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketCloseByIdCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
uint64 tguid = atoi(args);
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(tguid);
|
||||
if (!ticket || ticket->closed != 0 || ticket->completed)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (ticket && ticket->assignedToGM != 0 && ticket->assignedToGM != m_session->GetPlayer()->GetGUID())
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETCANNOTCLOSE, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETCLOSED, m_session->GetPlayer()->GetName());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
Player *plr = sObjectMgr.GetPlayer(ticket->playerGuid);
|
||||
sTicketMgr.RemoveGMTicket(ticket, m_session->GetPlayer()->GetGUID());
|
||||
|
||||
if (!plr || !plr->IsInWorld())
|
||||
return true;
|
||||
|
||||
// send abandon ticket
|
||||
WorldPacket deleteTicket(SMSG_GMTICKET_DELETETICKET, 4);
|
||||
deleteTicket << uint32(GMTICKET_RESPONSE_TICKET_DELETED);
|
||||
plr->GetSession()->SendPacket(&deleteTicket);
|
||||
|
||||
sTicketMgr.UpdateLastChange();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketAssignToCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
char* tguid = strtok((char*)args, " ");
|
||||
uint64 ticketGuid = atoi(tguid);
|
||||
char* targetgm = strtok(NULL, " ");
|
||||
|
||||
if (!targetgm)
|
||||
return false;
|
||||
|
||||
std::string targm = targetgm;
|
||||
if (!normalizePlayerName(targm))
|
||||
return false;
|
||||
|
||||
Player *cplr = m_session->GetPlayer();
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(ticketGuid);
|
||||
|
||||
if (!ticket || ticket->closed != 0)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
uint64 tarGUID = sObjectMgr.GetPlayerGUIDByName(targm.c_str());
|
||||
uint64 accid = sObjectMgr.GetPlayerAccountIdByGUID(tarGUID);
|
||||
uint32 gmlevel = sAccountMgr.GetSecurity(accid, realmID);
|
||||
|
||||
if (!tarGUID || gmlevel == SEC_PLAYER)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETASSIGNERROR_A);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (ticket->assignedToGM == tarGUID)
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETASSIGNERROR_B, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string gmname;
|
||||
sObjectMgr.GetPlayerNameByGUID(tarGUID, gmname);
|
||||
if (ticket->assignedToGM != 0 && ticket->assignedToGM != cplr->GetGUID())
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETALREADYASSIGNED, ticket->guid, gmname.c_str());
|
||||
return true;
|
||||
}
|
||||
|
||||
ticket->assignedToGM = tarGUID;
|
||||
|
||||
if (gmlevel == SEC_ADMINISTRATOR && ticket->escalated == TICKET_IN_ESCALATION_QUEUE)
|
||||
ticket->escalated = TICKET_ESCALATED_ASSIGNED;
|
||||
else if (ticket->escalated == TICKET_UNASSIGNED)
|
||||
ticket->escalated = TICKET_ASSIGNED;
|
||||
|
||||
sTicketMgr.AddOrUpdateGMTicket(*ticket);
|
||||
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
|
||||
sTicketMgr.UpdateLastChange();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketUnAssignCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
uint64 ticketGuid = atoi(args);
|
||||
Player *cplr = m_session->GetPlayer();
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(ticketGuid);
|
||||
|
||||
if (!ticket|| ticket->closed != 0)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
if (ticket->assignedToGM == 0)
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETNOTASSIGNED, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string gmname;
|
||||
sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname);
|
||||
Player *plr = sObjectMgr.GetPlayer(ticket->assignedToGM);
|
||||
if (plr && plr->IsInWorld() && plr->GetSession()->GetSecurity() > cplr->GetSession()->GetSecurity())
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETUNASSIGNSECURITY);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTUNASSIGNED, cplr->GetName());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
ticket->assignedToGM = 0;
|
||||
if (ticket->escalated != TICKET_UNASSIGNED && ticket->escalated != TICKET_IN_ESCALATION_QUEUE)
|
||||
ticket->escalated--;
|
||||
sTicketMgr.AddOrUpdateGMTicket(*ticket);
|
||||
sTicketMgr.UpdateLastChange();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketCommentCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
char* tguid = strtok((char*)args, " ");
|
||||
uint64 ticketGuid = atoi(tguid);
|
||||
char* comment = strtok(NULL, "\n");
|
||||
|
||||
if (!comment)
|
||||
return false;
|
||||
|
||||
Player *cplr = m_session->GetPlayer();
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(ticketGuid);
|
||||
|
||||
if (!ticket || ticket->closed != 0)
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
if (ticket->assignedToGM != 0 && ticket->assignedToGM != cplr->GetGUID())
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETALREADYASSIGNED, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::string gmname;
|
||||
sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname);
|
||||
ticket->comment = comment;
|
||||
sTicketMgr.AddOrUpdateGMTicket(*ticket);
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
|
||||
if (sObjectMgr.GetPlayerNameByGUID(ticket->assignedToGM, gmname))
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTASSIGNEDTO, gmname.c_str());
|
||||
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTADDCOMMENT, cplr->GetName(), ticket->comment.c_str());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
sTicketMgr.UpdateLastChange();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketDeleteByIdCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
uint64 ticketGuid = atoi(args);
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(ticketGuid);
|
||||
|
||||
if (!ticket)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
if (ticket->closed == 0)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETCLOSEFIRST);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::stringstream ss;
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTGUID, ticket->guid);
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETLISTNAME, ticket->name.c_str());
|
||||
ss << PGetParseString(LANG_COMMAND_TICKETDELETED, m_session->GetPlayer()->GetName());
|
||||
SendGlobalGMSysMessage(ss.str().c_str());
|
||||
Player *plr = sObjectMgr.GetPlayer(ticket->playerGuid);
|
||||
sTicketMgr.RemoveGMTicket(ticket, -1, true); // we don't need to care about who deleted it...
|
||||
if (plr && plr->IsInWorld())
|
||||
{
|
||||
// Force abandon ticket
|
||||
WorldPacket data(SMSG_GMTICKET_DELETETICKET, 4);
|
||||
data << uint32(GMTICKET_RESPONSE_TICKET_DELETED);
|
||||
plr->GetSession()->SendPacket(&data);
|
||||
}
|
||||
|
||||
ticket = NULL;
|
||||
sTicketMgr.UpdateLastChange();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketReloadCommand(const char* /* args */)
|
||||
{
|
||||
sTicketMgr.LoadGMTickets();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleToggleGMTicketSystem(const char* /* args */)
|
||||
{
|
||||
sTicketMgr.SetStatus(!sTicketMgr.GetStatus());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGoTicketCommand(const char * args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
char *cstrticket_id = strtok((char*)args, " ");
|
||||
|
||||
if (!cstrticket_id)
|
||||
return false;
|
||||
|
||||
uint64 ticket_id = atoi(cstrticket_id);
|
||||
if (!ticket_id)
|
||||
return false;
|
||||
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(ticket_id);
|
||||
if (!ticket)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
float x, y, z;
|
||||
int mapid;
|
||||
|
||||
x = ticket->pos_x;
|
||||
y = ticket->pos_y;
|
||||
z = ticket->pos_z;
|
||||
mapid = ticket->map;
|
||||
|
||||
Player* _player = m_session->GetPlayer();
|
||||
if (_player->isInFlight())
|
||||
{
|
||||
_player->GetMotionMaster()->MovementExpired();
|
||||
_player->CleanupAfterTaxiFlight();
|
||||
}
|
||||
else
|
||||
_player->SaveRecallPosition();
|
||||
|
||||
_player->TeleportTo(mapid, x, y, z, 1, 0);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketEscalateCommand(const char *args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
uint64 tguid = atoi(args);
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(tguid);
|
||||
if (!ticket || ticket->closed != 0 || ticket->completed || ticket->escalated != TICKET_UNASSIGNED)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
ticket->escalated = TICKET_IN_ESCALATION_QUEUE;
|
||||
|
||||
Player *plr = sObjectMgr.GetPlayer(ticket->playerGuid);
|
||||
if (plr && plr->IsInWorld())
|
||||
plr->GetSession()->SendGMTicketGetTicket(GMTICKET_STATUS_HASTEXT, ticket->message.c_str(), ticket);
|
||||
sTicketMgr.UpdateLastChange();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketCompleteCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
uint64 tguid = atoi(args);
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(tguid);
|
||||
if (!ticket || ticket->closed != 0 || ticket->completed)
|
||||
{
|
||||
SendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
Player *plr = sObjectMgr.GetPlayer(ticket->playerGuid);
|
||||
if (plr && plr->IsInWorld())
|
||||
plr->GetSession()->SendGMTicketResponse(ticket);
|
||||
sTicketMgr.UpdateLastChange();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketResponseAppendCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
char* tguid = strtok((char*)args, " ");
|
||||
uint64 ticketGuid = atoi(tguid);
|
||||
char* response = strtok(NULL, "\n");
|
||||
|
||||
if (!response)
|
||||
return false;
|
||||
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(ticketGuid);
|
||||
Player *cplr = m_session->GetPlayer();
|
||||
|
||||
if (!ticket || ticket->closed != 0)
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (ticket->assignedToGM != 0 && ticket->assignedToGM != cplr->GetGUID())
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETALREADYASSIGNED, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::stringstream ss;
|
||||
ss << ticket->response;
|
||||
ss << response;
|
||||
ticket->response = ss.str();
|
||||
sTicketMgr.AddOrUpdateGMTicket(*ticket);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool ChatHandler::HandleGMTicketResponseAppendLnCommand(const char* args)
|
||||
{
|
||||
if (!*args)
|
||||
return false;
|
||||
|
||||
char* tguid = strtok((char*)args, " ");
|
||||
uint64 ticketGuid = atoi(tguid);
|
||||
char* response = strtok(NULL, "\n");
|
||||
|
||||
if (!response)
|
||||
return false;
|
||||
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicket(ticketGuid);
|
||||
Player *cplr = m_session->GetPlayer();
|
||||
|
||||
if (!ticket || ticket->closed != 0)
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETNOTEXIST);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (ticket->assignedToGM != 0 && ticket->assignedToGM != cplr->GetGUID())
|
||||
{
|
||||
PSendSysMessage(LANG_COMMAND_TICKETALREADYASSIGNED, ticket->guid);
|
||||
return true;
|
||||
}
|
||||
|
||||
std::stringstream ss;
|
||||
ss << ticket->response;
|
||||
ss << response;
|
||||
ss << "\n";
|
||||
ticket->response = ss.str();
|
||||
sTicketMgr.AddOrUpdateGMTicket(*ticket);
|
||||
return true;
|
||||
}
|
||||
@@ -8816,129 +8816,6 @@ Quest const* GetQuestTemplateStore(uint32 entry)
|
||||
return sObjectMgr.GetQuestTemplate(entry);
|
||||
}
|
||||
|
||||
uint64 ObjectMgr::GenerateGMTicketId()
|
||||
{
|
||||
return ++m_GMticketid;
|
||||
}
|
||||
|
||||
void ObjectMgr::LoadGMTickets()
|
||||
{
|
||||
if (!m_GMTicketList.empty())
|
||||
{
|
||||
for (GmTicketList::const_iterator itr = m_GMTicketList.begin(); itr != m_GMTicketList.end(); ++itr)
|
||||
delete *itr;
|
||||
}
|
||||
m_GMTicketList.clear();
|
||||
m_GMticketid = 0;
|
||||
|
||||
QueryResult_AutoPtr result = CharacterDatabase.Query("SELECT guid, playerGuid, name, message, createtime, map, posX, posY, posZ, timestamp, closed, assignedto, comment FROM gm_tickets");
|
||||
|
||||
if (!result)
|
||||
{
|
||||
barGoLink bar(1);
|
||||
bar.step();
|
||||
sLog.outString();
|
||||
sLog.outString(">> GM Tickets table is empty, no tickets were loaded.");
|
||||
return;
|
||||
}
|
||||
|
||||
uint16 count = 0;
|
||||
barGoLink bar ((*result).GetRowCount());
|
||||
GM_Ticket *ticket;
|
||||
do
|
||||
{
|
||||
Field *fields = result->Fetch();
|
||||
ticket = new GM_Ticket;
|
||||
ticket->guid = fields[0].GetUInt64();
|
||||
ticket->playerGuid = fields[1].GetUInt64();
|
||||
ticket->name = fields[2].GetCppString();
|
||||
ticket->message = fields[3].GetCppString();
|
||||
ticket->createtime = fields[4].GetUInt64();
|
||||
ticket->map = fields[5].GetUInt32();
|
||||
ticket->pos_x = fields[6].GetFloat();
|
||||
ticket->pos_y = fields[7].GetFloat();
|
||||
ticket->pos_z = fields[8].GetFloat();
|
||||
ticket->timestamp = fields[9].GetUInt64();
|
||||
ticket->closed = fields[10].GetUInt64();
|
||||
ticket->assignedToGM = fields[11].GetUInt64();
|
||||
ticket->comment = fields[12].GetCppString();
|
||||
++count;
|
||||
bar.step();
|
||||
|
||||
m_GMTicketList.push_back(ticket);
|
||||
|
||||
} while (result->NextRow());
|
||||
|
||||
result = CharacterDatabase.Query("SELECT MAX(guid) from gm_tickets");
|
||||
|
||||
if (result)
|
||||
{
|
||||
Field *fields = result->Fetch();
|
||||
m_GMticketid = fields[0].GetUInt64();
|
||||
}
|
||||
|
||||
sLog.outString(">> Loaded %u GM Tickets from the database.", count);
|
||||
}
|
||||
|
||||
void ObjectMgr::AddOrUpdateGMTicket(GM_Ticket &ticket, bool create)
|
||||
{
|
||||
if (create)
|
||||
m_GMTicketList.push_back(&ticket);
|
||||
|
||||
_AddOrUpdateGMTicket(ticket);
|
||||
}
|
||||
|
||||
void ObjectMgr::_AddOrUpdateGMTicket(GM_Ticket &ticket)
|
||||
{
|
||||
std::string msg(ticket.message), name(ticket.name), comment(ticket.comment);
|
||||
CharacterDatabase.escape_string(msg);
|
||||
CharacterDatabase.escape_string(name);
|
||||
CharacterDatabase.escape_string(comment);
|
||||
std::ostringstream ss;
|
||||
ss << "REPLACE INTO gm_tickets (guid, playerGuid, name, message, createtime, map, posX, posY, posZ, timestamp, closed, assignedto, comment) VALUES('";
|
||||
ss << ticket.guid << "', '";
|
||||
ss << ticket.playerGuid << "', '";
|
||||
ss << name << "', '";
|
||||
ss << msg << "', '" ;
|
||||
ss << ticket.createtime << "', '";
|
||||
ss << ticket.map << "', '";
|
||||
ss << ticket.pos_x << "', '";
|
||||
ss << ticket.pos_y << "', '";
|
||||
ss << ticket.pos_z << "', '";
|
||||
ss << ticket.timestamp << "', '";
|
||||
ss << ticket.closed << "', '";
|
||||
ss << ticket.assignedToGM << "', '";
|
||||
ss << comment << "');";
|
||||
|
||||
SQLTransaction trans = CharacterDatabase.BeginTransaction();
|
||||
trans->Append(ss.str().c_str());
|
||||
CharacterDatabase.CommitTransaction(trans);
|
||||
}
|
||||
|
||||
void ObjectMgr::RemoveGMTicket(GM_Ticket *ticket, int64 source, bool permanently)
|
||||
{
|
||||
for (GmTicketList::iterator i = m_GMTicketList.begin(); i != m_GMTicketList.end(); ++i)
|
||||
if ((*i)->guid == ticket->guid)
|
||||
{
|
||||
if (permanently)
|
||||
{
|
||||
CharacterDatabase.PExecute("DELETE FROM gm_tickets WHERE guid = '%u'", ticket->guid);
|
||||
i = m_GMTicketList.erase(i);
|
||||
ticket = NULL;
|
||||
return;
|
||||
}
|
||||
(*i)->closed = source;
|
||||
_AddOrUpdateGMTicket(*(*i));
|
||||
}
|
||||
}
|
||||
|
||||
void ObjectMgr::RemoveGMTicket(uint64 ticketGuid, int64 source, bool permanently)
|
||||
{
|
||||
GM_Ticket *ticket = GetGMTicket(ticketGuid);
|
||||
ASSERT(ticket);
|
||||
RemoveGMTicket(ticket, source, permanently);
|
||||
}
|
||||
|
||||
CreatureBaseStats const* ObjectMgr::GetCreatureBaseStats(uint8 level, uint8 unitClass)
|
||||
{
|
||||
CreatureBaseStatsMap::const_iterator it = m_creatureBaseStatsMap.find(MAKE_PAIR16(level,unitClass));
|
||||
|
||||
@@ -337,23 +337,6 @@ enum SkillRangeType
|
||||
SKILL_RANGE_NONE, // 0..0 always
|
||||
};
|
||||
|
||||
struct GM_Ticket
|
||||
{
|
||||
uint64 guid;
|
||||
uint64 playerGuid;
|
||||
std::string name;
|
||||
float pos_x;
|
||||
float pos_y;
|
||||
float pos_z;
|
||||
uint32 map;
|
||||
std::string message;
|
||||
uint64 createtime;
|
||||
uint64 timestamp;
|
||||
int64 closed; // 0 = Open, -1 = Console, playerGuid = player abandoned ticket, other = GM who closed it.
|
||||
uint64 assignedToGM;
|
||||
std::string comment;
|
||||
};
|
||||
typedef std::list<GM_Ticket*> GmTicketList;
|
||||
SkillRangeType GetSkillRangeType(SkillLineEntry const *pSkill, bool racial);
|
||||
|
||||
#define MAX_PLAYER_NAME 12 // max allowed by client name length
|
||||
@@ -713,7 +696,6 @@ class ObjectMgr
|
||||
void LoadTrainerSpell();
|
||||
bool AddSpellToTrainer(uint32 entry, uint32 spell, Field *fields, std::set<uint32> *skip_trainers, std::set<uint32> *talentIds);
|
||||
int LoadReferenceTrainer(uint32 trainer, int32 spell, std::set<uint32> *skip_trainers, std::set<uint32> *talentIds);
|
||||
void LoadGMTickets();
|
||||
|
||||
std::string GeneratePetName(uint32 entry);
|
||||
uint32 GetBaseXP(uint8 level);
|
||||
@@ -950,23 +932,6 @@ class ObjectMgr
|
||||
return SpellClickInfoMapBounds(mSpellClickInfoMap.lower_bound(creature_id),mSpellClickInfoMap.upper_bound(creature_id));
|
||||
}
|
||||
|
||||
GM_Ticket *GetGMTicket(uint64 ticketGuid)
|
||||
{
|
||||
for (GmTicketList::const_iterator i = m_GMTicketList.begin(); i != m_GMTicketList.end(); ++i)
|
||||
if ((*i) && (*i)->guid == ticketGuid)
|
||||
return (*i);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
GM_Ticket *GetGMTicketByPlayer(uint64 playerGuid)
|
||||
{
|
||||
for (GmTicketList::const_iterator i = m_GMTicketList.begin(); i != m_GMTicketList.end(); ++i)
|
||||
if ((*i) && (*i)->playerGuid == playerGuid && (*i)->closed == 0)
|
||||
return (*i);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
GossipMenusMapBounds GetGossipMenusMapBounds(uint32 uiMenuId) const
|
||||
{
|
||||
return GossipMenusMapBounds(m_mGossipMenusMap.lower_bound(uiMenuId),m_mGossipMenusMap.upper_bound(uiMenuId));
|
||||
@@ -986,13 +951,6 @@ class ObjectMgr
|
||||
return GossipMenuItemsMapBoundsNonConst(m_mGossipMenuItemsMap.lower_bound(uiMenuId),m_mGossipMenuItemsMap.upper_bound(uiMenuId));
|
||||
}
|
||||
|
||||
void AddOrUpdateGMTicket(GM_Ticket &ticket, bool create = false);
|
||||
void _AddOrUpdateGMTicket(GM_Ticket &ticket);
|
||||
void RemoveGMTicket(uint64 ticketGuid, int64 source = -1, bool permanently = false);
|
||||
void RemoveGMTicket(GM_Ticket *ticket, int64 source = -1, bool permanently = false);
|
||||
GmTicketList m_GMTicketList;
|
||||
uint64 GenerateGMTicketId();
|
||||
|
||||
// for wintergrasp only
|
||||
GraveYardMap mGraveYardMap;
|
||||
|
||||
@@ -1013,7 +971,6 @@ class ObjectMgr
|
||||
uint32 m_ItemTextId;
|
||||
uint32 m_mailid;
|
||||
uint32 m_hiPetNumber;
|
||||
uint64 m_GMticketid;
|
||||
|
||||
// first free low guid for seelcted guid type
|
||||
uint32 m_hiCharGuid;
|
||||
|
||||
@@ -869,6 +869,7 @@ enum TrinityStrings
|
||||
LANG_COMMAND_TICKETLISTCOMMENT = 2023,
|
||||
LANG_COMMAND_TICKETLISTADDCOMMENT = 2024,
|
||||
LANG_COMMAND_TICKETLISTAGECREATE = 2025,
|
||||
LANG_COMMAND_TICKETSHOWESCALATEDLIST = 2026,
|
||||
|
||||
// Trinity strings 5000-9999
|
||||
LANG_COMMAND_FREEZE = 5000,
|
||||
|
||||
@@ -22,8 +22,11 @@
|
||||
#include "WorldPacket.h"
|
||||
#include "Common.h"
|
||||
#include "ObjectMgr.h"
|
||||
#include "TicketMgr.h"
|
||||
#include "Player.h"
|
||||
#include "World.h"
|
||||
#include "WorldSession.h"
|
||||
#include "Util.h"
|
||||
|
||||
void WorldSession::HandleGMTicketCreateOpcode(WorldPacket & recv_data)
|
||||
{
|
||||
@@ -33,31 +36,32 @@ void WorldSession::HandleGMTicketCreateOpcode(WorldPacket & recv_data)
|
||||
return;
|
||||
}
|
||||
|
||||
if (GM_Ticket *ticket = sObjectMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID()))
|
||||
if (GM_Ticket *ticket = sTicketMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID()))
|
||||
{
|
||||
WorldPacket data(SMSG_GMTICKET_CREATE, 4);
|
||||
data << uint32(1); // 1 - You already have GM ticket
|
||||
data << uint32(GMTICKET_RESPONSE_FAILURE); // You already have GM ticket
|
||||
SendPacket(&data);
|
||||
return;
|
||||
}
|
||||
|
||||
uint32 map;
|
||||
uint32 map, unk1;
|
||||
uint8 needResponse; // ignored
|
||||
float x, y, z;
|
||||
std::string ticketText, ticketText2;
|
||||
|
||||
SendQueryTimeResponse();
|
||||
|
||||
WorldPacket data(SMSG_GMTICKET_CREATE, 4);
|
||||
recv_data >> map;
|
||||
recv_data >> x;
|
||||
recv_data >> y;
|
||||
recv_data >> z;
|
||||
recv_data >> ticketText;
|
||||
recv_data >> ticketText2;
|
||||
recv_data >> unk1; // not sure what this is... replyTo?
|
||||
recv_data >> needResponse; // always 1/0 -- not sure what retail does with this
|
||||
|
||||
GM_Ticket *ticket = new GM_Ticket;
|
||||
ticket->name = GetPlayer()->GetName();
|
||||
ticket->guid = sObjectMgr.GenerateGMTicketId();
|
||||
ticket->guid = sTicketMgr.GenerateGMTicketId();
|
||||
ticket->playerGuid = GetPlayer()->GetGUID();
|
||||
ticket->message = ticketText;
|
||||
ticket->createtime = time(NULL);
|
||||
@@ -69,27 +73,29 @@ void WorldSession::HandleGMTicketCreateOpcode(WorldPacket & recv_data)
|
||||
ticket->closed = 0;
|
||||
ticket->assignedToGM = 0;
|
||||
ticket->comment = "";
|
||||
ticket->completed = false;
|
||||
ticket->escalated = TICKET_UNASSIGNED;
|
||||
ticket->response = "";
|
||||
|
||||
sObjectMgr.AddOrUpdateGMTicket(*ticket, true);
|
||||
sTicketMgr.AddOrUpdateGMTicket(*ticket, true);
|
||||
|
||||
data << uint32(2);
|
||||
WorldPacket data(SMSG_GMTICKET_CREATE, 4);
|
||||
data << uint32(GMTICKET_RESPONSE_SUCCESS);
|
||||
SendPacket(&data);
|
||||
|
||||
sWorld.SendGMText(LANG_COMMAND_TICKETNEW, GetPlayer()->GetName(), ticket->guid);
|
||||
|
||||
}
|
||||
|
||||
void WorldSession::HandleGMTicketUpdateOpcode(WorldPacket & recv_data)
|
||||
{
|
||||
WorldPacket data(SMSG_GMTICKET_UPDATETEXT, 4);
|
||||
|
||||
std::string message;
|
||||
recv_data >> message;
|
||||
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID());
|
||||
GM_Ticket *ticket = sTicketMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID());
|
||||
if (!ticket)
|
||||
{
|
||||
data << uint32(1);
|
||||
WorldPacket data(SMSG_GMTICKET_UPDATETEXT, 4);
|
||||
data << uint32(GMTICKET_RESPONSE_FAILURE);
|
||||
SendPacket(&data);
|
||||
return;
|
||||
}
|
||||
@@ -97,28 +103,28 @@ void WorldSession::HandleGMTicketUpdateOpcode(WorldPacket & recv_data)
|
||||
ticket->message = message;
|
||||
ticket->timestamp = time(NULL);
|
||||
|
||||
sObjectMgr.AddOrUpdateGMTicket(*ticket);
|
||||
sTicketMgr.AddOrUpdateGMTicket(*ticket);
|
||||
|
||||
data << uint32(2);
|
||||
WorldPacket data(SMSG_GMTICKET_UPDATETEXT, 4);
|
||||
data << uint32(GMTICKET_RESPONSE_SUCCESS);
|
||||
SendPacket(&data);
|
||||
|
||||
sWorld.SendGMText(LANG_COMMAND_TICKETUPDATED, GetPlayer()->GetName(), ticket->guid);
|
||||
|
||||
}
|
||||
|
||||
void WorldSession::HandleGMTicketDeleteOpcode(WorldPacket & /*recv_data*/)
|
||||
{
|
||||
GM_Ticket* ticket = sObjectMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID());
|
||||
GM_Ticket* ticket = sTicketMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID());
|
||||
|
||||
if (ticket)
|
||||
{
|
||||
WorldPacket data(SMSG_GMTICKET_DELETETICKET, 4);
|
||||
data << uint32(9);
|
||||
data << uint32(GMTICKET_RESPONSE_TICKET_DELETED);
|
||||
SendPacket(&data);
|
||||
|
||||
sWorld.SendGMText(LANG_COMMAND_TICKETPLAYERABANDON, GetPlayer()->GetName(), ticket->guid);
|
||||
sObjectMgr.RemoveGMTicket(ticket, GetPlayer()->GetGUID(), false);
|
||||
SendGMTicketGetTicket(0x0A, 0);
|
||||
sTicketMgr.RemoveGMTicket(ticket, GetPlayer()->GetGUID(), false);
|
||||
SendGMTicketGetTicket(GMTICKET_STATUS_DEFAULT, NULL);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -126,36 +132,184 @@ void WorldSession::HandleGMTicketGetTicketOpcode(WorldPacket & /*recv_data*/)
|
||||
{
|
||||
SendQueryTimeResponse();
|
||||
|
||||
GM_Ticket *ticket = sObjectMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID());
|
||||
if (ticket)
|
||||
SendGMTicketGetTicket(0x06, ticket->message.c_str());
|
||||
if (GM_Ticket *ticket = sTicketMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID()))
|
||||
{
|
||||
if (ticket->completed)
|
||||
SendGMTicketResponse(ticket);
|
||||
else
|
||||
SendGMTicketGetTicket(GMTICKET_STATUS_HASTEXT, ticket->message.c_str(), ticket);
|
||||
}
|
||||
else
|
||||
SendGMTicketGetTicket(0x0A, 0);
|
||||
|
||||
SendGMTicketGetTicket(GMTICKET_STATUS_DEFAULT, NULL);
|
||||
}
|
||||
|
||||
void WorldSession::HandleGMTicketSystemStatusOpcode(WorldPacket & /*recv_data*/)
|
||||
{
|
||||
WorldPacket data(SMSG_GMTICKET_SYSTEMSTATUS, 4);
|
||||
data << uint32(1);
|
||||
// are we sure this is a uint32? Should ask Zor
|
||||
data << uint32(sTicketMgr.GetStatus() ? GMTICKET_QUEUE_STATUS_ENABLED : GMTICKET_QUEUE_STATUS_DISABLED);
|
||||
SendPacket(&data);
|
||||
}
|
||||
|
||||
void WorldSession::SendGMTicketGetTicket(uint32 status, char const* text)
|
||||
void WorldSession::SendGMTicketGetTicket(uint32 status, char const* text, GM_Ticket *ticket /* = NULL */)
|
||||
{
|
||||
int len = text ? strlen(text) : 0;
|
||||
WorldPacket data(SMSG_GMTICKET_GETTICKET, (4+len+1+4+2+4+4));
|
||||
WorldPacket data(SMSG_GMTICKET_GETTICKET, (4+4+((status == GMTICKET_STATUS_HASTEXT) ? (len+1+4+4+4+1+1) : 0)));
|
||||
data << uint32(status); // standard 0x0A, 0x06 if text present
|
||||
data << uint32(1); // unk flags, if 0, can't edit the ticket
|
||||
if (status == 6)
|
||||
data << uint32(1); // g_HasActiveGMTicket -- not a flag
|
||||
|
||||
if (status == GMTICKET_STATUS_HASTEXT)
|
||||
{
|
||||
data << text; // ticket text
|
||||
data << uint8(0x7); // ticket category
|
||||
data << float(0); // tickets in queue?
|
||||
data << float(0); // if > "tickets in queue" then "We are currently experiencing a high volume of petitions."
|
||||
data << float(0); // 0 - "Your ticket will be serviced soon", 1 - "Wait time currently unavailable"
|
||||
data << uint8(0); // if == 2 and next field == 1 then "Your ticket has been escalated"
|
||||
data << uint8(0); // const
|
||||
data << uint8(0x7); // ticket category; why is this hardcoded? does it make a diff re: client?
|
||||
|
||||
// we've got the easy stuff done by now.
|
||||
// Now we need to go through the client logic for displaying various levels of ticket load
|
||||
if (ticket)
|
||||
{
|
||||
// get ticketage, but it's stored in seconds so we have to do it in days
|
||||
float ticketAge = (float)time(NULL) - (float)ticket->timestamp;
|
||||
ticketAge /= DAY;
|
||||
|
||||
data << float(ticketAge); // ticketAge (days)
|
||||
if (GM_Ticket *oldestTicket = sTicketMgr.GetOldestOpenGMTicket())
|
||||
{
|
||||
// get ticketage, but it's stored in seconds so we have to do it in days
|
||||
float oldestTicketAge = (float)time(NULL) - (float)oldestTicket->timestamp;
|
||||
oldestTicketAge /= DAY;
|
||||
data << float(oldestTicketAge);
|
||||
}
|
||||
else
|
||||
data << float(0);
|
||||
|
||||
// I am not sure how blizzlike this is, and we don't really have a way to find out
|
||||
int64 lastChange = int64(sTicketMgr.GetLastChange());
|
||||
float timeDiff = float(int64(time(NULL)) - lastChange);
|
||||
timeDiff /= DAY;
|
||||
data << float(timeDiff);
|
||||
|
||||
data << uint8(std::min(ticket->escalated, uint8(TICKET_IN_ESCALATION_QUEUE))); // escalated data
|
||||
data << uint8(ticket->viewed ? GMTICKET_OPENEDBYGM_STATUS_OPENED : GMTICKET_OPENEDBYGM_STATUS_NOT_OPENED); // whether or not it has been viewed
|
||||
}
|
||||
else
|
||||
{
|
||||
// we can't actually get any numbers here...
|
||||
data << float(0);
|
||||
data << float(0);
|
||||
data << float(1);
|
||||
data << uint8(0);
|
||||
data << uint8(0);
|
||||
}
|
||||
}
|
||||
|
||||
SendPacket(&data);
|
||||
}
|
||||
|
||||
void WorldSession::SendGMTicketResponse(GM_Ticket *ticket)
|
||||
{
|
||||
if (!ticket)
|
||||
return;
|
||||
|
||||
WorldPacket data(SMSG_GMRESPONSE_RECEIVED);
|
||||
data << uint32(1); // unk? Zor says "hasActiveTicket"
|
||||
data << uint32(0); // can-edit - always 1 or 0, not flags
|
||||
data << ticket->message.c_str();
|
||||
data << ticket->response.c_str();
|
||||
for (int8 j = 0; j < 3; j++)
|
||||
data << uint8(0); // 3 null strings
|
||||
SendPacket(&data);
|
||||
}
|
||||
|
||||
void WorldSession::HandleGMSurveySubmit(WorldPacket& recv_data)
|
||||
{
|
||||
uint64 nextSurveyID = sTicketMgr.GetNextSurveyID();
|
||||
// just put the survey into the database
|
||||
std::ostringstream ss;
|
||||
uint32 mainSurvey; // GMSurveyCurrentSurvey.dbc, column 1 (all 9) ref to GMSurveySurveys.dbc
|
||||
recv_data >> mainSurvey;
|
||||
|
||||
ss << "INSERT INTO gm_surveys (player, surveyid, mainSurvey, overall_comment, timestamp) VALUES (";
|
||||
ss << GetPlayer()->GetGUID() << ", ";
|
||||
ss << nextSurveyID << ", ";
|
||||
ss << mainSurvey << ", ";
|
||||
|
||||
// sub_survey1, r1, comment1, sub_survey2, r2, comment2, sub_survey3, r3, comment3, sub_survey4, r4, comment4, sub_survey5, r5, comment5, sub_survey6, r6, comment6, sub_survey7, r7, comment7, sub_survey8, r8, comment8, sub_survey9, r9, comment9, sub_survey10, r10, comment10,
|
||||
|
||||
for (uint8 i = 0; i < 10; i++)
|
||||
{
|
||||
std::ostringstream os;
|
||||
os << "INSERT INTO gm_subsurveys (surveyid, subsurveyid, rank, comment) VALUES (";
|
||||
uint32 subSurveyId; // ref to i'th GMSurveySurveys.dbc field (all fields in that dbc point to fields in GMSurveyQuestions.dbc)
|
||||
recv_data >> subSurveyId;
|
||||
if(!subSurveyId)
|
||||
break;
|
||||
|
||||
uint8 rank; // probably some sort of ref to GMSurveyAnswers.dbc
|
||||
std::string comment; // comment ("Usage: GMSurveyAnswerSubmit(question, rank, comment)")
|
||||
recv_data >> rank;
|
||||
recv_data >> comment;
|
||||
|
||||
os << nextSurveyID << " ";
|
||||
os << subSurveyId << ", ";
|
||||
os << rank << ", '";
|
||||
CharacterDatabase.escape_string(comment);
|
||||
os << comment << "');";
|
||||
CharacterDatabase.PExecute(os.str().c_str());
|
||||
}
|
||||
|
||||
std::string comment; // just a guess
|
||||
recv_data >> comment;
|
||||
CharacterDatabase.escape_string(comment);
|
||||
ss << "'" << comment << "', ";
|
||||
ss << int64(time_t(NULL)) << ");";
|
||||
|
||||
CharacterDatabase.PExecute(ss.str().c_str());
|
||||
}
|
||||
|
||||
void WorldSession::HandleReportLag(WorldPacket& recv_data)
|
||||
{
|
||||
// just put the lag report into the database...
|
||||
// can't think of anything else to do with it
|
||||
uint32 lagType, mapId;
|
||||
float x, y, z;
|
||||
recv_data >> lagType;
|
||||
recv_data >> mapId;
|
||||
recv_data >> x;
|
||||
recv_data >> y;
|
||||
recv_data >> z;
|
||||
|
||||
// build and execute query
|
||||
std::ostringstream os;
|
||||
os << "INSERT INTO lag_reports (player, lag_type, map, x, y, z) VALUES (";
|
||||
os << GetPlayer()->GetGUID() << ", ";
|
||||
os << lagType << ", ";
|
||||
os << mapId << ", ";
|
||||
os << x << ", ";
|
||||
os << y << ", ";
|
||||
os << z << ");";
|
||||
|
||||
CharacterDatabase.Execute(os.str().c_str());
|
||||
}
|
||||
|
||||
void WorldSession::HandleGMResponseResolve(WorldPacket& recvPacket)
|
||||
{
|
||||
// empty packet
|
||||
GM_Ticket* ticket = sTicketMgr.GetGMTicketByPlayer(GetPlayer()->GetGUID());
|
||||
|
||||
if (ticket)
|
||||
{
|
||||
uint8 getSurvey = 0;
|
||||
if ((float)rand_chance() < sWorld.getFloatConfig(CONFIG_CHANCE_OF_GM_SURVEY))
|
||||
getSurvey = 1;
|
||||
|
||||
WorldPacket data(SMSG_GMRESPONSE_STATUS_UPDATE, 4);
|
||||
data << uint8(getSurvey);
|
||||
SendPacket(&data);
|
||||
|
||||
WorldPacket data2(SMSG_GMTICKET_DELETETICKET, 4);
|
||||
data2 << uint32(GMTICKET_RESPONSE_TICKET_DELETED);
|
||||
SendPacket(&data2);
|
||||
sTicketMgr.RemoveGMTicket(ticket, GetPlayer()->GetGUID(), true);
|
||||
SendGMTicketGetTicket(GMTICKET_STATUS_DEFAULT, NULL);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -838,7 +838,7 @@ OpcodeHandler opcodeTable[NUM_MSG_TYPES] =
|
||||
/*0x327*/ { "CMSG_GM_UPDATE_TICKET_STATUS", STATUS_NEVER, &WorldSession::Handle_NULL },
|
||||
/*0x328*/ { "SMSG_GM_TICKET_STATUS_UPDATE", STATUS_NEVER, &WorldSession::Handle_ServerSide },
|
||||
/*0x329*/ { "MSG_SET_DUNGEON_DIFFICULTY", STATUS_LOGGEDIN, &WorldSession::HandleSetDungeonDifficultyOpcode},
|
||||
/*0x32A*/ { "CMSG_GMSURVEY_SUBMIT", STATUS_NEVER, &WorldSession::Handle_NULL },//LOGGEDIN, &WorldSession::HandleGMSurveySubmit },
|
||||
/*0x32A*/ { "CMSG_GMSURVEY_SUBMIT", STATUS_LOGGEDIN, &WorldSession::HandleGMSurveySubmit },
|
||||
/*0x32B*/ { "SMSG_UPDATE_INSTANCE_OWNERSHIP", STATUS_NEVER, &WorldSession::Handle_ServerSide },
|
||||
/*0x32C*/ { "CMSG_IGNORE_KNOCKBACK_CHEAT", STATUS_NEVER, &WorldSession::Handle_NULL },
|
||||
/*0x32D*/ { "SMSG_CHAT_PLAYER_AMBIGUOUS", STATUS_NEVER, &WorldSession::Handle_ServerSide },
|
||||
@@ -1292,7 +1292,7 @@ OpcodeHandler opcodeTable[NUM_MSG_TYPES] =
|
||||
/*0x4ED*/ { "SMSG_TOGGLE_XP_GAIN", STATUS_NEVER, &WorldSession::Handle_ServerSide },
|
||||
/*0x4EE*/ { "SMSG_GMRESPONSE_DB_ERROR", STATUS_NEVER, &WorldSession::Handle_ServerSide },
|
||||
/*0x4EF*/ { "SMSG_GMRESPONSE_RECEIVED", STATUS_NEVER, &WorldSession::Handle_ServerSide },
|
||||
/*0x4F0*/ { "CMSG_GMRESPONSE_RESOLVE", STATUS_NEVER, &WorldSession::Handle_NULL },
|
||||
/*0x4F0*/ { "CMSG_GMRESPONSE_RESOLVE", STATUS_LOGGEDIN, &WorldSession::HandleGMResponseResolve },
|
||||
/*0x4F1*/ { "SMSG_GMRESPONSE_STATUS_UPDATE", STATUS_NEVER, &WorldSession::Handle_ServerSide },
|
||||
/*0x4F2*/ { "UMSG_UNKNOWN_1266", STATUS_NEVER, &WorldSession::Handle_NULL },
|
||||
/*0x4F3*/ { "UMSG_UNKNOWN_1267", STATUS_NEVER, &WorldSession::Handle_NULL },
|
||||
|
||||
@@ -50,6 +50,8 @@ class CharacterHandler;
|
||||
class SpellCastTargets;
|
||||
struct AreaTableEntry;
|
||||
|
||||
struct GM_Ticket;
|
||||
|
||||
enum AccountDataType
|
||||
{
|
||||
GLOBAL_CONFIG_CACHE = 0, // 0x01 g
|
||||
@@ -375,9 +377,11 @@ class WorldSession
|
||||
void HandleGMTicketDeleteOpcode(WorldPacket& recvPacket);
|
||||
void HandleGMTicketGetTicketOpcode(WorldPacket& recvPacket);
|
||||
void HandleGMTicketSystemStatusOpcode(WorldPacket& recvPacket);
|
||||
void SendGMTicketGetTicket(uint32 status, char const* text);
|
||||
|
||||
//void HandleGMSurveySubmit(WorldPacket& recvPacket);
|
||||
void SendGMTicketGetTicket(uint32 status, char const* text, GM_Ticket *ticket = NULL);
|
||||
void SendGMTicketResponse(GM_Ticket *ticket);
|
||||
void HandleGMSurveySubmit(WorldPacket& recvPacket);
|
||||
void HandleReportLag(WorldPacket& recvPacket);
|
||||
void HandleGMResponseResolve(WorldPacket& recvPacket);
|
||||
|
||||
void HandleTogglePvP(WorldPacket& recvPacket);
|
||||
|
||||
|
||||
@@ -0,0 +1,193 @@
|
||||
/*
|
||||
* Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/>
|
||||
*
|
||||
* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "Common.h"
|
||||
#include "DatabaseEnv.h"
|
||||
#include "SQLStorage.h"
|
||||
#include "ProgressBar.h"
|
||||
#include "Log.h"
|
||||
#include "TicketMgr.h"
|
||||
#include "WorldPacket.h"
|
||||
#include "WorldSession.h"
|
||||
|
||||
TicketMgr::TicketMgr()
|
||||
{
|
||||
m_GMticketid = 0; // this is initialized in LoadGMTickets() but it's best to be safe
|
||||
m_GMSurveyID = 0;
|
||||
m_openTickets = 0;
|
||||
lastChange = time(NULL);
|
||||
status = true;
|
||||
}
|
||||
|
||||
uint64 TicketMgr::GenerateGMTicketId()
|
||||
{
|
||||
return ++m_GMticketid;
|
||||
}
|
||||
|
||||
void TicketMgr::LoadGMTickets()
|
||||
{
|
||||
if (!m_GMTicketList.empty())
|
||||
{
|
||||
for (GmTicketList::const_iterator itr = m_GMTicketList.begin(); itr != m_GMTicketList.end(); ++itr)
|
||||
delete *itr;
|
||||
}
|
||||
m_GMTicketList.clear();
|
||||
m_GMticketid = 0;
|
||||
m_openTickets = 0;
|
||||
|
||||
QueryResult_AutoPtr result = CharacterDatabase.Query("SELECT guid, playerGuid, name, message, createtime, map, posX, posY, posZ, timestamp, closed, assignedto, comment, completed, escalated, viewed FROM gm_tickets");
|
||||
|
||||
if (!result)
|
||||
{
|
||||
barGoLink bar(1);
|
||||
bar.step();
|
||||
sLog.outString();
|
||||
sLog.outString(">> GM Tickets table is empty, no tickets were loaded.");
|
||||
return;
|
||||
}
|
||||
|
||||
uint16 count = 0;
|
||||
barGoLink bar ((*result).GetRowCount());
|
||||
GM_Ticket *ticket;
|
||||
do
|
||||
{
|
||||
Field *fields = result->Fetch();
|
||||
ticket = new GM_Ticket;
|
||||
ticket->guid = fields[0].GetUInt64();
|
||||
ticket->playerGuid = fields[1].GetUInt64();
|
||||
ticket->name = fields[2].GetCppString();
|
||||
ticket->message = fields[3].GetCppString();
|
||||
ticket->createtime = fields[4].GetUInt64();
|
||||
ticket->map = fields[5].GetUInt32();
|
||||
ticket->pos_x = fields[6].GetFloat();
|
||||
ticket->pos_y = fields[7].GetFloat();
|
||||
ticket->pos_z = fields[8].GetFloat();
|
||||
ticket->timestamp = fields[9].GetUInt64();
|
||||
ticket->closed = fields[10].GetUInt64();
|
||||
if (ticket->closed == 0)
|
||||
m_openTickets++;
|
||||
|
||||
ticket->assignedToGM = fields[11].GetUInt64();
|
||||
ticket->comment = fields[12].GetCppString();
|
||||
ticket->completed = fields[13].GetBool();
|
||||
ticket->escalated = fields[14].GetUInt8();
|
||||
ticket->viewed = fields[15].GetBool();
|
||||
++count;
|
||||
bar.step();
|
||||
|
||||
m_GMTicketList.push_back(ticket);
|
||||
|
||||
} while (result->NextRow());
|
||||
|
||||
result = CharacterDatabase.Query("SELECT MAX(guid) from gm_tickets");
|
||||
|
||||
if (result)
|
||||
{
|
||||
Field *fields = result->Fetch();
|
||||
m_GMticketid = fields[0].GetUInt64();
|
||||
}
|
||||
|
||||
sLog.outString(">> Loaded %u GM Tickets from the database.", count);
|
||||
}
|
||||
|
||||
void TicketMgr::LoadGMSurveys()
|
||||
{
|
||||
// we don't actually load anything into memory here as there's no reason to
|
||||
QueryResult_AutoPtr result = CharacterDatabase.Query("SELECT MAX(surveyid) FROM gm_surveys");
|
||||
if (result)
|
||||
{
|
||||
Field *fields = result->Fetch();
|
||||
m_GMSurveyID = fields[0].GetUInt64();
|
||||
}
|
||||
else
|
||||
m_GMSurveyID = 0;
|
||||
|
||||
sLog.outString(">> Loaded GM Survey count from database.");
|
||||
}
|
||||
|
||||
void TicketMgr::AddOrUpdateGMTicket(GM_Ticket &ticket, bool create)
|
||||
{
|
||||
if (create)
|
||||
{
|
||||
m_GMTicketList.push_back(&ticket);
|
||||
if (ticket.closed == 0)
|
||||
m_openTickets++;
|
||||
}
|
||||
|
||||
_AddOrUpdateGMTicket(ticket);
|
||||
}
|
||||
|
||||
void TicketMgr::_AddOrUpdateGMTicket(GM_Ticket &ticket)
|
||||
{
|
||||
std::string msg(ticket.message), name(ticket.name), comment(ticket.comment);
|
||||
CharacterDatabase.escape_string(msg);
|
||||
CharacterDatabase.escape_string(name);
|
||||
CharacterDatabase.escape_string(comment);
|
||||
std::ostringstream ss;
|
||||
ss << "REPLACE INTO gm_tickets (guid, playerGuid, name, message, createtime, map, posX, posY, posZ, timestamp, closed, assignedto, comment, completed, escalated, viewed) VALUES (";
|
||||
ss << ticket.guid << ", ";
|
||||
ss << ticket.playerGuid << ", '";
|
||||
ss << name << "', '";
|
||||
ss << msg << "', " ;
|
||||
ss << ticket.createtime << ", ";
|
||||
ss << ticket.map << ", ";
|
||||
ss << ticket.pos_x << ", ";
|
||||
ss << ticket.pos_y << ", ";
|
||||
ss << ticket.pos_z << ", ";
|
||||
ss << ticket.timestamp << ", ";
|
||||
ss << ticket.closed << ", ";
|
||||
ss << ticket.assignedToGM << ", '";
|
||||
ss << comment << "', ";
|
||||
ss << (ticket.completed ? 1 : 0) << ", ";
|
||||
ss << ticket.escalated << ", ";
|
||||
ss << (ticket.viewed ? 1 : 0) << ");";
|
||||
|
||||
SQLTransaction trans = CharacterDatabase.BeginTransaction();
|
||||
trans->Append(ss.str().c_str());
|
||||
CharacterDatabase.CommitTransaction(trans);
|
||||
}
|
||||
|
||||
void TicketMgr::RemoveGMTicket(GM_Ticket *ticket, int64 source, bool permanently)
|
||||
{
|
||||
for (GmTicketList::iterator i = m_GMTicketList.begin(); i != m_GMTicketList.end(); ++i)
|
||||
if ((*i)->guid == ticket->guid)
|
||||
{
|
||||
if (permanently)
|
||||
{
|
||||
CharacterDatabase.PExecute("DELETE FROM gm_tickets WHERE guid = '%u'", ticket->guid);
|
||||
i = m_GMTicketList.erase(i);
|
||||
ticket = NULL;
|
||||
return;
|
||||
}
|
||||
(*i)->closed = source;
|
||||
|
||||
if (source != 0)
|
||||
m_openTickets--;
|
||||
|
||||
_AddOrUpdateGMTicket(*(*i));
|
||||
}
|
||||
}
|
||||
|
||||
void TicketMgr::RemoveGMTicket(uint64 ticketGuid, int64 source, bool permanently)
|
||||
{
|
||||
GM_Ticket *ticket = GetGMTicket(ticketGuid);
|
||||
ASSERT(ticket); // hmm
|
||||
RemoveGMTicket(ticket, source, permanently);
|
||||
}
|
||||
@@ -0,0 +1,173 @@
|
||||
/*
|
||||
* Copyright (C) 2008-2010 Trinity <http://www.trinitycore.org/>
|
||||
*
|
||||
* 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, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _TICKETMGR_H
|
||||
#define _TICKETMGR_H
|
||||
|
||||
#include <string>
|
||||
#include <ace/Singleton.h>
|
||||
#include "Common.h"
|
||||
#include "DatabaseEnv.h"
|
||||
#include "SQLStorage.h"
|
||||
#include "SQLStorageImpl.h"
|
||||
|
||||
// from blizzard lua
|
||||
enum GMTicketSystemStatus
|
||||
{
|
||||
GMTICKET_QUEUE_STATUS_DISABLED = -1,
|
||||
GMTICKET_QUEUE_STATUS_ENABLED = 1,
|
||||
};
|
||||
|
||||
enum GMTicketStatus
|
||||
{
|
||||
GMTICKET_STATUS_HASTEXT = 0x06,
|
||||
GMTICKET_STATUS_DEFAULT = 0x0A,
|
||||
};
|
||||
|
||||
enum GMTicketResponse
|
||||
{
|
||||
GMTICKET_RESPONSE_FAILURE = 1,
|
||||
GMTICKET_RESPONSE_SUCCESS = 2,
|
||||
GMTICKET_RESPONSE_TICKET_DELETED = 9,
|
||||
};
|
||||
|
||||
// from Blizzard LUA:
|
||||
// GMTICKET_ASSIGNEDTOGM_STATUS_NOT_ASSIGNED = 0; -- ticket is not currently assigned to a gm
|
||||
// GMTICKET_ASSIGNEDTOGM_STATUS_ASSIGNED = 1; -- ticket is assigned to a normal gm
|
||||
// GMTICKET_ASSIGNEDTOGM_STATUS_ESCALATED = 2; -- ticket is in the escalation queue
|
||||
// 3 is a custom value and should never actually be sent
|
||||
enum GMTicketEscalationStatus
|
||||
{
|
||||
TICKET_UNASSIGNED = 0,
|
||||
TICKET_ASSIGNED = 1,
|
||||
TICKET_IN_ESCALATION_QUEUE = 2,
|
||||
TICKET_ESCALATED_ASSIGNED = 3,
|
||||
};
|
||||
|
||||
// from blizzard lua
|
||||
enum GMTicketOpenedByGMStatus
|
||||
{
|
||||
GMTICKET_OPENEDBYGM_STATUS_NOT_OPENED = 0, // ticket has never been opened by a gm
|
||||
GMTICKET_OPENEDBYGM_STATUS_OPENED = 1, // ticket has been opened by a gm
|
||||
};
|
||||
|
||||
enum LagReportType
|
||||
{
|
||||
LAG_REPORT_TYPE_LOOT = 1,
|
||||
LAG_REPORT_TYPE_AUCTION_HOUSE = 2,
|
||||
LAG_REPORT_TYPE_MAIL = 3,
|
||||
LAG_REPORT_TYPE_CHAT = 4,
|
||||
LAG_REPORT_TYPE_MOVEMENT = 5,
|
||||
LAG_REPORT_TYPE_SPELL = 6
|
||||
};
|
||||
|
||||
struct GM_Ticket
|
||||
{
|
||||
uint64 guid;
|
||||
uint64 playerGuid;
|
||||
std::string name;
|
||||
float pos_x;
|
||||
float pos_y;
|
||||
float pos_z;
|
||||
uint32 map;
|
||||
std::string message;
|
||||
uint64 createtime;
|
||||
uint64 timestamp;
|
||||
int64 closed; // 0 = Open, -1 = Console, playerGuid = player abandoned ticket, other = GM who closed it.
|
||||
uint64 assignedToGM;
|
||||
std::string comment;
|
||||
bool completed;
|
||||
uint8 escalated;
|
||||
bool viewed;
|
||||
std::string response;
|
||||
};
|
||||
typedef std::list<GM_Ticket*> GmTicketList;
|
||||
|
||||
class TicketMgr
|
||||
{
|
||||
TicketMgr();
|
||||
friend class ACE_Singleton<TicketMgr, ACE_Null_Mutex>;
|
||||
|
||||
public:
|
||||
void LoadGMTickets();
|
||||
void LoadGMSurveys();
|
||||
|
||||
GM_Ticket *GetGMTicket(uint64 ticketGuid)
|
||||
{
|
||||
for (GmTicketList::const_iterator i = m_GMTicketList.begin(); i != m_GMTicketList.end(); ++i)
|
||||
if ((*i) && (*i)->guid == ticketGuid)
|
||||
return (*i);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
GM_Ticket *GetGMTicketByPlayer(uint64 playerGuid)
|
||||
{
|
||||
for (GmTicketList::const_iterator i = m_GMTicketList.begin(); i != m_GMTicketList.end(); ++i)
|
||||
if ((*i) && (*i)->playerGuid == playerGuid && (*i)->closed == 0)
|
||||
return (*i);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void AddOrUpdateGMTicket(GM_Ticket &ticket, bool create = false);
|
||||
void _AddOrUpdateGMTicket(GM_Ticket &ticket);
|
||||
void RemoveGMTicket(uint64 ticketGuid, int64 source = -1, bool permanently = false);
|
||||
void RemoveGMTicket(GM_Ticket *ticket, int64 source = -1, bool permanently = false);
|
||||
uint64 GenerateGMTicketId();
|
||||
bool GetStatus() const { return status; }
|
||||
void SetStatus(bool newStatus) { status = newStatus; }
|
||||
uint64 GetOpenTicketCount() { return m_openTickets; }
|
||||
uint64 GetNextSurveyID()
|
||||
{
|
||||
return ++m_GMSurveyID;
|
||||
}
|
||||
|
||||
GM_Ticket *GetOldestOpenGMTicket()
|
||||
{
|
||||
for (GmTicketList::const_iterator i = m_GMTicketList.begin(); i != m_GMTicketList.end(); ++i)
|
||||
if ((*i) && (*i)->closed == 0 && !(*i)->completed)
|
||||
return (*i);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
time_t GetLastChange()
|
||||
{
|
||||
return lastChange;
|
||||
}
|
||||
|
||||
void UpdateLastChange()
|
||||
{
|
||||
lastChange = time(NULL);
|
||||
}
|
||||
|
||||
GmTicketList m_GMTicketList;
|
||||
|
||||
protected:
|
||||
uint64 m_GMticketid;
|
||||
uint64 m_GMSurveyID;
|
||||
bool status;
|
||||
uint64 m_openTickets;
|
||||
uint32 m_gmCount;
|
||||
time_t lastChange;
|
||||
};
|
||||
|
||||
#define sTicketMgr (*ACE_Singleton<TicketMgr, ACE_Null_Mutex>::instance())
|
||||
|
||||
#endif // _TICKETMGR_H
|
||||
@@ -39,6 +39,7 @@
|
||||
#include "AchievementMgr.h"
|
||||
#include "AuctionHouseMgr.h"
|
||||
#include "ObjectMgr.h"
|
||||
#include "TicketMgr.h"
|
||||
#include "CreatureEventAIMgr.h"
|
||||
#include "SpellMgr.h"
|
||||
#include "Chat.h"
|
||||
@@ -886,6 +887,7 @@ void World::LoadConfigSettings(bool reload)
|
||||
m_bool_configs[CONFIG_ALLOW_GM_FRIEND] = sConfig.GetBoolDefault("GM.AllowFriend", false);
|
||||
m_bool_configs[CONFIG_GM_LOWER_SECURITY] = sConfig.GetBoolDefault("GM.LowerSecurity", false);
|
||||
m_bool_configs[CONFIG_GM_ALLOW_ACHIEVEMENT_GAINS] = sConfig.GetBoolDefault("GM.AllowAchievementGain", true);
|
||||
m_float_configs[CONFIG_CHANCE_OF_GM_SURVEY] = sConfig.GetFloatDefault("GM.TicketSystem.ChanceOfGMSurvey", 50.0f);
|
||||
|
||||
m_int_configs[CONFIG_GROUP_VISIBILITY] = sConfig.GetIntDefault("Visibility.GroupMode", 1);
|
||||
|
||||
@@ -1566,7 +1568,10 @@ void World::SetInitialWorldSettings()
|
||||
sConditionMgr.LoadConditions();
|
||||
|
||||
sLog.outString("Loading GM tickets...");
|
||||
sObjectMgr.LoadGMTickets();
|
||||
sTicketMgr.LoadGMTickets();
|
||||
|
||||
sLog.outString("Loading GM surveys...");
|
||||
sTicketMgr.LoadGMSurveys();
|
||||
|
||||
sLog.outString("Loading client addons...");
|
||||
sAddonMgr.LoadFromDB();
|
||||
|
||||
@@ -177,6 +177,7 @@ enum WorldFloatConfigs
|
||||
CONFIG_CREATURE_FAMILY_FLEE_ASSISTANCE_RADIUS,
|
||||
CONFIG_CREATURE_FAMILY_ASSISTANCE_RADIUS,
|
||||
CONFIG_THREAT_RADIUS,
|
||||
CONFIG_CHANCE_OF_GM_SURVEY,
|
||||
FLOAT_CONFIG_VALUE_COUNT
|
||||
};
|
||||
|
||||
|
||||
@@ -1354,6 +1354,11 @@ AllowPlayerCommands = 1
|
||||
# Default: 1 (enable)
|
||||
# 0 (disable)
|
||||
#
|
||||
# GM.TicketSystem.ChanceOfGMSurvey
|
||||
# Chance of sending a GM survey with every ticket completion.
|
||||
# Default: 50
|
||||
# 0 (disables surveys)
|
||||
#
|
||||
###############################################################################
|
||||
|
||||
GM.LoginState = 2
|
||||
@@ -1369,6 +1374,7 @@ GM.AllowInvite = 0
|
||||
GM.AllowFriend = 0
|
||||
GM.LowerSecurity = 0
|
||||
GM.AllowAchievementGain = 1
|
||||
GM.TicketSystem.ChanceOfGMSurvey = 50
|
||||
|
||||
###############################################################################
|
||||
# VISIBILITY AND RADIUSES
|
||||
|
||||
Reference in New Issue
Block a user