// Copyright (C) 2004 WoW Daemon
//
// 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 "StdAfx.h"

createFileSingleton( ChatHandler );


ChatHandler::ChatHandler()
{

}

ChatHandler::~ChatHandler()
{

}

ChatCommand * ChatHandler::getCommandTable()
{
    // Ignatich
    // TODO: change default security levels?

//    static bool first_call = true;

    static ChatCommand modifyCommandTable[] =
    {
        { "hp",         'm', NULL,    "Health Points/HP",    NULL, UNIT_FIELD_HEALTH,    UNIT_FIELD_MAXHEALTH, 1 },
        { "mana",       'm', NULL,    "Mana Points/MP",      NULL, UNIT_FIELD_POWER1,    UNIT_FIELD_MAXPOWER1, 1 },
        { "rage",       'm', NULL,    "Rage Points",         NULL, UNIT_FIELD_POWER2,    UNIT_FIELD_MAXPOWER2, 1 },
        { "energy",     'm', NULL,    "Energy Points",       NULL, UNIT_FIELD_POWER4,    UNIT_FIELD_MAXPOWER4, 1 },
        { "level",      'm', &ChatHandler::HandleModifyLevelCommand,"Level", NULL, 0, 0, 0 },
        { "armor",      'm', NULL,    "Armor",               NULL, UNIT_FIELD_STAT1,              0,           1 },
        { "holy",       'm', NULL,    "Holy Resistance",     NULL, UNIT_FIELD_RESISTANCES_01,     0,           1 },
        { "fire",       'm', NULL,    "Fire Resistance",     NULL, UNIT_FIELD_RESISTANCES_02,     0,           1 },
        { "nature",     'm', NULL,    "Nature Resistance",   NULL, UNIT_FIELD_RESISTANCES_03,     0,           1 },
        { "frost",      'm', NULL,    "Frost Resistance",    NULL, UNIT_FIELD_RESISTANCES_04,     0,           1 },
        { "shadow",     'm', NULL,    "Shadow Resistance",   NULL, UNIT_FIELD_RESISTANCES_05,     0,           1 },
        { "arcane",     'm', NULL,    "Arcane Resistance",   NULL, UNIT_FIELD_RESISTANCES_06,     0,           1 },
        { "damage",     'm', NULL,    "Unit Damage Min/Max", NULL, UNIT_FIELD_MINDAMAGE,  UNIT_FIELD_MAXDAMAGE,2 },
        { "scale",      'm', NULL,    "Size/Scale",          NULL, OBJECT_FIELD_SCALE_X, 0,                    2 },
        { "gold",       'm', &ChatHandler::HandleModifyGoldCommand,  "Gold/Money/Copper",      NULL,   0,  0,  0 },
        { "speed",      'm', &ChatHandler::HandleModifySpeedCommand, "Movement Speed",         NULL,   0,  0,  0 },
        { "nativedisplayid", 'm', NULL, "Native Display ID", NULL, UNIT_FIELD_NATIVEDISPLAYID, 0,              1 },
        { "displayid" , 'm', NULL,    "Display ID",          NULL, UNIT_FIELD_DISPLAYID,       0,              1 },
        { "flags" ,     'm', NULL,    "Unit Flags",          NULL, UNIT_FIELD_FLAGS,           0,              1 },
        { "faction",    'm', NULL,    "Faction Template",    NULL, UNIT_FIELD_FACTIONTEMPLATE, 0,              1 },
        { "dynamicflags",'m',NULL,    "Dynamic Flags",       NULL, UNIT_DYNAMIC_FLAGS,         0,              1 },
        { "talentpoints",'m',NULL,    "Talent Points",       NULL, PLAYER_CHARACTER_POINTS1,   0,              1 },
        { "loyalty",    'm', NULL,    "Loyalty",             NULL, UNIT_FIELD_POWER5,    UNIT_FIELD_MAXPOWER5, 1 },
        { "spirit",     'm', NULL,    "Spirit",              NULL, UNIT_FIELD_STAT0,           0,              1 },
        { "boundingraidus",'m',NULL,  "Bounding Radius",     NULL, UNIT_FIELD_BOUNDINGRADIUS,         0,              2 },
        { "combatreach",'m',NULL,     "Combat Reach",        NULL, UNIT_FIELD_COMBATREACH, 0, 2 },
        { "emotestate",'m', NULL,     "NPC Emote State",     NULL, UNIT_NPC_EMOTESTATE, 0, 1 },
        { NULL,          0, NULL,     "",                    NULL, 0, 0  }
    };

    static ChatCommand debugCommandTable[] =
    {
        { "infront",     'd', &ChatHandler::HandleDebugInFrontCommand,  "",                               NULL, 0, 0, 0},
        { "showreact",   'd', &ChatHandler::HandleShowReactionCommand,  "",                               NULL, 0, 0, 0},
        { "aimove",      'd', &ChatHandler::HandleAIMoveCommand,        "",                               NULL, 0, 0, 0},
        { "dist",        'd', &ChatHandler::HandleDistanceCommand,      "",                               NULL, 0, 0, 0},
        { "face",        'd', &ChatHandler::HandleFaceCommand,          "",                               NULL, 0, 0, 0},
        { "moveinfo",    'd', &ChatHandler::HandleMoveInfoCommand,      "",                               NULL, 0, 0, 0},
        { "setbytes",    'd', &ChatHandler::HandleSetBytesCommand,      "",                               NULL, 0, 0, 0},
        { "getbytes",    'd', &ChatHandler::HandleGetBytesCommand,      "",                               NULL, 0, 0, 0},
        { "unroot",      'd', &ChatHandler::HandleDebugUnroot,          "",                               NULL, 0, 0, 0},
        { "root",        'd', &ChatHandler::HandleDebugRoot,            "",                               NULL, 0, 0, 0},
        { "landwalk",    'd', &ChatHandler::HandleDebugLandWalk,        "",                               NULL, 0, 0, 0},
        { "waterwalk",   'd', &ChatHandler::HandleDebugWaterWalk,       "",                               NULL, 0, 0, 0},
        { "castspell",   'd', &ChatHandler::HandleCastSpellCommand,     ".castspell <spellid> - Casts spell on target.",  NULL, 0, 0, 0 },
        { "castspellne", 'd', &ChatHandler::HandleCastSpellNECommand,   ".castspellne <spellid> - Casts spell on target (only plays animations, doesnt handle effects or range/facing/etc.", NULL, 0, 0, 0 },
        { "celldelete",  'd', &ChatHandler::HandleCellDeleteCommand,    "!USE WITH CAUTION! '.celldelete YES' - Removes everything in current cell from game and database. '.celldelete YES YES' removes everything in a range of 1cell.", NULL, 0, 0, 0},
        { "addrestxp",   'd', &ChatHandler::HandleAddRestXPCommand,     ".addrestxp - Adds x rest XP to player.",         NULL, 0, 0, 0 },
        { "generatename",'d', &ChatHandler::HandleGenerateNameCommand,  ".generatename - Generates name for pet, etc.",   NULL, 0, 0, 0 },
        { "attackerinfo",'d', &ChatHandler::HandleAttackerInfoCommand,  ".attackerinfo - Shows selected mob/player's attacker's infomation.", NULL, 0, 0, 0 },
        { "showattackers",'d',&ChatHandler::HandleShowAttackersCommand, ".showattackers - Shows selected mob/player's attacker on the minimap.", NULL, 0, 0, 0 },
        { "aggrorange",  'd', &ChatHandler::HandleAggroRangeCommand,    ".aggrorange - Shows aggro Range of the selected Creature.", NULL, 0, 0, 0 },
        { "knockback ",  'd', &ChatHandler::HandleKnockBackCommand,     ".knockback <value> - Knocks you back.", NULL, 0, 0, 0 },
        { "fade ",       'd', &ChatHandler::HandleFadeCommand,          ".fade <value> - calls ModThreatModifyer().", NULL, 0, 0, 0 },
        { "threatMod ",  'd', &ChatHandler::HandleThreatModCommand,     ".threatMod <value> - calls ModGeneratedThreatModifyer().", NULL, 0, 0, 0 },
        { "calcThreat ", 'd', &ChatHandler::HandleCalcThreatCommand,    ".calcThreat <dmg> <spellId> - calculates threat.", NULL, 0, 0, 0 },
        { "threatList ", 'd', &ChatHandler::HandleThreatListCommand,    ".threatList  - returns all AI_Targets of the selected Creature.", NULL, 0, 0, 0 },
        { "gettptime",   'd', &ChatHandler::HandleGetTransporterTime,   "grabs transporter travel time",NULL, 0, 0, 0 },
        { "itempushresult",'d',&ChatHandler::HandleSendItemPushResult,  "sends item push result", NULL, 0, 0, 0 },
        { "weather",     'd', &ChatHandler::HandleWeatherCommand,       "",                               NULL, 0, 0, 0},
        { "setbit",      'd',  &ChatHandler::HandleModifyBitCommand,    "",                               NULL, 0, 0, 0},
        { "setvalue",    'd', &ChatHandler::HandleModifyValueCommand,   "",                               NULL, 0, 0, 0},
        { NULL,           0, NULL,                                      "",                               NULL, 0, 0  }
    };

    static ChatCommand waypointCommandTable[] =
    {
        { "add",         'w', &ChatHandler::HandleWPAddCommand,         "Add wp at current pos",          NULL, 0, 0, 0},
        { "show",        'w', &ChatHandler::HandleWPShowCommand,        "Show wp's for creature",         NULL, 0, 0, 0},
        { "hide",        'w', &ChatHandler::HandleWPHideCommand,        "Hide wp's for creature",         NULL, 0, 0, 0},
        { "delete",      'w', &ChatHandler::HandleWPDeleteCommand,      "Delete selected wp",             NULL, 0, 0, 0},
        { "movehere",    'w', &ChatHandler::HandleWPMoveHereCommand,    "Move to this wp",                NULL, 0, 0, 0},
        { "flags",       'w', &ChatHandler::HandleWPFlagsCommand,       "Wp flags",                       NULL, 0, 0, 0},
        { "waittime",    'w', &ChatHandler::HandleWPWaitCommand,        "Wait time at this wp",           NULL, 0, 0, 0},
        { "emote",       'w', &ChatHandler::HandleWPEmoteCommand,       "Emote at this wp",               NULL, 0, 0, 0},
        { "skin",        'w', &ChatHandler::HandleWPSkinCommand,        "Skin at this wp",                NULL, 0, 0, 0},
        { "change",      'w', &ChatHandler::HandleWPChangeNoCommand,    "Change at this wp",              NULL, 0, 0, 0},
        { "info",        'w', &ChatHandler::HandleWPInfoCommand,        "Show info for wp",               NULL, 0, 0, 0},
        { "movetype",    'w', &ChatHandler::HandleWPMoveTypeCommand,    "Movement type at wp",            NULL, 0, 0, 0},
        { NULL,            0, NULL,                                     "",                               NULL, 0, 0  }
    };

    static ChatCommand GMTicketCommandTable[] =
    {
        { "get",         'g', &ChatHandler::HandleGMTicketGetAllCommand,  "Gets GM Ticket",               NULL, 0, 0, 0},
        { "getId",       'g', &ChatHandler::HandleGMTicketGetByIdCommand, "Gets GM Ticket by ID",         NULL, 0, 0, 0},
        { "delId",       'g', &ChatHandler::HandleGMTicketDelByIdCommand, "Deletes GM Ticket by ID",      NULL, 0, 0, 0},
        { NULL,            2, NULL,                                       "",                             NULL, 0, 0  }
    };

    static ChatCommand GameObjectCommandTable[] =
    {
        { "select",      'o', &ChatHandler::HandleGOSelect,   "Selects the nearest GameObject to you",    NULL, 0, 0, 0},
        { "delete",      'o', &ChatHandler::HandleGODelete,   "Deletes selected GameObject",              NULL, 0, 0, 0},
        { "spawn",       'o', &ChatHandler::HandleGOSpawn,    "Spawns a GameObject by ID",                NULL, 0, 0, 0},
        { "info",        'o', &ChatHandler::HandleGOInfo,     "Gives you informations about selected GO", NULL, 0, 0, 0},
        { "activate",    'o', &ChatHandler::HandleGOActivate, "Activates/Opens the selected GO.",         NULL, 0, 0, 0},
        { "enable",      'o', &ChatHandler::HandleGOEnable,   "Enables the selected GO for use.",         NULL, 0, 0, 0},
        { "scale",       'o', &ChatHandler::HandleGOScale,    "Sets scale of selected GO",                NULL, 0, 0, 0},
        { "animprogress",'o', &ChatHandler::HandleGOAnimProgress, "Sets anim progress",                   NULL, 0, 0, 0 },
        { "export",      'o', &ChatHandler::HandleGOExport,   "Exports the current GO selected",          NULL, 0, 0, 0 },
        { NULL,            2, NULL,                           "",                                         NULL, 0, 0  }
    };

    static ChatCommand BattlegroundCommandTable[] = 
    {
        { "setbgscore",  'e', &ChatHandler::HandleSetBGScoreCommand,    "<Teamid> <Score> - Sets battleground score. 2 Arguments. ", NULL, 0, 0, 0},
        { "startbg",     'e', &ChatHandler::HandleStartBGCommand,       "Starts current battleground match.",  NULL, 0, 0, 0},
        { "pausebg",     'e', &ChatHandler::HandlePauseBGCommand,       "Pauses current battleground match.",  NULL, 0, 0, 0},
        { "bginfo",      'e', &ChatHandler::HandleBGInfoCommnad,        "Displays information about current battleground.", NULL, 0, 0, 0},
        { "battleground",'e', &ChatHandler::HandleBattlegroundCommand,  "Shows BG Menu",                       NULL, 0, 0, 0 },
        { "setworldstate",'e',&ChatHandler::HandleSetWorldStateCommand, "<var> <val> - Var can be in hex. WS Value.", NULL, 0, 0, 0 },
        { "playsound",   'e', &ChatHandler::HandlePlaySoundCommand,     "<val>. Val can be in hex.",           NULL, 0, 0, 0 },
        { "setbfstatus", 'e', &ChatHandler::HandleSetBattlefieldStatusCommand,".setbfstatus - NYI.",           NULL, 0, 0, 0 },
        { "leave",       'e', &ChatHandler::HandleBattlegroundExitCommand, "Leaves the current battleground.", NULL, 0, 0, 0 },
        { NULL,            2, NULL,                                     "",                                    NULL, 0, 0  }
    };

    static ChatCommand NPCCommandTable[] =
    {
        { "vendoradditem",   'n', &ChatHandler::HandleItemCommand,      "Adds to vendor",                 NULL, 0, 0, 0},
        { "vendorremoveitem",'n', &ChatHandler::HandleItemRemoveCommand,"Removes from vendor.",           NULL, 0, 0, 0},
        { "name",        'n', &ChatHandler::HandleNameCommand,          "Changes creature name",          NULL, 0, 0, 0},
        { "subname",     'n', &ChatHandler::HandleSubNameCommand,       "Changes creature subname",       NULL, 0, 0, 0},
        { "flags",       'n', &ChatHandler::HandleNPCFlagCommand,       "Changes NPC flags",              NULL, 0, 0, 0},
        { "emote",       'n', &ChatHandler::HandleEmoteCommand,         ".emote - Sets emote state",      NULL, 0, 0, 0 },
        { "run",         'n', &ChatHandler::HandleRunCommand,           "",                               NULL, 0, 0, 0},
        { "addweapon",   'n', &ChatHandler::HandleAddWeaponCommand,     "",                               NULL, 0, 0, 0},
        { "allowmove",   'n', &ChatHandler::HandleAllowMovementCommand, "",                               NULL, 0, 0, 0},
        { "addgrave",    'n', &ChatHandler::HandleAddGraveCommand,      "",                               NULL, 0, 0, 0},
        { "addsh",       'n', &ChatHandler::HandleAddSHCommand,         "",                               NULL, 0, 0, 0},
        { "addspirit",   'n', &ChatHandler::HandleAddSpiritCommand,     "",                               NULL, 0, 0, 0},
        //{ "spawn",       'n', &ChatHandler::HandleSpawnCommand,         "<entry> <flags> <faction> <level> <name>", NULL, 0, 0, 0},
        { "spawnentry",  'n', &ChatHandler::HandleSpawnEntryCommand,    "<entry>",                        NULL, 0, 0, 0},
        { "delete",      'n', &ChatHandler::HandleDeleteCommand,        "Deletes mob from db and world.", NULL, 0, 0, 0},
        { "info",        'n', &ChatHandler::HandleNpcInfoCommand,       "Displays NPC information",       NULL, 0, 0, 0},
        { "guid",        'n', &ChatHandler::HandleGUIDCommand,          "Shows selected object guid",     NULL, 0, 0, 0},
        { "addAgent",    'n', &ChatHandler::HandleAddAIAgentCommand,    ".npc addAgent <agent> <procEvent> <procChance> <procCount> <spellId> <spellType> <spelltargetType> <spellCooldown> <floatMisc1> <Misc2>",NULL, 0, 0, 0},
        { "delAgent",    'n', &ChatHandler::HandleDelAIAgentCommand,    ".npc delAgent <procEvent> <spellId>",NULL, 0, 0, 0},
        { "listAgent",   'n', &ChatHandler::HandleListAIAgentCommand,   ".npc listAgent",NULL, 0, 0, 0},
        { "reset",       'n', &ChatHandler::HandleResetHPCommand,       "resets npc health/dmg from temp table.", NULL, 0, 0, 0},
        { "export",      'n', &ChatHandler::HandleNpcExport,            "Exports the npc to a sql file",  NULL, 0, 0, 0},
        { "say",         'n', &ChatHandler::HandleMonsterSayCommand,    ".npc say <text> - Makes selected mob say text <text>.", NULL, 0, 0, 0 },
        { "yell",        'n', &ChatHandler::HandleMonsterYellCommand,   ".npc yell <Text> - Makes selected mob yell text <text>.", NULL, 0, 0, 0},
        { "come",        'n', &ChatHandler::HandleNpcComeCommand,       ".npc come - Makes npc move to your position", NULL, 0, 0, 0 },
        { "return",      'n', &ChatHandler::HandleNpcReturnCommand,     ".npc return - Returns ncp to spawnpoint.", NULL, 0, 0, 0 },
        { NULL,          2, NULL,                           "",                                           NULL, 0, 0  }
    };

    static ChatCommand CheatCommandTable[] =
    {
        { "status",     'm', &ChatHandler::HandleShowCheatsCommand, "Shows active cheats.",             NULL, 0, 0, 0 },
        { "taxi",       'm', &ChatHandler::HandleTaxiCheatCommand,     "Enables all taxi nodes.",       NULL, 0, 0, 0},
        { "cooldown",   'm', &ChatHandler::HandleCooldownCheatCommand, "Enables no cooldown cheat.",    NULL, 0, 0, 0 },
        { "casttime",   'm', &ChatHandler::HandleCastTimeCheatCommand, "Enables no cast time cheat.",   NULL, 0, 0, 0 },
        { "power",      'm', &ChatHandler::HandlePowerCheatCommand, "Disables mana consumption etc.",   NULL, 0, 0, 0 },
        { "god",        'm', &ChatHandler::HandleGodModeCommand, "Sets god mode, prevents you from taking damage.", NULL, 0, 0, 0 },
        { "fly",        'm', &ChatHandler::HandleFlyCommand, "Sets fly mode",                           NULL, 0, 0, 0 },
        { "land",       'm', &ChatHandler::HandleLandCommand, "Unsets fly mode",                        NULL, 0, 0, 0 },
        { "explore",    'm', &ChatHandler::HandleExploreCheatCommand, "Reveals the unexplored parts of the map.", NULL, 0, 0, 0 },
        { "flyspeed", 'm', &ChatHandler::HandleFlySpeedCheatCommand, "Modifies fly speed.", NULL, 0, 0, 0 },
        { "stack",      'm', &ChatHandler::HandleStackCheatCommand, "Enables aura stacking cheat.", NULL, 0, 0, 0 },
        { NULL,           0, NULL,                            "",                                       NULL, 0, 0, 0 },
    };

    static ChatCommand honorCommandTable[] =
    {
        { "getpvprank",  'm', &ChatHandler::HandleGetRankCommand,       "Gets PVP Rank",                               NULL, 0, 0, 0},
        { "setpvprank",  'm', &ChatHandler::HandleSetRankCommand,       "Sets PVP Rank",                               NULL, 0, 0, 0},
        { "addpoints",   'm', &ChatHandler::HandleAddHonorCommand,      "Adds x amount of honor points/currency",NULL,0,0,0},
        { "addkills",     'm', &ChatHandler::HandleAddKillCommand,       "Adds x amount of honor kills", NULL, 0, 0, 0 },
        { "globaldailyupdate", 'm', &ChatHandler::HandleGlobalHonorDailyMaintenanceCommand, "Daily honor field moves", NULL, 0, 0, 0},
        { "singledailyupdate", 'm', &ChatHandler::HandleNextDayCommand, "Daily honor field moves for selected player only", NULL,0,0,0},
        { "pvpcredit", 'm', &ChatHandler::HandlePVPCreditCommand, "Sends PVP credit packet, with specified rank and points", NULL,0,0,0},
        { NULL,0,NULL,"",NULL,0,0,0},
    };

    static ChatCommand petCommandTable[] = 
    {
        { "createpet",'m',&ChatHandler::HandleCreatePetCommand, "Creates a pet with <entry>.", NULL, 0, 0, 0 },
        { "renamepet",'m',&ChatHandler::HandleRenamePetCommand, "Renames a pet to <name>.", NULL, 0, 0, 0 },
        { "enablerename",'m',&ChatHandler::HandleEnableRenameCommand, "Enables pet rename.", NULL, 0, 0, 0 },
        { "addspell",'m',&ChatHandler::HandleAddPetSpellCommand, "Teaches pet <spell>.", NULL, 0, 0, 0 },
        { "removespell",'m',&ChatHandler::HandleRemovePetSpellCommand, "Removes pet spell <spell>.", NULL, 0, 0, 0 },
        { NULL,0,NULL,"",NULL,0,0,0},
    };

    static ChatCommand recallCommandTable[] =
    {
         { "list",        'q', &ChatHandler::HandleRecallListCommand,       "List recall locations",          NULL, 0, 0, 0},
         { "port",        'q', &ChatHandler::HandleRecallGoCommand,         "Port to recalled location",      NULL, 0, 0, 0},
         { "add",         'q', &ChatHandler::HandleRecallAddCommand,        "Add recall location",            NULL, 0, 0, 0},
         { "del",         'q', &ChatHandler::HandleRecallDelCommand,        "Remove a recall location",       NULL, 0, 0, 0},
         { NULL,           0,  NULL,                                        "",                               NULL, 0, 0, 0},
    };
    
    static ChatCommand commandTable[] = {
        { "commands",    1, &ChatHandler::HandleCommandsCommand,        "Shows Commands",                 NULL, 0, 0, 0},
        { "help",        1, &ChatHandler::HandleHelpCommand,            "Shows help for command",         NULL, 0, 0, 0},

        { "announce",    'u', &ChatHandler::HandleAnnounceCommand,      "Sends Msg To All",               NULL, 0, 0, 0},
        { "wannounce",   'u', &ChatHandler::HandleWAnnounceCommand,     "Sends Widescreen Msg To All",    NULL, 0, 0, 0},
        
        { "appear",      'v', &ChatHandler::HandleAppearCommand,        "Teleports to x's position.",     NULL, 0, 0, 0},
        { "summon",      'v', &ChatHandler::HandleSummonCommand,        "Summons x to your position",     NULL, 0, 0, 0},
        { "banchar",     'b', &ChatHandler::HandleBanCharacterCommand,  "Bans character x with or without reason",              NULL, 0, 0, 0},
        { "unbanchar",   'b', &ChatHandler::HandleUnBanCharacterCommand,"Unbans character x",             NULL, 0, 0, 0},
        { "banreason",   'b', &ChatHandler::HandleBanReasonCharacterCommand, "Shows the reason for ban",  NULL, 0, 0, 0},
        { "kick",        'b', &ChatHandler::HandleKickCommand,          "Kicks player from server",       NULL, 0, 0, 0},

        { "kill",        'r', &ChatHandler::HandleKillCommand,          ".kill - Kills selected unit.",   NULL, 0, 0, 0},
        { "revive",      'r', &ChatHandler::HandleReviveCommand,        "Revives you.",                   NULL, 0, 0, 0},
        { "reviveplr",   'r', &ChatHandler::HandleReviveStringcommand,  "Revives player specified.",      NULL, 0, 0, 0},

        { "morph",       'm', &ChatHandler::HandleMorphCommand,         "Morphs into model id x.",        NULL, 0, 0, 0},
        { "demorph",     'm', &ChatHandler::HandleDeMorphCommand,       "Demorphs from morphed model.",   NULL, 0, 0, 0},
        { "mount",       'm', &ChatHandler::HandleMountCommand,         "Mounts into modelid x.",         NULL, 0, 0, 0},
        { "dismount",      1, &ChatHandler::HandleDismountCommand,      "Dismounts.",                     NULL, 0, 0, 0},
        
        { "gm",          'p', &ChatHandler::HandleGMListCommand,        "Shows active GM's",              NULL, 0, 0, 0},
        { "gmoff",       't', &ChatHandler::HandleGMOffCommand,         "Sets GM tag off",                NULL, 0, 0, 0},
        { "gmon",        't', &ChatHandler::HandleGMOnCommand,          "Sets GM tag on",                 NULL, 0, 0, 0},
        
        { "gps",         'p', &ChatHandler::HandleGPSCommand,           "Shows Position",                 NULL, 0, 0, 0},
        { "info",        'p', &ChatHandler::HandleInfoCommand,          "Server info",                    NULL, 0, 0, 0},
        
        { "worldport",   'v', &ChatHandler::HandleWorldPortCommand,     "",                               NULL, 0, 0, 0},

        { "save",        's', &ChatHandler::HandleSaveCommand,          "Save's your character",          NULL, 0, 0, 0},
        { "saveall",     's', &ChatHandler::HandleSaveAllCommand,       "Save's all playing characters",  NULL, 0, 0, 0},
        { "security",    'z', &ChatHandler::HandleSecurityCommand,      "",                               NULL, 0, 0, 0},
        { "start",       'm', &ChatHandler::HandleStartCommand,         "Teleport's you to a starting location",                               NULL, 0, 0, 0},
        
        { "levelup",     'm', &ChatHandler::HandleLevelUpCommand,       "",                               NULL, 0, 0, 0},
        { "additem",     'm', &ChatHandler::HandleAddInvItemCommand,    "",                               NULL, 0, 0, 0},
        { "createguild", 'l', &ChatHandler::CreateGuildCommand,         "",                               NULL, 0, 0, 0},
       
        { "invincible",  'j', &ChatHandler::HandleInvincibleCommand,    ".invincible - Toggles INVINCIBILITY (mobs won't attack you)", NULL, 0, 0, 0},
        { "invisible",   'i', &ChatHandler::HandleInvisibleCommand,     ".invisible - Toggles INVINCIBILITY and INVISIBILITY (mobs won't attack you and nobody can see you, but they can see your chat messages)", NULL, 0, 0, 0},
        
        { "resetreputation", 'n',&ChatHandler::HandleResetReputationCommand, ".resetreputation - Resets reputation to start levels. (use on characters that were made before reputation fixes.)", NULL, 0, 0, 0},
        { "resetlevel",  'n', &ChatHandler::HandleResetLevelCommand,    ".resetlevel - Resets all stats to level 1 of targeted player. DANGEROUS.", NULL, 0, 0, 0 },
        { "resetspells", 'n', &ChatHandler::HandleResetSpellsCommand,   ".resetspells - Resets all spells to starting spells of targeted player. DANGEROUS.", NULL, 0, 0, 0 },
        { "resettalents",'n', &ChatHandler::HandleResetTalentsCommand,  ".resettalents - Resets all talents of targeted player to that of their current level. DANGEROUS.", NULL, 0, 0, 0 },
        { "resetskills", 'n', &ChatHandler::HandleResetSkillsCommand ,  ".resetskills - Resets all skills.", NULL, 0, 0, 0 },
        { "learn",       'm', &ChatHandler::HandleLearnCommand,         "Learns spell",                   NULL, 0, 0, 0},
        { "unlearn",     'm', &ChatHandler::HandleUnlearnCommand,       "Unlearns spell",                 NULL, 0, 0, 0},
        { "learnskill",  'm', &ChatHandler::HandleLearnSkillCommand,    ".learnskill <skillid> (optional) <value> <maxvalue> - Learns skill id skillid.", NULL, 0, 0, 0},
        { "advanceskill",'m', &ChatHandler::HandleModifySkillCommand,   "advanceskill <skillid> <amount, optional, default = 1> - Advances skill line x times..", NULL, 0, 0, 0},
        { "removeskill", 'm', &ChatHandler::HandleRemoveSkillCommand,   ".removeskill <skillid> - Removes skill",         NULL, 0, 0, 0 },
        { "increaseweaponskill", 'm', &ChatHandler::HandleIncreaseWeaponSkill, ".increaseweaponskill <count> - Increase eqipped weapon skill x times (defaults to 1).", NULL, 0, 0, 0},
        { "createaccount",'z',&ChatHandler::HandleCreateAccountCommand, ".createaccount - Creates account. Format should be .createaccount username password email", NULL, 0, 0, 0 },
        { "playerinfo",  'z', &ChatHandler::HandlePlayerInfo,           ".playerinfo - Displays informations about the selected character (account...)", NULL, 0, 0, 0 },

        { "uptime",        1, &ChatHandler::HandleUptimeCommand,        "Shows server uptime",            NULL, 0, 0, 0},

        { "modify",        'm', NULL,                                     "",                 modifyCommandTable, 0, 0, 0},
        { "waypoint",      'w', NULL,                                     "",               waypointCommandTable, 0, 0, 0},
        { "debug",         'd', NULL,                                     "",                  debugCommandTable, 0, 0, 0},
        { "gmTicket",      'g', NULL,                                     "",               GMTicketCommandTable, 0, 0, 0},
        { "gobject",       'o', NULL,                                     "",             GameObjectCommandTable, 0, 0, 0},
        { "battleground",  'e', NULL,                                     "",           BattlegroundCommandTable, 0, 0, 0},
        { "npc"         ,  'n', NULL,                                     "",                    NPCCommandTable, 0, 0, 0},
        { "cheat"       ,  'm', NULL,                                     "",                  CheatCommandTable, 0, 0, 0},
        { "honor"       ,  'm', NULL,                                     "",                  honorCommandTable, 0, 0, 0},
        { "pet",           'm', NULL,                                     "",                    petCommandTable, 0, 0, 0},
        { "recall",        'q', NULL,                                     "",                 recallCommandTable, 0, 0, 0},
        { "getpos"      ,  'd', &ChatHandler::HandleGetPosCommand,        "",                               NULL, 0, 0, 0},
        { "removeauras",   'm', &ChatHandler::HandleRemoveAurasCommand,   "Removes all auras from target",  NULL, 0, 0, 0},
        { "paralyze",      'b', &ChatHandler::HandleParalyzeCommand,      "Roots/Paralyzes the target.",    NULL, 0, 0, 0 },
        { "unparalyze",    'b', &ChatHandler::HandleUnParalyzeCommand,    "Unroots/Unparalyzes the target.",NULL, 0, 0, 0 },
        { "setmotd",       'm', &ChatHandler::HandleSetMotdCommand,       "Sets MOTD",                      NULL, 0, 0, 0 },
        { "additemset",    'm', &ChatHandler::HandleAddItemSetCommand,    "Adds item set to inv.",          NULL, 0, 0, 0 },
        { "gotrig",        'v', &ChatHandler::HandleTriggerCommand,       "Warps to areatrigger <id>",      NULL, 0, 0, 0 },
        { "createinstance",'m', &ChatHandler::HandleCreateInstanceCommand,"Creates instance on map <map>",  NULL, 0, 0, 0 },
        { "goinstance",    'm', &ChatHandler::HandleGoInstanceCommand,    "Joins instance <instance> <x> <y> <z> <optional mapid>", NULL, 0, 0, 0 },
        { "exitinstance",  'm', &ChatHandler::HandleExitInstanceCommand,  "Exits current instance, return to entry point.", NULL, 0, 0, 0 },
        { "dbreload",      'm', &ChatHandler::HandleDBReloadCommand,      "Reloads some of the database tables", NULL, 0, 0, 0 },
        { "spawnspiritguide",'m', &ChatHandler::HandleSpawnSpiritGuideCommand, "Spawns a spirit guide (params: 1 = horde, 0 = alliance", NULL, 0, 0, 0 },
        { "servershutdown", 'z', &ChatHandler::HandleShutdownCommand, "Initiates server shutdown in <x> seconds.", NULL, 0, 0, 0 },
        { "serverrestart", 'z', &ChatHandler::HandleShutdownRestartCommand, "Initiates server restart in <x> seconds.", NULL, 0, 0, 0 },
        { "allowwhispers", 'c', &ChatHandler::HandleAllowWhispersCommand, "Allows whispers from player <s> while in gmon mode.", NULL, 0, 0, 0 },
        { "blockwhispers", 'c', &ChatHandler::HandleBlockWhispersCommand, "Blocks whispers from player <s> while in gmon mode.", NULL, 0, 0, 0 },
        { "advanceallskills", 'm', &ChatHandler::HandleAdvanceAllSkillsCommand, "Advances all skills <x> points.", NULL, 0, 0, 0 },
        { "killbyplayer", 'f', &ChatHandler::HandleKillByPlayerCommand, "Disconnects the player with name <s>.", NULL, 0, 0, 0 },
        { "killbyaccount", 'f', &ChatHandler::HandleKillBySessionCommand, "Disconnects the session with account name <s>.", NULL, 0, 0, 0 },
        { "unlockmovement", 'm',&ChatHandler::HandleUnlockMovementCommand, "Unlocks movement for player.", NULL, 0, 0, 0},
        { "castall", 'z', &ChatHandler::HandleCastAllCommand, "Makes all players online cast spell <x>.", NULL, 0, 0, 0},
        { "getrate", 'f', &ChatHandler::HandleGetRateCommand, "Gets rate <x>.", NULL, 0, 0, 0 },
        { "setrate", 'f', &ChatHandler::HandleSetRateCommand, "Sets rate <x>.", NULL, 0, 0, 0 },
        { "modperiod" , 'm', &ChatHandler::HandleModPeriodCommand, "Changes period of current transporter.", NULL, 0, 0, 0 },
        { "npcfollow", 'm', &ChatHandler::HandleNpcFollowCommand, "Sets npc to follow you", NULL, 0, 0, 0 },
        { "nullfollow", 'm', &ChatHandler::HandleNullFollowCommand, "Sets npc to not follow anything", NULL, 0, 0, 0 },
        { "formationlink1", 'm', &ChatHandler::HandleFormationLink1Command, "Sets formation master.", NULL, 0, 0, 0 },
        { "formationlink2", 'm', &ChatHandler::HandleFormationLink2Command, "Sets formation slave with distance and angle", NULL, 0, 0, 0 },
        { "formationclear", 'm', &ChatHandler::HandleFormationClearCommand, "Removes formation from creature", NULL, 0, 0, 0 },
        { NULL,          0, NULL,                                         "",                               NULL, 0, 0  }
    };

    return commandTable;
}

bool ChatHandler::hasStringAbbr(const char* s1, const char* s2)
{
    for(;;)
    {
        if( !*s2 )
            return true;
        else if( !*s1 )
            return false;
        else if( tolower( *s1 ) != tolower( *s2 ) )
            return false;
        s1++; s2++;
    }
}

void ChatHandler::SendMultilineMessage(WorldSession *m_session, const char *str)
{
    char buf[256];
    const char* line = str;
    const char* pos = line;
    while((pos = strchr(line, '\n')) != NULL)
    {
        strncpy(buf, line, pos-line);
        buf[pos-line]=0;

        SystemMessage(m_session, buf);
        line = pos+1;
    }

    SystemMessage(m_session, line);
}

bool ChatHandler::ExecuteCommandInTable(ChatCommand *table, const char* text, WorldSession *m_session)
{
    std::string cmd = "";

    // get command
    while (*text != ' ' && *text != '\0')
    {
        cmd += *text;
        text++;
    }

    while (*text == ' ') text++; // skip whitespace

    if(!cmd.length())
        return false;

    for(uint32 i = 0; table[i].Name != NULL; i++)
    {
        if(!hasStringAbbr(table[i].Name, cmd.c_str()))
            continue;

        if(!m_session->CanUseCommand(table[i].CommandGroup))
            continue;

        if(table[i].ChildCommands != NULL)
        {
            if(!ExecuteCommandInTable(table[i].ChildCommands, text, m_session))
            {
                if(table[i].Help != "")
                    SendMultilineMessage(m_session, table[i].Help.c_str());
                else
                {
                    GreenSystemMessage(m_session, "Available Subcommands:");
                    for(uint32 k=0; table[i].ChildCommands[k].Name;k++)
                    {
                        if(m_session->CanUseCommand(table[i].ChildCommands[k].CommandGroup))
                            BlueSystemMessage(m_session, "    %s - %s", table[i].ChildCommands[k].Name, table[i].ChildCommands[k].Help.size() ? table[i].ChildCommands[k].Help.c_str() : "No Help Available");
                    }
                }
            }

            return true;
        }
        
        // Check for field-based commands
        if(table[i].Handler == NULL && (table[i].MaxValueField || table[i].NormalValueField))
        {
            bool result = false;
            if(strlen(text) == 0)
            {
                RedSystemMessage(m_session, "No values specified.");
            }
            if(table[i].ValueType == 2)
                result = CmdSetFloatField(m_session, table[i].NormalValueField, table[i].MaxValueField, table[i].Name, text);
            else
                result = CmdSetValueField(m_session, table[i].NormalValueField, table[i].MaxValueField, table[i].Name, text);
            if(!result)
                RedSystemMessage(m_session, "Must be in the form of (command) <value>, or, (command) <value> <maxvalue>");
        }
        else
        {
            if(!(this->*(table[i].Handler))(text, m_session))
            {
                if(table[i].Help != "")
                    SendMultilineMessage(m_session, table[i].Help.c_str());
                else
                {
                    RedSystemMessage(m_session, "Incorrect syntax specified. Try .help %s for the correct syntax.", table[i].Name);
                }
            }
        }

        return true;
    }

    return false;
}

int ChatHandler::ParseCommands(const char* text, WorldSession *session)
{
    if (!session)
        return 0;

    ASSERT(text);
    ASSERT(*text);

    if(session->GetPermissionCount() == 0)
        return 0;

    if(text[0] != '!' && text[0] != '.') // let's not confuse users
        return 0;

    text++;

    if(!ExecuteCommandInTable(getCommandTable(), text, session))
    {
        SystemMessage(session, "There is no such command, or you do not have access to it.");
    }

    return 1;
}

WorldPacket * ChatHandler::FillMessageData( uint32 type, uint32 language, const char *message,uint64 guid , uint8 flag) const
{
    //Packet structure
    //uint8      type;
    //uint32     language;
    //uint64     guid;
    //uint64     guid;
    //uint32      len_of_text;
    //char       text[];         // not sure ? i think is null terminated .. not null terminated
    //uint8      afk_state;
    ASSERT(type != CHAT_MSG_CHANNEL);
       //channels are handled in channel handler and so on
    uint32 messageLength = strlen((char*)message) + 1;

    WorldPacket *data = new WorldPacket(SMSG_MESSAGECHAT, messageLength + 30);
    data->Initialize(SMSG_MESSAGECHAT);
    *data << (uint8)type;
    *data << language;
    
    /*if (type == CHAT_MSG_CHANNEL)
    {
        ASSERT(channelName);
        *data << channelName;
    }*/

    *data << guid;

    // crashfix
    if (type == CHAT_MSG_SAY || type == CHAT_MSG_YELL || type == CHAT_MSG_PARTY || type == 0x53)
        *data << guid;

    *data << messageLength;
    *data << message;

    //*data << uint8(0);    // afk
    *data << uint8(flag);
    return data;
}

WorldPacket* ChatHandler::FillSystemMessageData(const char *message) const
{
    uint32 messageLength = strlen((char*)message) + 1;

    WorldPacket * data = new WorldPacket(SMSG_MESSAGECHAT, 20 + messageLength);

    data->Initialize(SMSG_MESSAGECHAT);
    *data << (uint8)CHAT_MSG_SYSTEM;
    *data << (uint32)LANG_UNIVERSAL;
    *data << (uint64)0; // Who cares about guid when there's no nickname displayed heh ?

    *data << messageLength;
    *data << message;

    *data << uint8(0);

    return data;
}

void ChatHandler::SpawnCreature(WorldSession *session, const char* name, uint32 displayId, uint32 npcFlags, uint32 factionId, uint32 level)
{
    // Create the requested monster
    Player *chr = session->GetPlayer();
    float x = chr->GetPositionX();
    float y = chr->GetPositionY();
    float z = chr->GetPositionZ();
    float o = chr->GetOrientation();

    Creature* pCreature = sObjHolder.Create<Creature>();

    pCreature->SetInstanceID(session->GetPlayer()->GetInstanceID());
    pCreature->Create(name, chr->GetMapId(), x, y, z, o);
    pCreature->SetZoneId(chr->GetZoneId());
    pCreature->SetUInt32Value(OBJECT_FIELD_ENTRY, objmgr.AddCreatureName(pCreature->GetName(), displayId));
    pCreature->SetFloatValue(OBJECT_FIELD_SCALE_X, 1.0f);
    pCreature->SetUInt32Value(UNIT_FIELD_DISPLAYID, displayId);
    pCreature->SetUInt32Value(UNIT_NPC_FLAGS , npcFlags);
    pCreature->SetUInt32Value(UNIT_FIELD_FACTIONTEMPLATE , factionId);
    pCreature->SetUInt32Value(UNIT_FIELD_HEALTH, 28 + 30*level);
    pCreature->SetUInt32Value(UNIT_FIELD_MAXHEALTH, 28 + 30*level);
    pCreature->SetUInt32Value(UNIT_FIELD_LEVEL , level);

    pCreature->SetFloatValue(UNIT_FIELD_COMBATREACH , 1.5f);
    pCreature->SetFloatValue(UNIT_FIELD_MAXDAMAGE ,  5.0f);
    pCreature->SetFloatValue(UNIT_FIELD_MINDAMAGE , 8.0f);
    pCreature->SetUInt32Value(UNIT_FIELD_BASEATTACKTIME, 1900);
    pCreature->SetUInt32Value(UNIT_FIELD_BASEATTACKTIME+1, 2000);
    pCreature->SetFloatValue(UNIT_FIELD_BOUNDINGRADIUS, 2.0f);
    //sLog.outError("AddObject at Chat.cpp");

    pCreature->_setFaction();

    pCreature->AddToWorld();
    CreatureTemplate *t = new CreatureTemplate;
    t->Create(pCreature);
    pCreature->GetMapMgr()->GetBaseMap()->GetTemplate()->AddIndex<Creature>(pCreature, t);

    pCreature->SaveToDB();
}

Player * ChatHandler::getSelectedChar(WorldSession *m_session, bool showerror)
{
    uint64 guid;
    Player *chr;
    
    guid = m_session->GetPlayer()->GetSelection();
    
    if (guid == 0)
    {
        if(showerror) 
            GreenSystemMessage(m_session, "Auto-targeting self.");
        chr = m_session->GetPlayer(); // autoselect
    }
    else
        chr = World::GetPlayer(guid);
    
    if(chr == NULL)
    {
        if(showerror) 
            RedSystemMessage(m_session, "This command requires that you select a player.");
        return NULL;
    }

    return chr;
}

Creature * ChatHandler::getSelectedCreature(WorldSession *m_session, bool showerror)
{
    uint64 guid;
    Creature *creature;

    guid = m_session->GetPlayer()->GetSelection();
    
    creature = World::GetCreature(guid);
    
    if(creature != NULL)
        return creature;
    else
    {
        if(showerror) 
            RedSystemMessage(m_session, "This command requires that you select a creature.");
        return NULL;
    }
}

void ChatHandler::SystemMessage(WorldSession *m_session, const char* message, ...)
{
    if( !message ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    WorldPacket * data = FillSystemMessageData(msg1);
    if(m_session != NULL) 
        m_session->SendPacket(data);
    delete data;
}

void ChatHandler::ColorSystemMessage(WorldSession *m_session, const char* colorcode, const char *message, ...)
{
    if( !message ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    char msg[1024];
    sprintf(msg, "%s%s|r", colorcode, msg1);
    WorldPacket * data = FillSystemMessageData(msg);
    if(m_session != NULL) 
        m_session->SendPacket(data);
    delete data;
}

void ChatHandler::RedSystemMessage(WorldSession *m_session, const char *message, ...)
{
    if( !message ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    char msg[1024];
    sprintf(msg, "%s%s|r", MSG_COLOR_LIGHTRED/*MSG_COLOR_RED*/, msg1);
    WorldPacket * data = FillSystemMessageData(msg);
    if(m_session != NULL) 
        m_session->SendPacket(data);
    delete data;
}

void ChatHandler::GreenSystemMessage(WorldSession *m_session, const char *message, ...)
{
    if( !message ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    char msg[1024];
    sprintf(msg, "%s%s|r", MSG_COLOR_GREEN, msg1);
    WorldPacket * data = FillSystemMessageData(msg);
    if(m_session != NULL) 
        m_session->SendPacket(data);
    delete data;
}

void ChatHandler::BlueSystemMessage(WorldSession *m_session, const char *message, ...)
{
    if( !message ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    char msg[1024];
    sprintf(msg, "%s%s|r", MSG_COLOR_LIGHTBLUE, msg1);
    WorldPacket * data = FillSystemMessageData(msg);
    if(m_session != NULL) 
        m_session->SendPacket(data);
    delete data;
}

void ChatHandler::RedSystemMessageToPlr(Player* plr, const char *message, ...)
{
    if( !message || !plr->GetSession() ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    RedSystemMessage(plr->GetSession(), (const char*)msg1);
}

void ChatHandler::GreenSystemMessageToPlr(Player* plr, const char *message, ...)
{
    if( !message || !plr->GetSession() ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    GreenSystemMessage(plr->GetSession(), (const char*)msg1);
}

void ChatHandler::BlueSystemMessageToPlr(Player* plr, const char *message, ...)
{
    if( !message || !plr->GetSession() ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    BlueSystemMessage(plr->GetSession(), (const char*)msg1);
}

void ChatHandler::SystemMessageToPlr(Player *plr, const char* message, ...)
{
    if( !message || !plr->GetSession() ) return;
    va_list ap;
    va_start(ap, message);
    char msg1[1024];
    vsprintf(msg1,message,ap);
    SystemMessage(plr->GetSession(), msg1);
}

bool ChatHandler::CmdSetValueField(WorldSession *m_session, uint32 field, uint32 fieldmax, const char *fieldname, const char *args)
{
    if(!args) return false;
    char* pvalue = strtok((char*)args, " ");
    uint32 mv, av;

    if (!pvalue)
        return false;
    else
        av = atol(pvalue);

    if(fieldmax)
    {
        char* pvaluemax = strtok(NULL, " ");   
        if (!pvaluemax)
            return false;  
        else
            mv = atol(pvaluemax);
    }
    else
    {
        mv = 0;
    }

    if (av <= 0 && mv > 0)
    {  
        RedSystemMessage(m_session, "Values are invalid. Value must be < max (if max exists), and both must be > 0.");
        return true;   
    }
    if(fieldmax)
    {
        if(mv < av || mv <= 0)
        {
            RedSystemMessage(m_session, "Values are invalid. Value must be < max (if max exists), and both must be > 0.");
            return true;  
        }
    }

    Player *plr = getSelectedChar(m_session, false);
    if(plr)
    {  
        sGMLog.writefromsession(m_session, "used modify field value: %s, %u on %s", fieldname, av, plr->GetName());
        if(fieldmax)
        {
            BlueSystemMessage(m_session, "You set the %s of %s to %d/%d.", fieldname, plr->GetName(), av, mv);
            GreenSystemMessageToPlr(plr, "%s set your %s to %d/%d.", m_session->GetPlayer()->GetName(), fieldname, av, mv);
        }
        else
        {
            BlueSystemMessage(m_session, "You set the %s of %s to %d.", fieldname, plr->GetName(), av);
            GreenSystemMessageToPlr(plr, "%s set your %s to %d.", m_session->GetPlayer()->GetName(), fieldname, av);
        }

        if(field == UNIT_FIELD_STAT1) av /= 2;
        if(field == UNIT_FIELD_BASE_HEALTH) 
        {
            plr->SetUInt32Value(UNIT_FIELD_HEALTH, av);
            plr->SetBaseUInt32Value(UNIT_FIELD_HEALTH,av);
        }

        plr->SetUInt32Value(field, av);
        plr->SetBaseUInt32Value(field,av);

        if(fieldmax) {
            plr->SetUInt32Value(fieldmax, mv);
            plr->SetBaseUInt32Value(fieldmax,mv);
        }
    }
    else
    {
        Creature *cr = getSelectedCreature(m_session, false);
        if(cr)
        {
            if(!(field < UNIT_END && fieldmax < UNIT_END)) return false;
            std::string creaturename = "Unknown Being";
            if(cr->GetCreatureName())
                creaturename = cr->GetCreatureName()->Name;
            if(fieldmax)
                BlueSystemMessage(m_session, "Setting %s of %s to %d/%d.", fieldname, creaturename.c_str(), av, mv);
            else
                BlueSystemMessage(m_session, "Setting %s of %s to %d.", fieldname, creaturename.c_str(), av);
            sGMLog.writefromsession(m_session, "used modify field value: [creature]%s, %u on %s", fieldname, av, creaturename.c_str());
            if(field == UNIT_FIELD_STAT1) av /= 2;
            if(field == UNIT_FIELD_BASE_HEALTH) 
            {
                cr->SetUInt32Value(UNIT_FIELD_HEALTH, av);
                cr->SetBaseUInt32Value(UNIT_FIELD_HEALTH,av);
            }

            cr->SetUInt32Value(field, av);
            cr->SetBaseUInt32Value(field,av);

            if(fieldmax) {
                cr->SetUInt32Value(fieldmax, mv);
                cr->SetBaseUInt32Value(fieldmax,mv);
            }
            // reset faction
            if(field == UNIT_FIELD_FACTIONTEMPLATE)
                cr->_setFaction();

            cr->SaveToDB();
        }
        else
        {
            RedSystemMessage(m_session, "Invalid Selection.");
        }
    }
    return true;
}

bool ChatHandler::CmdSetFloatField(WorldSession *m_session, uint32 field, uint32 fieldmax, const char *fieldname, const char *args)
{
    char* pvalue = strtok((char*)args, " ");
    float mv, av;

    if (!pvalue)
        return false;
    else
        av = (float)atof(pvalue);

    if(fieldmax)
    {
        char* pvaluemax = strtok(NULL, " ");   
        if (!pvaluemax)
            return false;  
        else
            mv = (float)atof(pvaluemax);
    }
    else
    {
        mv = 0;
    }

    if (av <= 0)
    {  
        RedSystemMessage(m_session, "Values are invalid. Value must be < max (if max exists), and both must be > 0.");
        return true;   
    }
    if(fieldmax)
    {
        if(mv < av || mv <= 0)
        {
            RedSystemMessage(m_session, "Values are invalid. Value must be < max (if max exists), and both must be > 0.");
            return true;  
        }
    }

    Player *plr = getSelectedChar(m_session, false);
    if(plr)
    {  
        sGMLog.writefromsession(m_session, "used modify field value: %s, %f on %s", fieldname, av, plr->GetName());
        if(fieldmax)
        {
            BlueSystemMessage(m_session, "You set the %s of %s to %.1f/%.1f.", fieldname, plr->GetName(), av, mv);
            GreenSystemMessageToPlr(plr, "%s set your %s to %.1f/%.1f.", m_session->GetPlayer()->GetName(), fieldname, av, mv);
        }
        else
        {
            BlueSystemMessage(m_session, "You set the %s of %s to %.1f.", fieldname, plr->GetName(), av);
            GreenSystemMessageToPlr(plr, "%s set your %s to %.1f.", m_session->GetPlayer()->GetName(), fieldname, av);
        }
        plr->SetFloatValue(field, av);
        if(fieldmax) plr->SetFloatValue(fieldmax, mv);
    }
    else
    {
        Creature *cr = getSelectedCreature(m_session, false);
        if(cr)
        {
            if(!(field < UNIT_END && fieldmax < UNIT_END)) return false;
            std::string creaturename = "Unknown Being";
            if(cr->GetCreatureName())
                creaturename = cr->GetCreatureName()->Name;
            if(fieldmax)
                BlueSystemMessage(m_session, "Setting %s of %s to %.1f/%.1f.", fieldname, creaturename.c_str(), av, mv);
            else
                BlueSystemMessage(m_session, "Setting %s of %s to %.1f.", fieldname, creaturename.c_str(), av);
            cr->SetFloatValue(field, av);
            cr->SetBaseFloatValue(field,mv);
            sGMLog.writefromsession(m_session, "used modify field value: [creature]%s, %f on %s", fieldname, av, creaturename.c_str());
            if(fieldmax) {
                cr->SetFloatValue(fieldmax, mv);
                cr->SetBaseFloatValue(fieldmax,mv);
            }
            //cr->SaveToDB();
        }
        else
        {
            RedSystemMessage(m_session, "Invalid Selection.");
        }
    }
    return true;
}

bool ChatHandler::HandleGetPosCommand(const char* args, WorldSession *m_session)
{
    /*if(m_session->GetPlayer()->GetSelection() == 0) return false;
    Creature *creature = objmgr.GetCreature(m_session->GetPlayer()->GetSelection());

    if(!creature) return false;
    BlueSystemMessage(m_session, "Creature Position: \nX: %f\nY: %f\nZ: %f\n", creature->GetPositionX(), creature->GetPositionY(), creature->GetPositionZ());
    return true;*/

    uint32 spell = atol(args);
    SpellEntry *se = sSpellStore.LookupEntry(spell);
    if(se)
        BlueSystemMessage(m_session, "SpellIcon for %d is %d", se->Id, se->field114);
    return true;
}


