[7297] Fixed profession spells sorting in trainer spell list at client.
[getmangos.git] / src / game / Level3.cpp
blob70b25ab1c3aca74a8ffcc3de4d1271ba466881fc
1 /*
2 * Copyright (C) 2005-2009 MaNGOS <http://getmangos.com/>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 #include "Common.h"
20 #include "Database/DatabaseEnv.h"
21 #include "WorldPacket.h"
22 #include "WorldSession.h"
23 #include "World.h"
24 #include "ObjectMgr.h"
25 #include "AccountMgr.h"
26 #include "PlayerDump.h"
27 #include "SpellMgr.h"
28 #include "Player.h"
29 #include "Opcodes.h"
30 #include "GameObject.h"
31 #include "Chat.h"
32 #include "Log.h"
33 #include "Guild.h"
34 #include "ObjectAccessor.h"
35 #include "MapManager.h"
36 #include "SpellAuras.h"
37 #include "ScriptCalls.h"
38 #include "Language.h"
39 #include "GridNotifiersImpl.h"
40 #include "CellImpl.h"
41 #include "Weather.h"
42 #include "PointMovementGenerator.h"
43 #include "TargetedMovementGenerator.h"
44 #include "SkillDiscovery.h"
45 #include "SkillExtraItems.h"
46 #include "SystemConfig.h"
47 #include "Config/ConfigEnv.h"
48 #include "Util.h"
49 #include "ItemEnchantmentMgr.h"
50 #include "BattleGroundMgr.h"
51 #include "InstanceSaveMgr.h"
52 #include "InstanceData.h"
54 //reload commands
55 bool ChatHandler::HandleReloadAllCommand(const char*)
57 HandleReloadSkillFishingBaseLevelCommand("");
59 HandleReloadAllAreaCommand("");
60 HandleReloadAllLootCommand("");
61 HandleReloadAllNpcCommand("");
62 HandleReloadAllQuestCommand("");
63 HandleReloadAllSpellCommand("");
64 HandleReloadAllItemCommand("");
65 HandleReloadAllLocalesCommand("");
67 HandleReloadCommandCommand("");
68 HandleReloadReservedNameCommand("");
69 HandleReloadMangosStringCommand("");
70 HandleReloadGameTeleCommand("");
71 return true;
74 bool ChatHandler::HandleReloadAllAreaCommand(const char*)
76 //HandleReloadQuestAreaTriggersCommand(""); -- reloaded in HandleReloadAllQuestCommand
77 HandleReloadAreaTriggerTeleportCommand("");
78 HandleReloadAreaTriggerTavernCommand("");
79 HandleReloadGameGraveyardZoneCommand("");
80 return true;
83 bool ChatHandler::HandleReloadAllLootCommand(const char*)
85 sLog.outString( "Re-Loading Loot Tables..." );
86 LoadLootTables();
87 SendGlobalSysMessage("DB tables `*_loot_template` reloaded.");
88 return true;
91 bool ChatHandler::HandleReloadAllNpcCommand(const char* /*args*/)
93 HandleReloadNpcGossipCommand("a");
94 HandleReloadNpcOptionCommand("a");
95 HandleReloadNpcTrainerCommand("a");
96 HandleReloadNpcVendorCommand("a");
97 HandleReloadPointsOfInterestCommand("a");
98 return true;
101 bool ChatHandler::HandleReloadAllQuestCommand(const char* /*args*/)
103 HandleReloadQuestAreaTriggersCommand("a");
104 HandleReloadQuestTemplateCommand("a");
106 sLog.outString( "Re-Loading Quests Relations..." );
107 objmgr.LoadQuestRelations();
108 SendGlobalSysMessage("DB tables `*_questrelation` and `*_involvedrelation` reloaded.");
109 return true;
112 bool ChatHandler::HandleReloadAllScriptsCommand(const char*)
114 if(sWorld.IsScriptScheduled())
116 PSendSysMessage("DB scripts used currently, please attempt reload later.");
117 SetSentErrorMessage(true);
118 return false;
121 sLog.outString( "Re-Loading Scripts..." );
122 HandleReloadGameObjectScriptsCommand("a");
123 HandleReloadEventScriptsCommand("a");
124 HandleReloadQuestEndScriptsCommand("a");
125 HandleReloadQuestStartScriptsCommand("a");
126 HandleReloadSpellScriptsCommand("a");
127 SendGlobalSysMessage("DB tables `*_scripts` reloaded.");
128 HandleReloadDbScriptStringCommand("a");
129 return true;
132 bool ChatHandler::HandleReloadAllSpellCommand(const char*)
134 HandleReloadSkillDiscoveryTemplateCommand("a");
135 HandleReloadSkillExtraItemTemplateCommand("a");
136 HandleReloadSpellAffectCommand("a");
137 HandleReloadSpellChainCommand("a");
138 HandleReloadSpellElixirCommand("a");
139 HandleReloadSpellLearnSpellCommand("a");
140 HandleReloadSpellProcEventCommand("a");
141 HandleReloadSpellBonusesCommand("a");
142 HandleReloadSpellScriptTargetCommand("a");
143 HandleReloadSpellTargetPositionCommand("a");
144 HandleReloadSpellThreatsCommand("a");
145 HandleReloadSpellPetAurasCommand("a");
146 return true;
149 bool ChatHandler::HandleReloadAllItemCommand(const char*)
151 HandleReloadPageTextsCommand("a");
152 HandleReloadItemEnchantementsCommand("a");
153 return true;
156 bool ChatHandler::HandleReloadAllLocalesCommand(const char* /*args*/)
158 HandleReloadLocalesCreatureCommand("a");
159 HandleReloadLocalesGameobjectCommand("a");
160 HandleReloadLocalesItemCommand("a");
161 HandleReloadLocalesNpcTextCommand("a");
162 HandleReloadLocalesPageTextCommand("a");
163 HandleReloadLocalesPointsOfInterestCommand("a");
164 HandleReloadLocalesQuestCommand("a");
165 return true;
168 bool ChatHandler::HandleReloadConfigCommand(const char* /*args*/)
170 sLog.outString( "Re-Loading config settings..." );
171 sWorld.LoadConfigSettings(true);
172 SendGlobalSysMessage("World config settings reloaded.");
173 return true;
176 bool ChatHandler::HandleReloadAreaTriggerTavernCommand(const char*)
178 sLog.outString( "Re-Loading Tavern Area Triggers..." );
179 objmgr.LoadTavernAreaTriggers();
180 SendGlobalSysMessage("DB table `areatrigger_tavern` reloaded.");
181 return true;
184 bool ChatHandler::HandleReloadAreaTriggerTeleportCommand(const char*)
186 sLog.outString( "Re-Loading AreaTrigger teleport definitions..." );
187 objmgr.LoadAreaTriggerTeleports();
188 SendGlobalSysMessage("DB table `areatrigger_teleport` reloaded.");
189 return true;
192 bool ChatHandler::HandleReloadCommandCommand(const char*)
194 load_command_table = true;
195 SendGlobalSysMessage("DB table `command` will be reloaded at next chat command use.");
196 return true;
199 bool ChatHandler::HandleReloadCreatureQuestRelationsCommand(const char*)
201 sLog.outString( "Loading Quests Relations... (`creature_questrelation`)" );
202 objmgr.LoadCreatureQuestRelations();
203 SendGlobalSysMessage("DB table `creature_questrelation` (creature quest givers) reloaded.");
204 return true;
207 bool ChatHandler::HandleReloadCreatureQuestInvRelationsCommand(const char*)
209 sLog.outString( "Loading Quests Relations... (`creature_involvedrelation`)" );
210 objmgr.LoadCreatureInvolvedRelations();
211 SendGlobalSysMessage("DB table `creature_involvedrelation` (creature quest takers) reloaded.");
212 return true;
215 bool ChatHandler::HandleReloadGOQuestRelationsCommand(const char*)
217 sLog.outString( "Loading Quests Relations... (`gameobject_questrelation`)" );
218 objmgr.LoadGameobjectQuestRelations();
219 SendGlobalSysMessage("DB table `gameobject_questrelation` (gameobject quest givers) reloaded.");
220 return true;
223 bool ChatHandler::HandleReloadGOQuestInvRelationsCommand(const char*)
225 sLog.outString( "Loading Quests Relations... (`gameobject_involvedrelation`)" );
226 objmgr.LoadGameobjectInvolvedRelations();
227 SendGlobalSysMessage("DB table `gameobject_involvedrelation` (gameobject quest takers) reloaded.");
228 return true;
231 bool ChatHandler::HandleReloadQuestAreaTriggersCommand(const char*)
233 sLog.outString( "Re-Loading Quest Area Triggers..." );
234 objmgr.LoadQuestAreaTriggers();
235 SendGlobalSysMessage("DB table `areatrigger_involvedrelation` (quest area triggers) reloaded.");
236 return true;
239 bool ChatHandler::HandleReloadQuestTemplateCommand(const char*)
241 sLog.outString( "Re-Loading Quest Templates..." );
242 objmgr.LoadQuests();
243 SendGlobalSysMessage("DB table `quest_template` (quest definitions) reloaded.");
245 /// dependent also from `gameobject` but this table not reloaded anyway
246 sLog.outString( "Re-Loading GameObjects for quests..." );
247 objmgr.LoadGameObjectForQuests();
248 SendGlobalSysMessage("Data GameObjects for quests reloaded.");
249 return true;
252 bool ChatHandler::HandleReloadLootTemplatesCreatureCommand(const char*)
254 sLog.outString( "Re-Loading Loot Tables... (`creature_loot_template`)" );
255 LoadLootTemplates_Creature();
256 LootTemplates_Creature.CheckLootRefs();
257 SendGlobalSysMessage("DB table `creature_loot_template` reloaded.");
258 return true;
261 bool ChatHandler::HandleReloadLootTemplatesDisenchantCommand(const char*)
263 sLog.outString( "Re-Loading Loot Tables... (`disenchant_loot_template`)" );
264 LoadLootTemplates_Disenchant();
265 LootTemplates_Disenchant.CheckLootRefs();
266 SendGlobalSysMessage("DB table `disenchant_loot_template` reloaded.");
267 return true;
270 bool ChatHandler::HandleReloadLootTemplatesFishingCommand(const char*)
272 sLog.outString( "Re-Loading Loot Tables... (`fishing_loot_template`)" );
273 LoadLootTemplates_Fishing();
274 LootTemplates_Fishing.CheckLootRefs();
275 SendGlobalSysMessage("DB table `fishing_loot_template` reloaded.");
276 return true;
279 bool ChatHandler::HandleReloadLootTemplatesGameobjectCommand(const char*)
281 sLog.outString( "Re-Loading Loot Tables... (`gameobject_loot_template`)" );
282 LoadLootTemplates_Gameobject();
283 LootTemplates_Gameobject.CheckLootRefs();
284 SendGlobalSysMessage("DB table `gameobject_loot_template` reloaded.");
285 return true;
288 bool ChatHandler::HandleReloadLootTemplatesItemCommand(const char*)
290 sLog.outString( "Re-Loading Loot Tables... (`item_loot_template`)" );
291 LoadLootTemplates_Item();
292 LootTemplates_Item.CheckLootRefs();
293 SendGlobalSysMessage("DB table `item_loot_template` reloaded.");
294 return true;
297 bool ChatHandler::HandleReloadLootTemplatesMillingCommand(const char*)
299 sLog.outString( "Re-Loading Loot Tables... (`milling_loot_template`)" );
300 LoadLootTemplates_Milling();
301 LootTemplates_Milling.CheckLootRefs();
302 SendGlobalSysMessage("DB table `milling_loot_template` reloaded.");
303 return true;
306 bool ChatHandler::HandleReloadLootTemplatesPickpocketingCommand(const char*)
308 sLog.outString( "Re-Loading Loot Tables... (`pickpocketing_loot_template`)" );
309 LoadLootTemplates_Pickpocketing();
310 LootTemplates_Pickpocketing.CheckLootRefs();
311 SendGlobalSysMessage("DB table `pickpocketing_loot_template` reloaded.");
312 return true;
315 bool ChatHandler::HandleReloadLootTemplatesProspectingCommand(const char*)
317 sLog.outString( "Re-Loading Loot Tables... (`prospecting_loot_template`)" );
318 LoadLootTemplates_Prospecting();
319 LootTemplates_Prospecting.CheckLootRefs();
320 SendGlobalSysMessage("DB table `prospecting_loot_template` reloaded.");
321 return true;
324 bool ChatHandler::HandleReloadLootTemplatesQuestMailCommand(const char*)
326 sLog.outString( "Re-Loading Loot Tables... (`quest_mail_loot_template`)" );
327 LoadLootTemplates_QuestMail();
328 LootTemplates_QuestMail.CheckLootRefs();
329 SendGlobalSysMessage("DB table `quest_mail_loot_template` reloaded.");
330 return true;
333 bool ChatHandler::HandleReloadLootTemplatesReferenceCommand(const char*)
335 sLog.outString( "Re-Loading Loot Tables... (`reference_loot_template`)" );
336 LoadLootTemplates_Reference();
337 SendGlobalSysMessage("DB table `reference_loot_template` reloaded.");
338 return true;
341 bool ChatHandler::HandleReloadLootTemplatesSkinningCommand(const char*)
343 sLog.outString( "Re-Loading Loot Tables... (`skinning_loot_template`)" );
344 LoadLootTemplates_Skinning();
345 LootTemplates_Skinning.CheckLootRefs();
346 SendGlobalSysMessage("DB table `skinning_loot_template` reloaded.");
347 return true;
350 bool ChatHandler::HandleReloadLootTemplatesSpellCommand(const char*)
352 sLog.outString( "Re-Loading Loot Tables... (`spell_loot_template`)" );
353 LoadLootTemplates_Spell();
354 LootTemplates_Spell.CheckLootRefs();
355 SendGlobalSysMessage("DB table `spell_loot_template` reloaded.");
356 return true;
359 bool ChatHandler::HandleReloadMangosStringCommand(const char*)
361 sLog.outString( "Re-Loading mangos_string Table!" );
362 objmgr.LoadMangosStrings();
363 SendGlobalSysMessage("DB table `mangos_string` reloaded.");
364 return true;
367 bool ChatHandler::HandleReloadNpcOptionCommand(const char*)
369 sLog.outString( "Re-Loading `npc_option` Table!" );
370 objmgr.LoadNpcOptions();
371 SendGlobalSysMessage("DB table `npc_option` reloaded.");
372 return true;
375 bool ChatHandler::HandleReloadNpcGossipCommand(const char*)
377 sLog.outString( "Re-Loading `npc_gossip` Table!" );
378 objmgr.LoadNpcTextId();
379 SendGlobalSysMessage("DB table `npc_gossip` reloaded.");
380 return true;
383 bool ChatHandler::HandleReloadNpcTrainerCommand(const char*)
385 sLog.outString( "Re-Loading `npc_trainer` Table!" );
386 objmgr.LoadTrainerSpell();
387 SendGlobalSysMessage("DB table `npc_trainer` reloaded.");
388 return true;
391 bool ChatHandler::HandleReloadNpcVendorCommand(const char*)
393 sLog.outString( "Re-Loading `npc_vendor` Table!" );
394 objmgr.LoadVendors();
395 SendGlobalSysMessage("DB table `npc_vendor` reloaded.");
396 return true;
399 bool ChatHandler::HandleReloadPointsOfInterestCommand(const char*)
401 sLog.outString( "Re-Loading `points_of_interest` Table!" );
402 objmgr.LoadPointsOfInterest();
403 SendGlobalSysMessage("DB table `points_of_interest` reloaded.");
404 return true;
407 bool ChatHandler::HandleReloadReservedNameCommand(const char*)
409 sLog.outString( "Loading ReservedNames... (`reserved_name`)" );
410 objmgr.LoadReservedPlayersNames();
411 SendGlobalSysMessage("DB table `reserved_name` (player reserved names) reloaded.");
412 return true;
415 bool ChatHandler::HandleReloadSkillDiscoveryTemplateCommand(const char* /*args*/)
417 sLog.outString( "Re-Loading Skill Discovery Table..." );
418 LoadSkillDiscoveryTable();
419 SendGlobalSysMessage("DB table `skill_discovery_template` (recipes discovered at crafting) reloaded.");
420 return true;
423 bool ChatHandler::HandleReloadSkillExtraItemTemplateCommand(const char* /*args*/)
425 sLog.outString( "Re-Loading Skill Extra Item Table..." );
426 LoadSkillExtraItemTable();
427 SendGlobalSysMessage("DB table `skill_extra_item_template` (extra item creation when crafting) reloaded.");
428 return true;
431 bool ChatHandler::HandleReloadSkillFishingBaseLevelCommand(const char* /*args*/)
433 sLog.outString( "Re-Loading Skill Fishing base level requirements..." );
434 objmgr.LoadFishingBaseSkillLevel();
435 SendGlobalSysMessage("DB table `skill_fishing_base_level` (fishing base level for zone/subzone) reloaded.");
436 return true;
439 bool ChatHandler::HandleReloadSpellAffectCommand(const char*)
441 sLog.outString( "Re-Loading SpellAffect definitions..." );
442 spellmgr.LoadSpellAffects();
443 SendGlobalSysMessage("DB table `spell_affect` (spell mods apply requirements) reloaded.");
444 return true;
447 bool ChatHandler::HandleReloadSpellChainCommand(const char*)
449 sLog.outString( "Re-Loading Spell Chain Data... " );
450 spellmgr.LoadSpellChains();
451 SendGlobalSysMessage("DB table `spell_chain` (spell ranks) reloaded.");
452 return true;
455 bool ChatHandler::HandleReloadSpellElixirCommand(const char*)
457 sLog.outString( "Re-Loading Spell Elixir types..." );
458 spellmgr.LoadSpellElixirs();
459 SendGlobalSysMessage("DB table `spell_elixir` (spell elixir types) reloaded.");
460 return true;
463 bool ChatHandler::HandleReloadSpellLearnSpellCommand(const char*)
465 sLog.outString( "Re-Loading Spell Learn Spells..." );
466 spellmgr.LoadSpellLearnSpells();
467 SendGlobalSysMessage("DB table `spell_learn_spell` reloaded.");
468 return true;
471 bool ChatHandler::HandleReloadSpellProcEventCommand(const char*)
473 sLog.outString( "Re-Loading Spell Proc Event conditions..." );
474 spellmgr.LoadSpellProcEvents();
475 SendGlobalSysMessage("DB table `spell_proc_event` (spell proc trigger requirements) reloaded.");
476 return true;
479 bool ChatHandler::HandleReloadSpellBonusesCommand(const char*)
481 sLog.outString( "Re-Loading Spell Bonus Data..." );
482 spellmgr.LoadSpellBonusess();
483 SendGlobalSysMessage("DB table `spell_bonus_data` (spell damage/healing coefficients) reloaded.");
484 return true;
487 bool ChatHandler::HandleReloadSpellScriptTargetCommand(const char*)
489 sLog.outString( "Re-Loading SpellsScriptTarget..." );
490 spellmgr.LoadSpellScriptTarget();
491 SendGlobalSysMessage("DB table `spell_script_target` (spell targets selection in case specific creature/GO requirements) reloaded.");
492 return true;
495 bool ChatHandler::HandleReloadSpellTargetPositionCommand(const char*)
497 sLog.outString( "Re-Loading Spell target coordinates..." );
498 spellmgr.LoadSpellTargetPositions();
499 SendGlobalSysMessage("DB table `spell_target_position` (destination coordinates for spell targets) reloaded.");
500 return true;
503 bool ChatHandler::HandleReloadSpellThreatsCommand(const char*)
505 sLog.outString( "Re-Loading Aggro Spells Definitions...");
506 spellmgr.LoadSpellThreats();
507 SendGlobalSysMessage("DB table `spell_threat` (spell aggro definitions) reloaded.");
508 return true;
511 bool ChatHandler::HandleReloadSpellPetAurasCommand(const char*)
513 sLog.outString( "Re-Loading Spell pet auras...");
514 spellmgr.LoadSpellPetAuras();
515 SendGlobalSysMessage("DB table `spell_pet_auras` reloaded.");
516 return true;
519 bool ChatHandler::HandleReloadPageTextsCommand(const char*)
521 sLog.outString( "Re-Loading Page Texts..." );
522 objmgr.LoadPageTexts();
523 SendGlobalSysMessage("DB table `page_texts` reloaded.");
524 return true;
527 bool ChatHandler::HandleReloadItemEnchantementsCommand(const char*)
529 sLog.outString( "Re-Loading Item Random Enchantments Table..." );
530 LoadRandomEnchantmentsTable();
531 SendGlobalSysMessage("DB table `item_enchantment_template` reloaded.");
532 return true;
535 bool ChatHandler::HandleReloadGameObjectScriptsCommand(const char* arg)
537 if(sWorld.IsScriptScheduled())
539 SendSysMessage("DB scripts used currently, please attempt reload later.");
540 SetSentErrorMessage(true);
541 return false;
544 if(*arg!='a')
545 sLog.outString( "Re-Loading Scripts from `gameobject_scripts`...");
547 objmgr.LoadGameObjectScripts();
549 if(*arg!='a')
550 SendGlobalSysMessage("DB table `gameobject_scripts` reloaded.");
552 return true;
555 bool ChatHandler::HandleReloadEventScriptsCommand(const char* arg)
557 if(sWorld.IsScriptScheduled())
559 SendSysMessage("DB scripts used currently, please attempt reload later.");
560 SetSentErrorMessage(true);
561 return false;
564 if(*arg!='a')
565 sLog.outString( "Re-Loading Scripts from `event_scripts`...");
567 objmgr.LoadEventScripts();
569 if(*arg!='a')
570 SendGlobalSysMessage("DB table `event_scripts` reloaded.");
572 return true;
575 bool ChatHandler::HandleReloadQuestEndScriptsCommand(const char* arg)
577 if(sWorld.IsScriptScheduled())
579 SendSysMessage("DB scripts used currently, please attempt reload later.");
580 SetSentErrorMessage(true);
581 return false;
584 if(*arg!='a')
585 sLog.outString( "Re-Loading Scripts from `quest_end_scripts`...");
587 objmgr.LoadQuestEndScripts();
589 if(*arg!='a')
590 SendGlobalSysMessage("DB table `quest_end_scripts` reloaded.");
592 return true;
595 bool ChatHandler::HandleReloadQuestStartScriptsCommand(const char* arg)
597 if(sWorld.IsScriptScheduled())
599 SendSysMessage("DB scripts used currently, please attempt reload later.");
600 SetSentErrorMessage(true);
601 return false;
604 if(*arg!='a')
605 sLog.outString( "Re-Loading Scripts from `quest_start_scripts`...");
607 objmgr.LoadQuestStartScripts();
609 if(*arg!='a')
610 SendGlobalSysMessage("DB table `quest_start_scripts` reloaded.");
612 return true;
615 bool ChatHandler::HandleReloadSpellScriptsCommand(const char* arg)
617 if(sWorld.IsScriptScheduled())
619 SendSysMessage("DB scripts used currently, please attempt reload later.");
620 SetSentErrorMessage(true);
621 return false;
624 if(*arg!='a')
625 sLog.outString( "Re-Loading Scripts from `spell_scripts`...");
627 objmgr.LoadSpellScripts();
629 if(*arg!='a')
630 SendGlobalSysMessage("DB table `spell_scripts` reloaded.");
632 return true;
635 bool ChatHandler::HandleReloadDbScriptStringCommand(const char* arg)
637 sLog.outString( "Re-Loading Script strings from `db_script_string`...");
638 objmgr.LoadDbScriptStrings();
639 SendGlobalSysMessage("DB table `db_script_string` reloaded.");
640 return true;
643 bool ChatHandler::HandleReloadGameGraveyardZoneCommand(const char* /*arg*/)
645 sLog.outString( "Re-Loading Graveyard-zone links...");
647 objmgr.LoadGraveyardZones();
649 SendGlobalSysMessage("DB table `game_graveyard_zone` reloaded.");
651 return true;
654 bool ChatHandler::HandleReloadGameTeleCommand(const char* /*arg*/)
656 sLog.outString( "Re-Loading Game Tele coordinates...");
658 objmgr.LoadGameTele();
660 SendGlobalSysMessage("DB table `game_tele` reloaded.");
662 return true;
665 bool ChatHandler::HandleReloadLocalesCreatureCommand(const char* /*arg*/)
667 sLog.outString( "Re-Loading Locales Creature ...");
668 objmgr.LoadCreatureLocales();
669 SendGlobalSysMessage("DB table `locales_creature` reloaded.");
670 return true;
673 bool ChatHandler::HandleReloadLocalesGameobjectCommand(const char* /*arg*/)
675 sLog.outString( "Re-Loading Locales Gameobject ... ");
676 objmgr.LoadGameObjectLocales();
677 SendGlobalSysMessage("DB table `locales_gameobject` reloaded.");
678 return true;
681 bool ChatHandler::HandleReloadLocalesItemCommand(const char* /*arg*/)
683 sLog.outString( "Re-Loading Locales Item ... ");
684 objmgr.LoadItemLocales();
685 SendGlobalSysMessage("DB table `locales_item` reloaded.");
686 return true;
689 bool ChatHandler::HandleReloadLocalesNpcTextCommand(const char* /*arg*/)
691 sLog.outString( "Re-Loading Locales NPC Text ... ");
692 objmgr.LoadNpcTextLocales();
693 SendGlobalSysMessage("DB table `locales_npc_text` reloaded.");
694 return true;
697 bool ChatHandler::HandleReloadLocalesPageTextCommand(const char* /*arg*/)
699 sLog.outString( "Re-Loading Locales Page Text ... ");
700 objmgr.LoadPageTextLocales();
701 SendGlobalSysMessage("DB table `locales_page_text` reloaded.");
702 return true;
705 bool ChatHandler::HandleReloadLocalesPointsOfInterestCommand(const char* /*arg*/)
707 sLog.outString( "Re-Loading Locales Points Of Interest ... ");
708 objmgr.LoadPointOfInterestLocales();
709 SendGlobalSysMessage("DB table `locales_points_of_interest` reloaded.");
710 return true;
713 bool ChatHandler::HandleReloadLocalesQuestCommand(const char* /*arg*/)
715 sLog.outString( "Re-Loading Locales Quest ... ");
716 objmgr.LoadQuestLocales();
717 SendGlobalSysMessage("DB table `locales_quest` reloaded.");
718 return true;
721 bool ChatHandler::HandleLoadScriptsCommand(const char* args)
723 if(!LoadScriptingModule(args)) return true;
725 sWorld.SendWorldText(LANG_SCRIPTS_RELOADED);
726 return true;
729 bool ChatHandler::HandleAccountSetGmLevelCommand(const char* args)
731 char* arg1 = strtok((char*)args, " ");
732 if( !arg1 )
733 return false;
735 /// must be NULL if targeted syntax and must be not nULL if not targeted
736 char* arg2 = strtok(NULL, " ");
738 std::string targetAccountName;
739 uint32 targetAccountId = 0;
741 /// only target player different from self allowed (if targetPlayer!=NULL then not console)
742 Player* targetPlayer = getSelectedPlayer();
743 if(targetPlayer && m_session->GetPlayer()!=targetPlayer)
745 /// wrong command syntax or unexpected targeting
746 if(arg2)
747 return false;
749 /// security level expected in arg2 after this if.
750 arg2 = arg1;
752 targetAccountId = targetPlayer->GetSession()->GetAccountId();
754 else
756 /// wrong command syntax (second arg expected)
757 if(!arg2)
758 return false;
760 targetAccountName = arg1;
761 if(!AccountMgr::normilizeString(targetAccountName))
763 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,targetAccountName.c_str());
764 SetSentErrorMessage(true);
765 return false;
768 targetAccountId = accmgr.GetId(targetAccountName);
769 if(!targetAccountId)
771 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,targetAccountName.c_str());
772 SetSentErrorMessage(true);
773 return false;
777 int32 gm = (int32)atoi(arg2);
778 if ( gm < SEC_PLAYER || gm > SEC_ADMINISTRATOR )
780 SendSysMessage(LANG_BAD_VALUE);
781 SetSentErrorMessage(true);
782 return false;
785 /// can set security level only for target with less security and to less security that we have
786 /// This is also reject self apply in fact
787 if(HasLowerSecurityAccount(NULL,targetAccountId,true))
788 return false;
790 /// account can't set security to same or grater level, need more power GM or console
791 uint32 plSecurity = m_session ? m_session->GetSecurity() : SEC_CONSOLE;
792 if (uint32(gm) >= plSecurity )
794 SendSysMessage(LANG_YOURS_SECURITY_IS_LOW);
795 SetSentErrorMessage(true);
796 return false;
799 if(targetPlayer)
801 ChatHandler(targetPlayer).PSendSysMessage(LANG_YOURS_SECURITY_CHANGED,GetNameLink().c_str(), gm);
802 targetPlayer->GetSession()->SetSecurity(gm);
805 PSendSysMessage(LANG_YOU_CHANGE_SECURITY, targetAccountName.c_str(), gm);
806 loginDatabase.PExecute("UPDATE account SET gmlevel = '%i' WHERE id = '%u'", gm, targetAccountId);
808 return true;
811 /// Set password for account
812 bool ChatHandler::HandleAccountSetPasswordCommand(const char* args)
814 if(!*args)
815 return false;
817 ///- Get the command line arguments
818 char *szAccount = strtok ((char*)args," ");
819 char *szPassword1 = strtok (NULL," ");
820 char *szPassword2 = strtok (NULL," ");
822 if (!szAccount||!szPassword1 || !szPassword2)
823 return false;
825 std::string account_name = szAccount;
826 if(!AccountMgr::normilizeString(account_name))
828 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
829 SetSentErrorMessage(true);
830 return false;
833 uint32 targetAccountId = accmgr.GetId(account_name);
834 if (!targetAccountId)
836 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
837 SetSentErrorMessage(true);
838 return false;
841 /// can set password only for target with less security
842 /// This is also reject self apply in fact
843 if(HasLowerSecurityAccount (NULL,targetAccountId,true))
844 return false;
846 if (strcmp(szPassword1,szPassword2))
848 SendSysMessage (LANG_NEW_PASSWORDS_NOT_MATCH);
849 SetSentErrorMessage (true);
850 return false;
853 AccountOpResult result = accmgr.ChangePassword(targetAccountId, szPassword1);
855 switch(result)
857 case AOR_OK:
858 SendSysMessage(LANG_COMMAND_PASSWORD);
859 break;
860 case AOR_NAME_NOT_EXIST:
861 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
862 SetSentErrorMessage(true);
863 return false;
864 case AOR_PASS_TOO_LONG:
865 SendSysMessage(LANG_PASSWORD_TOO_LONG);
866 SetSentErrorMessage(true);
867 return false;
868 default:
869 SendSysMessage(LANG_COMMAND_NOTCHANGEPASSWORD);
870 SetSentErrorMessage(true);
871 return false;
874 return true;
877 bool ChatHandler::HandleAllowMovementCommand(const char* /*args*/)
879 if(sWorld.getAllowMovement())
881 sWorld.SetAllowMovement(false);
882 SendSysMessage(LANG_CREATURE_MOVE_DISABLED);
884 else
886 sWorld.SetAllowMovement(true);
887 SendSysMessage(LANG_CREATURE_MOVE_ENABLED);
889 return true;
892 bool ChatHandler::HandleMaxSkillCommand(const char* /*args*/)
894 Player* SelectedPlayer = getSelectedPlayer();
895 if(!SelectedPlayer)
897 SendSysMessage(LANG_NO_CHAR_SELECTED);
898 SetSentErrorMessage(true);
899 return false;
902 // each skills that have max skill value dependent from level seted to current level max skill value
903 SelectedPlayer->UpdateSkillsToMaxSkillsForLevel();
904 return true;
907 bool ChatHandler::HandleSetSkillCommand(const char* args)
909 // number or [name] Shift-click form |color|Hskill:skill_id|h[name]|h|r
910 char* skill_p = extractKeyFromLink((char*)args,"Hskill");
911 if(!skill_p)
912 return false;
914 char *level_p = strtok (NULL, " ");
916 if( !level_p)
917 return false;
919 char *max_p = strtok (NULL, " ");
921 int32 skill = atoi(skill_p);
922 if (skill <= 0)
924 PSendSysMessage(LANG_INVALID_SKILL_ID, skill);
925 SetSentErrorMessage(true);
926 return false;
929 int32 level = atol (level_p);
931 Player * target = getSelectedPlayer();
932 if(!target)
934 SendSysMessage(LANG_NO_CHAR_SELECTED);
935 SetSentErrorMessage(true);
936 return false;
939 SkillLineEntry const* sl = sSkillLineStore.LookupEntry(skill);
940 if(!sl)
942 PSendSysMessage(LANG_INVALID_SKILL_ID, skill);
943 SetSentErrorMessage(true);
944 return false;
947 std::string tNameLink = GetNameLink(target);
949 if(!target->GetSkillValue(skill))
951 PSendSysMessage(LANG_SET_SKILL_ERROR, tNameLink.c_str(), skill, sl->name[0]);
952 SetSentErrorMessage(true);
953 return false;
956 int32 max = max_p ? atol (max_p) : target->GetPureMaxSkillValue(skill);
958 if( level <= 0 || level > max || max <= 0 )
959 return false;
961 target->SetSkill(skill, level, max);
962 PSendSysMessage(LANG_SET_SKILL, skill, sl->name[0], tNameLink.c_str(), level, max);
964 return true;
967 bool ChatHandler::HandleUnLearnCommand(const char* args)
969 if (!*args)
970 return false;
972 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r
973 uint32 spell_id = extractSpellIdFromLink((char*)args);
974 if(!spell_id)
975 return false;
977 char const* allStr = strtok(NULL," ");
978 bool allRanks = allStr ? (strncmp(allStr, "all", strlen(allStr)) == 0) : false;
980 Player* target = getSelectedPlayer();
981 if(!target)
983 SendSysMessage(LANG_NO_CHAR_SELECTED);
984 SetSentErrorMessage(true);
985 return false;
988 if(allRanks)
989 spell_id = spellmgr.GetFirstSpellInChain (spell_id);
991 if (target->HasSpell(spell_id))
992 target->removeSpell(spell_id,false,!allRanks);
993 else
994 SendSysMessage(LANG_FORGET_SPELL);
996 return true;
999 bool ChatHandler::HandleCooldownCommand(const char* args)
1001 Player* target = getSelectedPlayer();
1002 if(!target)
1004 SendSysMessage(LANG_PLAYER_NOT_FOUND);
1005 SetSentErrorMessage(true);
1006 return false;
1009 std::string tNameLink = GetNameLink(target);
1011 if (!*args)
1013 target->RemoveAllSpellCooldown();
1014 PSendSysMessage(LANG_REMOVEALL_COOLDOWN, tNameLink.c_str());
1016 else
1018 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
1019 uint32 spell_id = extractSpellIdFromLink((char*)args);
1020 if(!spell_id)
1021 return false;
1023 if(!sSpellStore.LookupEntry(spell_id))
1025 PSendSysMessage(LANG_UNKNOWN_SPELL, target==m_session->GetPlayer() ? GetMangosString(LANG_YOU) : tNameLink.c_str());
1026 SetSentErrorMessage(true);
1027 return false;
1030 WorldPacket data( SMSG_CLEAR_COOLDOWN, (4+8) );
1031 data << uint32(spell_id);
1032 data << uint64(target->GetGUID());
1033 target->GetSession()->SendPacket(&data);
1034 target->RemoveSpellCooldown(spell_id);
1035 PSendSysMessage(LANG_REMOVE_COOLDOWN, spell_id, target==m_session->GetPlayer() ? GetMangosString(LANG_YOU) : tNameLink.c_str());
1037 return true;
1040 bool ChatHandler::HandleLearnAllCommand(const char* /*args*/)
1042 static const char *allSpellList[] =
1044 "3365",
1045 "6233",
1046 "6247",
1047 "6246",
1048 "6477",
1049 "6478",
1050 "22810",
1051 "8386",
1052 "21651",
1053 "21652",
1054 "522",
1055 "7266",
1056 "8597",
1057 "2479",
1058 "22027",
1059 "6603",
1060 "5019",
1061 "133",
1062 "168",
1063 "227",
1064 "5009",
1065 "9078",
1066 "668",
1067 "203",
1068 "20599",
1069 "20600",
1070 "81",
1071 "20597",
1072 "20598",
1073 "20864",
1074 "1459",
1075 "5504",
1076 "587",
1077 "5143",
1078 "118",
1079 "5505",
1080 "597",
1081 "604",
1082 "1449",
1083 "1460",
1084 "2855",
1085 "1008",
1086 "475",
1087 "5506",
1088 "1463",
1089 "12824",
1090 "8437",
1091 "990",
1092 "5145",
1093 "8450",
1094 "1461",
1095 "759",
1096 "8494",
1097 "8455",
1098 "8438",
1099 "6127",
1100 "8416",
1101 "6129",
1102 "8451",
1103 "8495",
1104 "8439",
1105 "3552",
1106 "8417",
1107 "10138",
1108 "12825",
1109 "10169",
1110 "10156",
1111 "10144",
1112 "10191",
1113 "10201",
1114 "10211",
1115 "10053",
1116 "10173",
1117 "10139",
1118 "10145",
1119 "10192",
1120 "10170",
1121 "10202",
1122 "10054",
1123 "10174",
1124 "10193",
1125 "12826",
1126 "2136",
1127 "143",
1128 "145",
1129 "2137",
1130 "2120",
1131 "3140",
1132 "543",
1133 "2138",
1134 "2948",
1135 "8400",
1136 "2121",
1137 "8444",
1138 "8412",
1139 "8457",
1140 "8401",
1141 "8422",
1142 "8445",
1143 "8402",
1144 "8413",
1145 "8458",
1146 "8423",
1147 "8446",
1148 "10148",
1149 "10197",
1150 "10205",
1151 "10149",
1152 "10215",
1153 "10223",
1154 "10206",
1155 "10199",
1156 "10150",
1157 "10216",
1158 "10207",
1159 "10225",
1160 "10151",
1161 "116",
1162 "205",
1163 "7300",
1164 "122",
1165 "837",
1166 "10",
1167 "7301",
1168 "7322",
1169 "6143",
1170 "120",
1171 "865",
1172 "8406",
1173 "6141",
1174 "7302",
1175 "8461",
1176 "8407",
1177 "8492",
1178 "8427",
1179 "8408",
1180 "6131",
1181 "7320",
1182 "10159",
1183 "8462",
1184 "10185",
1185 "10179",
1186 "10160",
1187 "10180",
1188 "10219",
1189 "10186",
1190 "10177",
1191 "10230",
1192 "10181",
1193 "10161",
1194 "10187",
1195 "10220",
1196 "2018",
1197 "2663",
1198 "12260",
1199 "2660",
1200 "3115",
1201 "3326",
1202 "2665",
1203 "3116",
1204 "2738",
1205 "3293",
1206 "2661",
1207 "3319",
1208 "2662",
1209 "9983",
1210 "8880",
1211 "2737",
1212 "2739",
1213 "7408",
1214 "3320",
1215 "2666",
1216 "3323",
1217 "3324",
1218 "3294",
1219 "22723",
1220 "23219",
1221 "23220",
1222 "23221",
1223 "23228",
1224 "23338",
1225 "10788",
1226 "10790",
1227 "5611",
1228 "5016",
1229 "5609",
1230 "2060",
1231 "10963",
1232 "10964",
1233 "10965",
1234 "22593",
1235 "22594",
1236 "596",
1237 "996",
1238 "499",
1239 "768",
1240 "17002",
1241 "1448",
1242 "1082",
1243 "16979",
1244 "1079",
1245 "5215",
1246 "20484",
1247 "5221",
1248 "15590",
1249 "17007",
1250 "6795",
1251 "6807",
1252 "5487",
1253 "1446",
1254 "1066",
1255 "5421",
1256 "3139",
1257 "779",
1258 "6811",
1259 "6808",
1260 "1445",
1261 "5216",
1262 "1737",
1263 "5222",
1264 "5217",
1265 "1432",
1266 "6812",
1267 "9492",
1268 "5210",
1269 "3030",
1270 "1441",
1271 "783",
1272 "6801",
1273 "20739",
1274 "8944",
1275 "9491",
1276 "22569",
1277 "5226",
1278 "6786",
1279 "1433",
1280 "8973",
1281 "1828",
1282 "9495",
1283 "9006",
1284 "6794",
1285 "8993",
1286 "5203",
1287 "16914",
1288 "6784",
1289 "9635",
1290 "22830",
1291 "20722",
1292 "9748",
1293 "6790",
1294 "9753",
1295 "9493",
1296 "9752",
1297 "9831",
1298 "9825",
1299 "9822",
1300 "5204",
1301 "5401",
1302 "22831",
1303 "6793",
1304 "9845",
1305 "17401",
1306 "9882",
1307 "9868",
1308 "20749",
1309 "9893",
1310 "9899",
1311 "9895",
1312 "9832",
1313 "9902",
1314 "9909",
1315 "22832",
1316 "9828",
1317 "9851",
1318 "9883",
1319 "9869",
1320 "17406",
1321 "17402",
1322 "9914",
1323 "20750",
1324 "9897",
1325 "9848",
1326 "3127",
1327 "107",
1328 "204",
1329 "9116",
1330 "2457",
1331 "78",
1332 "18848",
1333 "331",
1334 "403",
1335 "2098",
1336 "1752",
1337 "11278",
1338 "11288",
1339 "11284",
1340 "6461",
1341 "2344",
1342 "2345",
1343 "6463",
1344 "2346",
1345 "2352",
1346 "775",
1347 "1434",
1348 "1612",
1349 "71",
1350 "2468",
1351 "2458",
1352 "2467",
1353 "7164",
1354 "7178",
1355 "7367",
1356 "7376",
1357 "7381",
1358 "21156",
1359 "5209",
1360 "3029",
1361 "5201",
1362 "9849",
1363 "9850",
1364 "20719",
1365 "22568",
1366 "22827",
1367 "22828",
1368 "22829",
1369 "6809",
1370 "8972",
1371 "9005",
1372 "9823",
1373 "9827",
1374 "6783",
1375 "9913",
1376 "6785",
1377 "6787",
1378 "9866",
1379 "9867",
1380 "9894",
1381 "9896",
1382 "6800",
1383 "8992",
1384 "9829",
1385 "9830",
1386 "780",
1387 "769",
1388 "6749",
1389 "6750",
1390 "9755",
1391 "9754",
1392 "9908",
1393 "20745",
1394 "20742",
1395 "20747",
1396 "20748",
1397 "9746",
1398 "9745",
1399 "9880",
1400 "9881",
1401 "5391",
1402 "842",
1403 "3025",
1404 "3031",
1405 "3287",
1406 "3329",
1407 "1945",
1408 "3559",
1409 "4933",
1410 "4934",
1411 "4935",
1412 "4936",
1413 "5142",
1414 "5390",
1415 "5392",
1416 "5404",
1417 "5420",
1418 "6405",
1419 "7293",
1420 "7965",
1421 "8041",
1422 "8153",
1423 "9033",
1424 "9034",
1425 //"9036", problems with ghost state
1426 "16421",
1427 "21653",
1428 "22660",
1429 "5225",
1430 "9846",
1431 "2426",
1432 "5916",
1433 "6634",
1434 //"6718", phasing stealth, annoying for learn all case.
1435 "6719",
1436 "8822",
1437 "9591",
1438 "9590",
1439 "10032",
1440 "17746",
1441 "17747",
1442 "8203",
1443 "11392",
1444 "12495",
1445 "16380",
1446 "23452",
1447 "4079",
1448 "4996",
1449 "4997",
1450 "4998",
1451 "4999",
1452 "5000",
1453 "6348",
1454 "6349",
1455 "6481",
1456 "6482",
1457 "6483",
1458 "6484",
1459 "11362",
1460 "11410",
1461 "11409",
1462 "12510",
1463 "12509",
1464 "12885",
1465 "13142",
1466 "21463",
1467 "23460",
1468 "11421",
1469 "11416",
1470 "11418",
1471 "1851",
1472 "10059",
1473 "11423",
1474 "11417",
1475 "11422",
1476 "11419",
1477 "11424",
1478 "11420",
1479 "27",
1480 "31",
1481 "33",
1482 "34",
1483 "35",
1484 "15125",
1485 "21127",
1486 "22950",
1487 "1180",
1488 "201",
1489 "12593",
1490 "12842",
1491 "16770",
1492 "6057",
1493 "12051",
1494 "18468",
1495 "12606",
1496 "12605",
1497 "18466",
1498 "12502",
1499 "12043",
1500 "15060",
1501 "12042",
1502 "12341",
1503 "12848",
1504 "12344",
1505 "12353",
1506 "18460",
1507 "11366",
1508 "12350",
1509 "12352",
1510 "13043",
1511 "11368",
1512 "11113",
1513 "12400",
1514 "11129",
1515 "16766",
1516 "12573",
1517 "15053",
1518 "12580",
1519 "12475",
1520 "12472",
1521 "12953",
1522 "12488",
1523 "11189",
1524 "12985",
1525 "12519",
1526 "16758",
1527 "11958",
1528 "12490",
1529 "11426",
1530 "3565",
1531 "3562",
1532 "18960",
1533 "3567",
1534 "3561",
1535 "3566",
1536 "3563",
1537 "1953",
1538 "2139",
1539 "12505",
1540 "13018",
1541 "12522",
1542 "12523",
1543 "5146",
1544 "5144",
1545 "5148",
1546 "8419",
1547 "8418",
1548 "10213",
1549 "10212",
1550 "10157",
1551 "12524",
1552 "13019",
1553 "12525",
1554 "13020",
1555 "12526",
1556 "13021",
1557 "18809",
1558 "13031",
1559 "13032",
1560 "13033",
1561 "4036",
1562 "3920",
1563 "3919",
1564 "3918",
1565 "7430",
1566 "3922",
1567 "3923",
1568 "7411",
1569 "7418",
1570 "7421",
1571 "13262",
1572 "7412",
1573 "7415",
1574 "7413",
1575 "7416",
1576 "13920",
1577 "13921",
1578 "7745",
1579 "7779",
1580 "7428",
1581 "7457",
1582 "7857",
1583 "7748",
1584 "7426",
1585 "13421",
1586 "7454",
1587 "13378",
1588 "7788",
1589 "14807",
1590 "14293",
1591 "7795",
1592 "6296",
1593 "20608",
1594 "755",
1595 "444",
1596 "427",
1597 "428",
1598 "442",
1599 "447",
1600 "3578",
1601 "3581",
1602 "19027",
1603 "3580",
1604 "665",
1605 "3579",
1606 "3577",
1607 "6755",
1608 "3576",
1609 "2575",
1610 "2577",
1611 "2578",
1612 "2579",
1613 "2580",
1614 "2656",
1615 "2657",
1616 "2576",
1617 "3564",
1618 "10248",
1619 "8388",
1620 "2659",
1621 "14891",
1622 "3308",
1623 "3307",
1624 "10097",
1625 "2658",
1626 "3569",
1627 "16153",
1628 "3304",
1629 "10098",
1630 "4037",
1631 "3929",
1632 "3931",
1633 "3926",
1634 "3924",
1635 "3930",
1636 "3977",
1637 "3925",
1638 "136",
1639 "228",
1640 "5487",
1641 "43",
1642 "202",
1646 int loop = 0;
1647 while(strcmp(allSpellList[loop], "0"))
1649 uint32 spell = atol((char*)allSpellList[loop++]);
1651 if (m_session->GetPlayer()->HasSpell(spell))
1652 continue;
1654 SpellEntry const* spellInfo = sSpellStore.LookupEntry(spell);
1655 if(!spellInfo || !SpellMgr::IsSpellValid(spellInfo,m_session->GetPlayer()))
1657 PSendSysMessage(LANG_COMMAND_SPELL_BROKEN,spell);
1658 continue;
1661 m_session->GetPlayer()->learnSpell(spell,false);
1664 SendSysMessage(LANG_COMMAND_LEARN_MANY_SPELLS);
1666 return true;
1669 bool ChatHandler::HandleLearnAllGMCommand(const char* /*args*/)
1671 static const char *gmSpellList[] =
1673 "24347", // Become A Fish, No Breath Bar
1674 "35132", // Visual Boom
1675 "38488", // Attack 4000-8000 AOE
1676 "38795", // Attack 2000 AOE + Slow Down 90%
1677 "15712", // Attack 200
1678 "1852", // GM Spell Silence
1679 "31899", // Kill
1680 "31924", // Kill
1681 "29878", // Kill My Self
1682 "26644", // More Kill
1684 "28550", //Invisible 24
1685 "23452", //Invisible + Target
1689 uint16 gmSpellIter = 0;
1690 while( strcmp(gmSpellList[gmSpellIter], "0") )
1692 uint32 spell = atol((char*)gmSpellList[gmSpellIter++]);
1694 SpellEntry const* spellInfo = sSpellStore.LookupEntry(spell);
1695 if(!spellInfo || !SpellMgr::IsSpellValid(spellInfo,m_session->GetPlayer()))
1697 PSendSysMessage(LANG_COMMAND_SPELL_BROKEN,spell);
1698 continue;
1701 m_session->GetPlayer()->learnSpell(spell,false);
1704 SendSysMessage(LANG_LEARNING_GM_SKILLS);
1705 return true;
1708 bool ChatHandler::HandleLearnAllMyClassCommand(const char* /*args*/)
1710 HandleLearnAllMySpellsCommand("");
1711 HandleLearnAllMyTalentsCommand("");
1712 return true;
1715 bool ChatHandler::HandleLearnAllMySpellsCommand(const char* /*args*/)
1717 ChrClassesEntry const* clsEntry = sChrClassesStore.LookupEntry(m_session->GetPlayer()->getClass());
1718 if(!clsEntry)
1719 return true;
1720 uint32 family = clsEntry->spellfamily;
1722 for (uint32 i = 0; i < sSpellStore.GetNumRows(); i++)
1724 SpellEntry const *spellInfo = sSpellStore.LookupEntry(i);
1725 if(!spellInfo)
1726 continue;
1728 // skip server-side/triggered spells
1729 if(spellInfo->spellLevel==0)
1730 continue;
1732 // skip wrong class/race skills
1733 if(!m_session->GetPlayer()->IsSpellFitByClassAndRace(spellInfo->Id))
1734 continue;
1736 // skip other spell families
1737 if( spellInfo->SpellFamilyName != family)
1738 continue;
1740 // skip spells with first rank learned as talent (and all talents then also)
1741 uint32 first_rank = spellmgr.GetFirstSpellInChain(spellInfo->Id);
1742 if(GetTalentSpellCost(first_rank) > 0 )
1743 continue;
1745 // skip broken spells
1746 if(!SpellMgr::IsSpellValid(spellInfo,m_session->GetPlayer(),false))
1747 continue;
1749 m_session->GetPlayer()->learnSpell(i,false);
1752 SendSysMessage(LANG_COMMAND_LEARN_CLASS_SPELLS);
1753 return true;
1756 bool ChatHandler::HandleLearnAllMyTalentsCommand(const char* /*args*/)
1758 Player* player = m_session->GetPlayer();
1759 uint32 classMask = player->getClassMask();
1761 for (uint32 i = 0; i < sTalentStore.GetNumRows(); i++)
1763 TalentEntry const *talentInfo = sTalentStore.LookupEntry(i);
1764 if(!talentInfo)
1765 continue;
1767 TalentTabEntry const *talentTabInfo = sTalentTabStore.LookupEntry( talentInfo->TalentTab );
1768 if(!talentTabInfo)
1769 continue;
1771 if( (classMask & talentTabInfo->ClassMask) == 0 )
1772 continue;
1774 // search highest talent rank
1775 uint32 spellid = 0;
1776 int rank = 4;
1777 for(; rank >= 0; --rank)
1779 if(talentInfo->RankID[rank]!=0)
1781 spellid = talentInfo->RankID[rank];
1782 break;
1786 if(!spellid) // ??? none spells in talent
1787 continue;
1789 SpellEntry const* spellInfo = sSpellStore.LookupEntry(spellid);
1790 if(!spellInfo || !SpellMgr::IsSpellValid(spellInfo,m_session->GetPlayer(),false))
1791 continue;
1793 // learn highest rank of talent and learn all non-talent spell ranks (recursive by tree)
1794 player->learnSpellHighRank(spellid);
1797 SendSysMessage(LANG_COMMAND_LEARN_CLASS_TALENTS);
1798 return true;
1801 bool ChatHandler::HandleLearnAllLangCommand(const char* /*args*/)
1803 // skipping UNIVERSAL language (0)
1804 for(int i = 1; i < LANGUAGES_COUNT; ++i)
1805 m_session->GetPlayer()->learnSpell(lang_description[i].spell_id,false);
1807 SendSysMessage(LANG_COMMAND_LEARN_ALL_LANG);
1808 return true;
1811 bool ChatHandler::HandleLearnAllDefaultCommand(const char* args)
1813 Player *player = NULL;
1814 if (*args)
1816 std::string name = extractPlayerNameFromLink((char*)args);
1817 if(name.empty())
1819 SendSysMessage(LANG_PLAYER_NOT_FOUND);
1820 SetSentErrorMessage(true);
1821 return false;
1824 player = objmgr.GetPlayer(name.c_str());
1826 else
1827 player = getSelectedPlayer();
1829 if(!player)
1831 SendSysMessage(LANG_NO_CHAR_SELECTED);
1832 SetSentErrorMessage(true);
1833 return false;
1836 player->learnDefaultSpells();
1837 player->learnQuestRewardedSpells();
1839 PSendSysMessage(LANG_COMMAND_LEARN_ALL_DEFAULT_AND_QUEST,GetNameLink(player).c_str());
1840 return true;
1843 bool ChatHandler::HandleLearnCommand(const char* args)
1845 Player* targetPlayer = getSelectedPlayer();
1847 if(!targetPlayer)
1849 SendSysMessage(LANG_PLAYER_NOT_FOUND);
1850 SetSentErrorMessage(true);
1851 return false;
1854 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
1855 uint32 spell = extractSpellIdFromLink((char*)args);
1856 if(!spell || !sSpellStore.LookupEntry(spell))
1857 return false;
1859 char const* allStr = strtok(NULL," ");
1860 bool allRanks = allStr ? (strncmp(allStr, "all", strlen(allStr)) == 0) : false;
1862 SpellEntry const* spellInfo = sSpellStore.LookupEntry(spell);
1863 if(!spellInfo || !SpellMgr::IsSpellValid(spellInfo,m_session->GetPlayer()))
1865 PSendSysMessage(LANG_COMMAND_SPELL_BROKEN,spell);
1866 SetSentErrorMessage(true);
1867 return false;
1870 if (!allRanks && targetPlayer->HasSpell(spell))
1872 if(targetPlayer == m_session->GetPlayer())
1873 SendSysMessage(LANG_YOU_KNOWN_SPELL);
1874 else
1875 PSendSysMessage(LANG_TARGET_KNOWN_SPELL,GetNameLink(targetPlayer).c_str());
1876 SetSentErrorMessage(true);
1877 return false;
1880 if(allRanks)
1881 targetPlayer->learnSpellHighRank(spell);
1882 else
1883 targetPlayer->learnSpell(spell,false);
1885 return true;
1888 bool ChatHandler::HandleAddItemCommand(const char* args)
1890 if (!*args)
1891 return false;
1893 uint32 itemId = 0;
1895 if(args[0]=='[') // [name] manual form
1897 char* citemName = citemName = strtok((char*)args, "]");
1899 if(citemName && citemName[0])
1901 std::string itemName = citemName+1;
1902 WorldDatabase.escape_string(itemName);
1903 QueryResult *result = WorldDatabase.PQuery("SELECT entry FROM item_template WHERE name = '%s'", itemName.c_str());
1904 if (!result)
1906 PSendSysMessage(LANG_COMMAND_COULDNOTFIND, citemName+1);
1907 SetSentErrorMessage(true);
1908 return false;
1910 itemId = result->Fetch()->GetUInt16();
1911 delete result;
1913 else
1914 return false;
1916 else // item_id or [name] Shift-click form |color|Hitem:item_id:0:0:0|h[name]|h|r
1918 char* cId = extractKeyFromLink((char*)args,"Hitem");
1919 if(!cId)
1920 return false;
1921 itemId = atol(cId);
1924 char* ccount = strtok(NULL, " ");
1926 int32 count = 1;
1928 if (ccount)
1929 count = strtol(ccount, NULL, 10);
1931 if (count == 0)
1932 count = 1;
1934 Player* pl = m_session->GetPlayer();
1935 Player* plTarget = getSelectedPlayer();
1936 if(!plTarget)
1937 plTarget = pl;
1939 sLog.outDetail(GetMangosString(LANG_ADDITEM), itemId, count);
1941 ItemPrototype const *pProto = objmgr.GetItemPrototype(itemId);
1942 if(!pProto)
1944 PSendSysMessage(LANG_COMMAND_ITEMIDINVALID, itemId);
1945 SetSentErrorMessage(true);
1946 return false;
1949 //Subtract
1950 if (count < 0)
1952 plTarget->DestroyItemCount(itemId, -count, true, false);
1953 PSendSysMessage(LANG_REMOVEITEM, itemId, -count, GetNameLink(plTarget).c_str());
1954 return true;
1957 //Adding items
1958 uint32 noSpaceForCount = 0;
1960 // check space and find places
1961 ItemPosCountVec dest;
1962 uint8 msg = plTarget->CanStoreNewItem( NULL_BAG, NULL_SLOT, dest, itemId, count, &noSpaceForCount );
1963 if( msg != EQUIP_ERR_OK ) // convert to possible store amount
1964 count -= noSpaceForCount;
1966 if( count == 0 || dest.empty()) // can't add any
1968 PSendSysMessage(LANG_ITEM_CANNOT_CREATE, itemId, noSpaceForCount );
1969 SetSentErrorMessage(true);
1970 return false;
1973 Item* item = plTarget->StoreNewItem( dest, itemId, true, Item::GenerateItemRandomPropertyId(itemId));
1975 // remove binding (let GM give it to another player later)
1976 if(pl==plTarget)
1977 for(ItemPosCountVec::const_iterator itr = dest.begin(); itr != dest.end(); ++itr)
1978 if(Item* item1 = pl->GetItemByPos(itr->pos))
1979 item1->SetBinding( false );
1981 if(count > 0 && item)
1983 pl->SendNewItem(item,count,false,true);
1984 if(pl!=plTarget)
1985 plTarget->SendNewItem(item,count,true,false);
1988 if(noSpaceForCount > 0)
1989 PSendSysMessage(LANG_ITEM_CANNOT_CREATE, itemId, noSpaceForCount);
1991 return true;
1994 bool ChatHandler::HandleAddItemSetCommand(const char* args)
1996 if (!*args)
1997 return false;
1999 char* cId = extractKeyFromLink((char*)args,"Hitemset"); // number or [name] Shift-click form |color|Hitemset:itemset_id|h[name]|h|r
2000 if (!cId)
2001 return false;
2003 uint32 itemsetId = atol(cId);
2005 // prevent generation all items with itemset field value '0'
2006 if (itemsetId == 0)
2008 PSendSysMessage(LANG_NO_ITEMS_FROM_ITEMSET_FOUND,itemsetId);
2009 SetSentErrorMessage(true);
2010 return false;
2013 Player* pl = m_session->GetPlayer();
2014 Player* plTarget = getSelectedPlayer();
2015 if(!plTarget)
2016 plTarget = pl;
2018 sLog.outDetail(GetMangosString(LANG_ADDITEMSET), itemsetId);
2020 bool found = false;
2021 for (uint32 id = 0; id < sItemStorage.MaxEntry; id++)
2023 ItemPrototype const *pProto = sItemStorage.LookupEntry<ItemPrototype>(id);
2024 if (!pProto)
2025 continue;
2027 if (pProto->ItemSet == itemsetId)
2029 found = true;
2030 ItemPosCountVec dest;
2031 uint8 msg = plTarget->CanStoreNewItem( NULL_BAG, NULL_SLOT, dest, pProto->ItemId, 1 );
2032 if (msg == EQUIP_ERR_OK)
2034 Item* item = plTarget->StoreNewItem( dest, pProto->ItemId, true);
2036 // remove binding (let GM give it to another player later)
2037 if (pl==plTarget)
2038 item->SetBinding( false );
2040 pl->SendNewItem(item,1,false,true);
2041 if (pl!=plTarget)
2042 plTarget->SendNewItem(item,1,true,false);
2044 else
2046 pl->SendEquipError( msg, NULL, NULL );
2047 PSendSysMessage(LANG_ITEM_CANNOT_CREATE, pProto->ItemId, 1);
2052 if (!found)
2054 PSendSysMessage(LANG_NO_ITEMS_FROM_ITEMSET_FOUND,itemsetId);
2056 SetSentErrorMessage(true);
2057 return false;
2060 return true;
2063 bool ChatHandler::HandleListItemCommand(const char* args)
2065 if(!*args)
2066 return false;
2068 char* cId = extractKeyFromLink((char*)args,"Hitem");
2069 if(!cId)
2070 return false;
2072 uint32 item_id = atol(cId);
2073 if(!item_id)
2075 PSendSysMessage(LANG_COMMAND_ITEMIDINVALID, item_id);
2076 SetSentErrorMessage(true);
2077 return false;
2080 ItemPrototype const* itemProto = objmgr.GetItemPrototype(item_id);
2081 if(!itemProto)
2083 PSendSysMessage(LANG_COMMAND_ITEMIDINVALID, item_id);
2084 SetSentErrorMessage(true);
2085 return false;
2088 char* c_count = strtok(NULL, " ");
2089 int count = c_count ? atol(c_count) : 10;
2091 if(count < 0)
2092 return false;
2094 QueryResult *result;
2096 // inventory case
2097 uint32 inv_count = 0;
2098 result=CharacterDatabase.PQuery("SELECT COUNT(item_template) FROM character_inventory WHERE item_template='%u'",item_id);
2099 if(result)
2101 inv_count = (*result)[0].GetUInt32();
2102 delete result;
2105 result=CharacterDatabase.PQuery(
2106 // 0 1 2 3 4 5
2107 "SELECT ci.item, cibag.slot AS bag, ci.slot, ci.guid, characters.account,characters.name "
2108 "FROM character_inventory AS ci LEFT JOIN character_inventory AS cibag ON (cibag.item=ci.bag),characters "
2109 "WHERE ci.item_template='%u' AND ci.guid = characters.guid LIMIT %u ",
2110 item_id,uint32(count));
2112 if(result)
2116 Field *fields = result->Fetch();
2117 uint32 item_guid = fields[0].GetUInt32();
2118 uint32 item_bag = fields[1].GetUInt32();
2119 uint32 item_slot = fields[2].GetUInt32();
2120 uint32 owner_guid = fields[3].GetUInt32();
2121 uint32 owner_acc = fields[4].GetUInt32();
2122 std::string owner_name = fields[5].GetCppString();
2124 char const* item_pos = 0;
2125 if(Player::IsEquipmentPos(item_bag,item_slot))
2126 item_pos = "[equipped]";
2127 else if(Player::IsInventoryPos(item_bag,item_slot))
2128 item_pos = "[in inventory]";
2129 else if(Player::IsBankPos(item_bag,item_slot))
2130 item_pos = "[in bank]";
2131 else
2132 item_pos = "";
2134 PSendSysMessage(LANG_ITEMLIST_SLOT,
2135 item_guid,owner_name.c_str(),owner_guid,owner_acc,item_pos);
2136 } while (result->NextRow());
2138 int64 res_count = result->GetRowCount();
2140 delete result;
2142 if(count > res_count)
2143 count-=res_count;
2144 else if(count)
2145 count = 0;
2148 // mail case
2149 uint32 mail_count = 0;
2150 result=CharacterDatabase.PQuery("SELECT COUNT(item_template) FROM mail_items WHERE item_template='%u'", item_id);
2151 if(result)
2153 mail_count = (*result)[0].GetUInt32();
2154 delete result;
2157 if(count > 0)
2159 result=CharacterDatabase.PQuery(
2160 // 0 1 2 3 4 5 6
2161 "SELECT mail_items.item_guid, mail.sender, mail.receiver, char_s.account, char_s.name, char_r.account, char_r.name "
2162 "FROM mail,mail_items,characters as char_s,characters as char_r "
2163 "WHERE mail_items.item_template='%u' AND char_s.guid = mail.sender AND char_r.guid = mail.receiver AND mail.id=mail_items.mail_id LIMIT %u",
2164 item_id,uint32(count));
2166 else
2167 result = NULL;
2169 if(result)
2173 Field *fields = result->Fetch();
2174 uint32 item_guid = fields[0].GetUInt32();
2175 uint32 item_s = fields[1].GetUInt32();
2176 uint32 item_r = fields[2].GetUInt32();
2177 uint32 item_s_acc = fields[3].GetUInt32();
2178 std::string item_s_name = fields[4].GetCppString();
2179 uint32 item_r_acc = fields[5].GetUInt32();
2180 std::string item_r_name = fields[6].GetCppString();
2182 char const* item_pos = "[in mail]";
2184 PSendSysMessage(LANG_ITEMLIST_MAIL,
2185 item_guid,item_s_name.c_str(),item_s,item_s_acc,item_r_name.c_str(),item_r,item_r_acc,item_pos);
2186 } while (result->NextRow());
2188 int64 res_count = result->GetRowCount();
2190 delete result;
2192 if(count > res_count)
2193 count-=res_count;
2194 else if(count)
2195 count = 0;
2198 // auction case
2199 uint32 auc_count = 0;
2200 result=CharacterDatabase.PQuery("SELECT COUNT(item_template) FROM auctionhouse WHERE item_template='%u'",item_id);
2201 if(result)
2203 auc_count = (*result)[0].GetUInt32();
2204 delete result;
2207 if(count > 0)
2209 result=CharacterDatabase.PQuery(
2210 // 0 1 2 3
2211 "SELECT auctionhouse.itemguid, auctionhouse.itemowner, characters.account, characters.name "
2212 "FROM auctionhouse,characters WHERE auctionhouse.item_template='%u' AND characters.guid = auctionhouse.itemowner LIMIT %u",
2213 item_id,uint32(count));
2215 else
2216 result = NULL;
2218 if(result)
2222 Field *fields = result->Fetch();
2223 uint32 item_guid = fields[0].GetUInt32();
2224 uint32 owner = fields[1].GetUInt32();
2225 uint32 owner_acc = fields[2].GetUInt32();
2226 std::string owner_name = fields[3].GetCppString();
2228 char const* item_pos = "[in auction]";
2230 PSendSysMessage(LANG_ITEMLIST_AUCTION, item_guid, owner_name.c_str(), owner, owner_acc,item_pos);
2231 } while (result->NextRow());
2233 delete result;
2236 // guild bank case
2237 uint32 guild_count = 0;
2238 result=CharacterDatabase.PQuery("SELECT COUNT(item_entry) FROM guild_bank_item WHERE item_entry='%u'",item_id);
2239 if(result)
2241 guild_count = (*result)[0].GetUInt32();
2242 delete result;
2245 result=CharacterDatabase.PQuery(
2246 // 0 1 2
2247 "SELECT gi.item_guid, gi.guildid, guild.name "
2248 "FROM guild_bank_item AS gi, guild WHERE gi.item_entry='%u' AND gi.guildid = guild.guildid LIMIT %u ",
2249 item_id,uint32(count));
2251 if(result)
2255 Field *fields = result->Fetch();
2256 uint32 item_guid = fields[0].GetUInt32();
2257 uint32 guild_guid = fields[1].GetUInt32();
2258 std::string guild_name = fields[2].GetCppString();
2260 char const* item_pos = "[in guild bank]";
2262 PSendSysMessage(LANG_ITEMLIST_GUILD,item_guid,guild_name.c_str(),guild_guid,item_pos);
2263 } while (result->NextRow());
2265 int64 res_count = result->GetRowCount();
2267 delete result;
2269 if(count > res_count)
2270 count-=res_count;
2271 else if(count)
2272 count = 0;
2275 if(inv_count+mail_count+auc_count+guild_count == 0)
2277 SendSysMessage(LANG_COMMAND_NOITEMFOUND);
2278 SetSentErrorMessage(true);
2279 return false;
2282 PSendSysMessage(LANG_COMMAND_LISTITEMMESSAGE,item_id,inv_count+mail_count+auc_count+guild_count,inv_count,mail_count,auc_count,guild_count);
2284 return true;
2287 bool ChatHandler::HandleListObjectCommand(const char* args)
2289 if(!*args)
2290 return false;
2292 // number or [name] Shift-click form |color|Hgameobject_entry:go_id|h[name]|h|r
2293 char* cId = extractKeyFromLink((char*)args,"Hgameobject_entry");
2294 if(!cId)
2295 return false;
2297 uint32 go_id = atol(cId);
2298 if(!go_id)
2300 PSendSysMessage(LANG_COMMAND_LISTOBJINVALIDID, go_id);
2301 SetSentErrorMessage(true);
2302 return false;
2305 GameObjectInfo const * gInfo = objmgr.GetGameObjectInfo(go_id);
2306 if(!gInfo)
2308 PSendSysMessage(LANG_COMMAND_LISTOBJINVALIDID, go_id);
2309 SetSentErrorMessage(true);
2310 return false;
2313 char* c_count = strtok(NULL, " ");
2314 int count = c_count ? atol(c_count) : 10;
2316 if(count < 0)
2317 return false;
2319 QueryResult *result;
2321 uint32 obj_count = 0;
2322 result=WorldDatabase.PQuery("SELECT COUNT(guid) FROM gameobject WHERE id='%u'",go_id);
2323 if(result)
2325 obj_count = (*result)[0].GetUInt32();
2326 delete result;
2329 if(m_session)
2331 Player* pl = m_session->GetPlayer();
2332 result = WorldDatabase.PQuery("SELECT guid, position_x, position_y, position_z, map, (POW(position_x - '%f', 2) + POW(position_y - '%f', 2) + POW(position_z - '%f', 2)) AS order_ FROM gameobject WHERE id = '%u' ORDER BY order_ ASC LIMIT %u",
2333 pl->GetPositionX(), pl->GetPositionY(), pl->GetPositionZ(),go_id,uint32(count));
2335 else
2336 result = WorldDatabase.PQuery("SELECT guid, position_x, position_y, position_z, map FROM gameobject WHERE id = '%u' LIMIT %u",
2337 go_id,uint32(count));
2339 if (result)
2343 Field *fields = result->Fetch();
2344 uint32 guid = fields[0].GetUInt32();
2345 float x = fields[1].GetFloat();
2346 float y = fields[2].GetFloat();
2347 float z = fields[3].GetFloat();
2348 int mapid = fields[4].GetUInt16();
2350 if (m_session)
2351 PSendSysMessage(LANG_GO_LIST_CHAT, guid, guid, gInfo->name, x, y, z, mapid);
2352 else
2353 PSendSysMessage(LANG_GO_LIST_CONSOLE, guid, gInfo->name, x, y, z, mapid);
2354 } while (result->NextRow());
2356 delete result;
2359 PSendSysMessage(LANG_COMMAND_LISTOBJMESSAGE,go_id,obj_count);
2360 return true;
2363 bool ChatHandler::HandleNearObjectCommand(const char* args)
2365 float distance = (!*args) ? 10 : atol(args);
2366 uint32 count = 0;
2368 Player* pl = m_session->GetPlayer();
2369 QueryResult *result = WorldDatabase.PQuery("SELECT guid, id, position_x, position_y, position_z, map, "
2370 "(POW(position_x - '%f', 2) + POW(position_y - '%f', 2) + POW(position_z - '%f', 2)) AS order_ "
2371 "FROM gameobject WHERE map='%u' AND (POW(position_x - '%f', 2) + POW(position_y - '%f', 2) + POW(position_z - '%f', 2)) <= '%f' ORDER BY order_",
2372 pl->GetPositionX(), pl->GetPositionY(), pl->GetPositionZ(),
2373 pl->GetMapId(),pl->GetPositionX(), pl->GetPositionY(), pl->GetPositionZ(),distance*distance);
2375 if (result)
2379 Field *fields = result->Fetch();
2380 uint32 guid = fields[0].GetUInt32();
2381 uint32 entry = fields[1].GetUInt32();
2382 float x = fields[2].GetFloat();
2383 float y = fields[3].GetFloat();
2384 float z = fields[4].GetFloat();
2385 int mapid = fields[5].GetUInt16();
2387 GameObjectInfo const * gInfo = objmgr.GetGameObjectInfo(entry);
2389 if(!gInfo)
2390 continue;
2392 PSendSysMessage(LANG_GO_LIST_CHAT, guid, guid, gInfo->name, x, y, z, mapid);
2394 ++count;
2395 } while (result->NextRow());
2397 delete result;
2400 PSendSysMessage(LANG_COMMAND_NEAROBJMESSAGE,distance,count);
2401 return true;
2404 bool ChatHandler::HandleListCreatureCommand(const char* args)
2406 if(!*args)
2407 return false;
2409 // number or [name] Shift-click form |color|Hcreature_entry:creature_id|h[name]|h|r
2410 char* cId = extractKeyFromLink((char*)args,"Hcreature_entry");
2411 if(!cId)
2412 return false;
2414 uint32 cr_id = atol(cId);
2415 if(!cr_id)
2417 PSendSysMessage(LANG_COMMAND_INVALIDCREATUREID, cr_id);
2418 SetSentErrorMessage(true);
2419 return false;
2422 CreatureInfo const* cInfo = objmgr.GetCreatureTemplate(cr_id);
2423 if(!cInfo)
2425 PSendSysMessage(LANG_COMMAND_INVALIDCREATUREID, cr_id);
2426 SetSentErrorMessage(true);
2427 return false;
2430 char* c_count = strtok(NULL, " ");
2431 int count = c_count ? atol(c_count) : 10;
2433 if(count < 0)
2434 return false;
2436 QueryResult *result;
2438 uint32 cr_count = 0;
2439 result=WorldDatabase.PQuery("SELECT COUNT(guid) FROM creature WHERE id='%u'",cr_id);
2440 if(result)
2442 cr_count = (*result)[0].GetUInt32();
2443 delete result;
2446 if(m_session)
2448 Player* pl = m_session->GetPlayer();
2449 result = WorldDatabase.PQuery("SELECT guid, position_x, position_y, position_z, map, (POW(position_x - '%f', 2) + POW(position_y - '%f', 2) + POW(position_z - '%f', 2)) AS order_ FROM creature WHERE id = '%u' ORDER BY order_ ASC LIMIT %u",
2450 pl->GetPositionX(), pl->GetPositionY(), pl->GetPositionZ(), cr_id,uint32(count));
2452 else
2453 result = WorldDatabase.PQuery("SELECT guid, position_x, position_y, position_z, map FROM creature WHERE id = '%u' LIMIT %u",
2454 cr_id,uint32(count));
2456 if (result)
2460 Field *fields = result->Fetch();
2461 uint32 guid = fields[0].GetUInt32();
2462 float x = fields[1].GetFloat();
2463 float y = fields[2].GetFloat();
2464 float z = fields[3].GetFloat();
2465 int mapid = fields[4].GetUInt16();
2467 if (m_session)
2468 PSendSysMessage(LANG_CREATURE_LIST_CHAT, guid, guid, cInfo->Name, x, y, z, mapid);
2469 else
2470 PSendSysMessage(LANG_CREATURE_LIST_CONSOLE, guid, cInfo->Name, x, y, z, mapid);
2471 } while (result->NextRow());
2473 delete result;
2476 PSendSysMessage(LANG_COMMAND_LISTCREATUREMESSAGE,cr_id,cr_count);
2477 return true;
2480 bool ChatHandler::HandleLookupItemCommand(const char* args)
2482 if(!*args)
2483 return false;
2485 std::string namepart = args;
2486 std::wstring wnamepart;
2488 // converting string that we try to find to lower case
2489 if(!Utf8toWStr(namepart,wnamepart))
2490 return false;
2492 wstrToLower(wnamepart);
2494 uint32 counter = 0;
2496 // Search in `item_template`
2497 for (uint32 id = 0; id < sItemStorage.MaxEntry; id++)
2499 ItemPrototype const *pProto = sItemStorage.LookupEntry<ItemPrototype >(id);
2500 if(!pProto)
2501 continue;
2503 int loc_idx = m_session ? m_session->GetSessionDbLocaleIndex() : objmgr.GetDBCLocaleIndex();
2504 if ( loc_idx >= 0 )
2506 ItemLocale const *il = objmgr.GetItemLocale(pProto->ItemId);
2507 if (il)
2509 if (il->Name.size() > loc_idx && !il->Name[loc_idx].empty())
2511 std::string name = il->Name[loc_idx];
2513 if (Utf8FitTo(name, wnamepart))
2515 if (m_session)
2516 PSendSysMessage(LANG_ITEM_LIST_CHAT, id, id, name.c_str());
2517 else
2518 PSendSysMessage(LANG_ITEM_LIST_CONSOLE, id, name.c_str());
2519 ++counter;
2520 continue;
2526 std::string name = pProto->Name1;
2527 if(name.empty())
2528 continue;
2530 if (Utf8FitTo(name, wnamepart))
2532 if (m_session)
2533 PSendSysMessage(LANG_ITEM_LIST_CHAT, id, id, name.c_str());
2534 else
2535 PSendSysMessage(LANG_ITEM_LIST_CONSOLE, id, name.c_str());
2536 ++counter;
2540 if (counter==0)
2541 SendSysMessage(LANG_COMMAND_NOITEMFOUND);
2543 return true;
2546 bool ChatHandler::HandleLookupItemSetCommand(const char* args)
2548 if(!*args)
2549 return false;
2551 std::string namepart = args;
2552 std::wstring wnamepart;
2554 if(!Utf8toWStr(namepart,wnamepart))
2555 return false;
2557 // converting string that we try to find to lower case
2558 wstrToLower( wnamepart );
2560 uint32 counter = 0; // Counter for figure out that we found smth.
2562 // Search in ItemSet.dbc
2563 for (uint32 id = 0; id < sItemSetStore.GetNumRows(); id++)
2565 ItemSetEntry const *set = sItemSetStore.LookupEntry(id);
2566 if(set)
2568 int loc = m_session ? m_session->GetSessionDbcLocale() : sWorld.GetDefaultDbcLocale();
2569 std::string name = set->name[loc];
2570 if(name.empty())
2571 continue;
2573 if (!Utf8FitTo(name, wnamepart))
2575 loc = 0;
2576 for(; loc < MAX_LOCALE; ++loc)
2578 if(m_session && loc==m_session->GetSessionDbcLocale())
2579 continue;
2581 name = set->name[loc];
2582 if(name.empty())
2583 continue;
2585 if (Utf8FitTo(name, wnamepart))
2586 break;
2590 if(loc < MAX_LOCALE)
2592 // send item set in "id - [namedlink locale]" format
2593 if (m_session)
2594 PSendSysMessage(LANG_ITEMSET_LIST_CHAT,id,id,name.c_str(),localeNames[loc]);
2595 else
2596 PSendSysMessage(LANG_ITEMSET_LIST_CONSOLE,id,name.c_str(),localeNames[loc]);
2597 ++counter;
2601 if (counter == 0) // if counter == 0 then we found nth
2602 SendSysMessage(LANG_COMMAND_NOITEMSETFOUND);
2603 return true;
2606 bool ChatHandler::HandleLookupSkillCommand(const char* args)
2608 if(!*args)
2609 return false;
2611 // can be NULL in console call
2612 Player* target = getSelectedPlayer();
2614 std::string namepart = args;
2615 std::wstring wnamepart;
2617 if(!Utf8toWStr(namepart,wnamepart))
2618 return false;
2620 // converting string that we try to find to lower case
2621 wstrToLower( wnamepart );
2623 uint32 counter = 0; // Counter for figure out that we found smth.
2625 // Search in SkillLine.dbc
2626 for (uint32 id = 0; id < sSkillLineStore.GetNumRows(); id++)
2628 SkillLineEntry const *skillInfo = sSkillLineStore.LookupEntry(id);
2629 if(skillInfo)
2631 int loc = m_session ? m_session->GetSessionDbcLocale() : sWorld.GetDefaultDbcLocale();
2632 std::string name = skillInfo->name[loc];
2633 if(name.empty())
2634 continue;
2636 if (!Utf8FitTo(name, wnamepart))
2638 loc = 0;
2639 for(; loc < MAX_LOCALE; ++loc)
2641 if(m_session && loc==m_session->GetSessionDbcLocale())
2642 continue;
2644 name = skillInfo->name[loc];
2645 if(name.empty())
2646 continue;
2648 if (Utf8FitTo(name, wnamepart))
2649 break;
2653 if(loc < MAX_LOCALE)
2655 char valStr[50] = "";
2656 char const* knownStr = "";
2657 if(target && target->HasSkill(id))
2659 knownStr = GetMangosString(LANG_KNOWN);
2660 uint32 curValue = target->GetPureSkillValue(id);
2661 uint32 maxValue = target->GetPureMaxSkillValue(id);
2662 uint32 permValue = target->GetSkillPermBonusValue(id);
2663 uint32 tempValue = target->GetSkillTempBonusValue(id);
2665 char const* valFormat = GetMangosString(LANG_SKILL_VALUES);
2666 snprintf(valStr,50,valFormat,curValue,maxValue,permValue,tempValue);
2669 // send skill in "id - [namedlink locale]" format
2670 if (m_session)
2671 PSendSysMessage(LANG_SKILL_LIST_CHAT,id,id,name.c_str(),localeNames[loc],knownStr,valStr);
2672 else
2673 PSendSysMessage(LANG_SKILL_LIST_CONSOLE,id,name.c_str(),localeNames[loc],knownStr,valStr);
2675 ++counter;
2679 if (counter == 0) // if counter == 0 then we found nth
2680 SendSysMessage(LANG_COMMAND_NOSKILLFOUND);
2681 return true;
2684 bool ChatHandler::HandleLookupSpellCommand(const char* args)
2686 if(!*args)
2687 return false;
2689 // can be NULL at console call
2690 Player* target = getSelectedPlayer();
2692 std::string namepart = args;
2693 std::wstring wnamepart;
2695 if(!Utf8toWStr(namepart,wnamepart))
2696 return false;
2698 // converting string that we try to find to lower case
2699 wstrToLower( wnamepart );
2701 uint32 counter = 0; // Counter for figure out that we found smth.
2703 // Search in Spell.dbc
2704 for (uint32 id = 0; id < sSpellStore.GetNumRows(); id++)
2706 SpellEntry const *spellInfo = sSpellStore.LookupEntry(id);
2707 if(spellInfo)
2709 int loc = m_session ? m_session->GetSessionDbcLocale() : sWorld.GetDefaultDbcLocale();
2710 std::string name = spellInfo->SpellName[loc];
2711 if(name.empty())
2712 continue;
2714 if (!Utf8FitTo(name, wnamepart))
2716 loc = 0;
2717 for(; loc < MAX_LOCALE; ++loc)
2719 if(m_session && loc==m_session->GetSessionDbcLocale())
2720 continue;
2722 name = spellInfo->SpellName[loc];
2723 if(name.empty())
2724 continue;
2726 if (Utf8FitTo(name, wnamepart))
2727 break;
2731 if(loc < MAX_LOCALE)
2733 bool known = target && target->HasSpell(id);
2734 bool learn = (spellInfo->Effect[0] == SPELL_EFFECT_LEARN_SPELL);
2736 uint32 talentCost = GetTalentSpellCost(id);
2738 bool talent = (talentCost > 0);
2739 bool passive = IsPassiveSpell(id);
2740 bool active = target && target->HasAura(id);
2742 // unit32 used to prevent interpreting uint8 as char at output
2743 // find rank of learned spell for learning spell, or talent rank
2744 uint32 rank = talentCost ? talentCost : spellmgr.GetSpellRank(learn ? spellInfo->EffectTriggerSpell[0] : id);
2746 // send spell in "id - [name, rank N] [talent] [passive] [learn] [known]" format
2747 std::ostringstream ss;
2748 if (m_session)
2749 ss << id << " - |cffffffff|Hspell:" << id << "|h[" << name;
2750 else
2751 ss << id << " - " << name;
2753 // include rank in link name
2754 if(rank)
2755 ss << GetMangosString(LANG_SPELL_RANK) << rank;
2757 if (m_session)
2758 ss << " " << localeNames[loc] << "]|h|r";
2759 else
2760 ss << " " << localeNames[loc];
2762 if(talent)
2763 ss << GetMangosString(LANG_TALENT);
2764 if(passive)
2765 ss << GetMangosString(LANG_PASSIVE);
2766 if(learn)
2767 ss << GetMangosString(LANG_LEARN);
2768 if(known)
2769 ss << GetMangosString(LANG_KNOWN);
2770 if(active)
2771 ss << GetMangosString(LANG_ACTIVE);
2773 SendSysMessage(ss.str().c_str());
2775 ++counter;
2779 if (counter == 0) // if counter == 0 then we found nth
2780 SendSysMessage(LANG_COMMAND_NOSPELLFOUND);
2781 return true;
2784 bool ChatHandler::HandleLookupQuestCommand(const char* args)
2786 if(!*args)
2787 return false;
2789 // can be NULL at console call
2790 Player* target = getSelectedPlayer();
2792 std::string namepart = args;
2793 std::wstring wnamepart;
2795 // converting string that we try to find to lower case
2796 if(!Utf8toWStr(namepart,wnamepart))
2797 return false;
2799 wstrToLower(wnamepart);
2801 uint32 counter = 0 ;
2803 ObjectMgr::QuestMap const& qTemplates = objmgr.GetQuestTemplates();
2804 for (ObjectMgr::QuestMap::const_iterator iter = qTemplates.begin(); iter != qTemplates.end(); ++iter)
2806 Quest * qinfo = iter->second;
2808 int loc_idx = m_session ? m_session->GetSessionDbLocaleIndex() : objmgr.GetDBCLocaleIndex();
2809 if ( loc_idx >= 0 )
2811 QuestLocale const *il = objmgr.GetQuestLocale(qinfo->GetQuestId());
2812 if (il)
2814 if (il->Title.size() > loc_idx && !il->Title[loc_idx].empty())
2816 std::string title = il->Title[loc_idx];
2818 if (Utf8FitTo(title, wnamepart))
2820 char const* statusStr = "";
2822 if(target)
2824 QuestStatus status = target->GetQuestStatus(qinfo->GetQuestId());
2826 if(status == QUEST_STATUS_COMPLETE)
2828 if(target->GetQuestRewardStatus(qinfo->GetQuestId()))
2829 statusStr = GetMangosString(LANG_COMMAND_QUEST_REWARDED);
2830 else
2831 statusStr = GetMangosString(LANG_COMMAND_QUEST_COMPLETE);
2833 else if(status == QUEST_STATUS_INCOMPLETE)
2834 statusStr = GetMangosString(LANG_COMMAND_QUEST_ACTIVE);
2837 if (m_session)
2838 PSendSysMessage(LANG_QUEST_LIST_CHAT,qinfo->GetQuestId(),qinfo->GetQuestId(),title.c_str(),statusStr);
2839 else
2840 PSendSysMessage(LANG_QUEST_LIST_CONSOLE,qinfo->GetQuestId(),title.c_str(),statusStr);
2841 ++counter;
2842 continue;
2848 std::string title = qinfo->GetTitle();
2849 if(title.empty())
2850 continue;
2852 if (Utf8FitTo(title, wnamepart))
2854 char const* statusStr = "";
2856 if(target)
2858 QuestStatus status = target->GetQuestStatus(qinfo->GetQuestId());
2860 if(status == QUEST_STATUS_COMPLETE)
2862 if(target->GetQuestRewardStatus(qinfo->GetQuestId()))
2863 statusStr = GetMangosString(LANG_COMMAND_QUEST_REWARDED);
2864 else
2865 statusStr = GetMangosString(LANG_COMMAND_QUEST_COMPLETE);
2867 else if(status == QUEST_STATUS_INCOMPLETE)
2868 statusStr = GetMangosString(LANG_COMMAND_QUEST_ACTIVE);
2871 if (m_session)
2872 PSendSysMessage(LANG_QUEST_LIST_CHAT,qinfo->GetQuestId(),qinfo->GetQuestId(),title.c_str(),statusStr);
2873 else
2874 PSendSysMessage(LANG_QUEST_LIST_CONSOLE,qinfo->GetQuestId(),title.c_str(),statusStr);
2876 ++counter;
2880 if (counter==0)
2881 SendSysMessage(LANG_COMMAND_NOQUESTFOUND);
2883 return true;
2886 bool ChatHandler::HandleLookupCreatureCommand(const char* args)
2888 if (!*args)
2889 return false;
2891 std::string namepart = args;
2892 std::wstring wnamepart;
2894 // converting string that we try to find to lower case
2895 if (!Utf8toWStr (namepart,wnamepart))
2896 return false;
2898 wstrToLower (wnamepart);
2900 uint32 counter = 0;
2902 for (uint32 id = 0; id< sCreatureStorage.MaxEntry; ++id)
2904 CreatureInfo const* cInfo = sCreatureStorage.LookupEntry<CreatureInfo> (id);
2905 if(!cInfo)
2906 continue;
2908 int loc_idx = m_session ? m_session->GetSessionDbLocaleIndex() : objmgr.GetDBCLocaleIndex();
2909 if (loc_idx >= 0)
2911 CreatureLocale const *cl = objmgr.GetCreatureLocale (id);
2912 if (cl)
2914 if (cl->Name.size() > loc_idx && !cl->Name[loc_idx].empty ())
2916 std::string name = cl->Name[loc_idx];
2918 if (Utf8FitTo (name, wnamepart))
2920 if (m_session)
2921 PSendSysMessage (LANG_CREATURE_ENTRY_LIST_CHAT, id, id, name.c_str ());
2922 else
2923 PSendSysMessage (LANG_CREATURE_ENTRY_LIST_CONSOLE, id, name.c_str ());
2924 ++counter;
2925 continue;
2931 std::string name = cInfo->Name;
2932 if (name.empty ())
2933 continue;
2935 if (Utf8FitTo(name, wnamepart))
2937 if (m_session)
2938 PSendSysMessage (LANG_CREATURE_ENTRY_LIST_CHAT, id, id, name.c_str ());
2939 else
2940 PSendSysMessage (LANG_CREATURE_ENTRY_LIST_CONSOLE, id, name.c_str ());
2941 ++counter;
2945 if (counter==0)
2946 SendSysMessage (LANG_COMMAND_NOCREATUREFOUND);
2948 return true;
2951 bool ChatHandler::HandleLookupObjectCommand(const char* args)
2953 if(!*args)
2954 return false;
2956 std::string namepart = args;
2957 std::wstring wnamepart;
2959 // converting string that we try to find to lower case
2960 if(!Utf8toWStr(namepart,wnamepart))
2961 return false;
2963 wstrToLower(wnamepart);
2965 uint32 counter = 0;
2967 for (uint32 id = 0; id< sGOStorage.MaxEntry; id++ )
2969 GameObjectInfo const* gInfo = sGOStorage.LookupEntry<GameObjectInfo>(id);
2970 if(!gInfo)
2971 continue;
2973 int loc_idx = m_session ? m_session->GetSessionDbLocaleIndex() : objmgr.GetDBCLocaleIndex();
2974 if ( loc_idx >= 0 )
2976 GameObjectLocale const *gl = objmgr.GetGameObjectLocale(id);
2977 if (gl)
2979 if (gl->Name.size() > loc_idx && !gl->Name[loc_idx].empty())
2981 std::string name = gl->Name[loc_idx];
2983 if (Utf8FitTo(name, wnamepart))
2985 if (m_session)
2986 PSendSysMessage(LANG_GO_ENTRY_LIST_CHAT, id, id, name.c_str());
2987 else
2988 PSendSysMessage(LANG_GO_ENTRY_LIST_CONSOLE, id, name.c_str());
2989 ++counter;
2990 continue;
2996 std::string name = gInfo->name;
2997 if(name.empty())
2998 continue;
3000 if(Utf8FitTo(name, wnamepart))
3002 if (m_session)
3003 PSendSysMessage(LANG_GO_ENTRY_LIST_CHAT, id, id, name.c_str());
3004 else
3005 PSendSysMessage(LANG_GO_ENTRY_LIST_CONSOLE, id, name.c_str());
3006 ++counter;
3010 if(counter==0)
3011 SendSysMessage(LANG_COMMAND_NOGAMEOBJECTFOUND);
3013 return true;
3016 /** \brief GM command level 3 - Create a guild.
3018 * This command allows a GM (level 3) to create a guild.
3020 * The "args" parameter contains the name of the guild leader
3021 * and then the name of the guild.
3024 bool ChatHandler::HandleGuildCreateCommand(const char* args)
3027 if (!*args)
3028 return false;
3030 char *lname = strtok ((char*)args, " ");
3031 char *gname = strtok (NULL, "");
3033 if (!lname)
3034 return false;
3036 if (!gname)
3038 SendSysMessage (LANG_INSERT_GUILD_NAME);
3039 SetSentErrorMessage (true);
3040 return false;
3043 std::string guildname = gname;
3045 Player* player = ObjectAccessor::Instance ().FindPlayerByName (lname);
3046 if (!player)
3048 SendSysMessage (LANG_PLAYER_NOT_FOUND);
3049 SetSentErrorMessage (true);
3050 return false;
3053 if (player->GetGuildId())
3055 SendSysMessage (LANG_PLAYER_IN_GUILD);
3056 return true;
3059 Guild *guild = new Guild;
3060 if (!guild->create (player->GetGUID (),guildname))
3062 delete guild;
3063 SendSysMessage (LANG_GUILD_NOT_CREATED);
3064 SetSentErrorMessage (true);
3065 return false;
3068 objmgr.AddGuild (guild);
3069 return true;
3072 bool ChatHandler::HandleGuildInviteCommand(const char *args)
3074 if (!*args)
3075 return false;
3077 char* par1 = strtok ((char*)args, " ");
3078 char* par2 = strtok (NULL, "");
3079 if(!par1 || !par2)
3080 return false;
3082 std::string glName = par2;
3083 Guild* targetGuild = objmgr.GetGuildByName (glName);
3084 if (!targetGuild)
3085 return false;
3087 std::string plName = extractPlayerNameFromLink(par1);
3088 if(plName.empty())
3090 SendSysMessage(LANG_PLAYER_NOT_FOUND);
3091 SetSentErrorMessage(true);
3092 return false;
3095 uint64 plGuid = 0;
3096 if (Player* targetPlayer = ObjectAccessor::Instance ().FindPlayerByName (plName.c_str ()))
3097 plGuid = targetPlayer->GetGUID ();
3098 else
3099 plGuid = objmgr.GetPlayerGUIDByName (plName);
3101 if (!plGuid)
3102 false;
3104 // player's guild membership checked in AddMember before add
3105 if (!targetGuild->AddMember (plGuid,targetGuild->GetLowestRank ()))
3106 return false;
3108 return true;
3111 bool ChatHandler::HandleGuildUninviteCommand(const char *args)
3113 if (!*args)
3114 return false;
3116 char* par1 = strtok ((char*)args, " ");
3117 if(!par1)
3118 return false;
3120 std::string plName = extractPlayerNameFromLink(par1);
3121 if(plName.empty())
3123 SendSysMessage(LANG_PLAYER_NOT_FOUND);
3124 SetSentErrorMessage(true);
3125 return false;
3128 uint64 plGuid = 0;
3129 uint32 glId = 0;
3130 if (Player* targetPlayer = ObjectAccessor::Instance ().FindPlayerByName (plName.c_str ()))
3132 plGuid = targetPlayer->GetGUID ();
3133 glId = targetPlayer->GetGuildId ();
3135 else
3137 plGuid = objmgr.GetPlayerGUIDByName (plName);
3138 glId = Player::GetGuildIdFromDB (plGuid);
3141 if (!plGuid || !glId)
3142 return false;
3144 Guild* targetGuild = objmgr.GetGuildById (glId);
3145 if (!targetGuild)
3146 return false;
3148 targetGuild->DelMember (plGuid);
3150 return true;
3153 bool ChatHandler::HandleGuildRankCommand(const char *args)
3155 if (!*args)
3156 return false;
3158 char* par1 = strtok ((char*)args, " ");
3159 char* par2 = strtok (NULL, " ");
3160 if (!par1 || !par2)
3161 return false;
3163 std::string plName = extractPlayerNameFromLink(par1);
3164 if(plName.empty())
3166 SendSysMessage(LANG_PLAYER_NOT_FOUND);
3167 SetSentErrorMessage(true);
3168 return false;
3172 uint64 plGuid = 0;
3173 uint32 glId = 0;
3174 if (Player* targetPlayer = ObjectAccessor::Instance ().FindPlayerByName (plName.c_str ()))
3176 plGuid = targetPlayer->GetGUID ();
3177 glId = targetPlayer->GetGuildId ();
3179 else
3181 plGuid = objmgr.GetPlayerGUIDByName (plName);
3182 glId = Player::GetGuildIdFromDB (plGuid);
3185 if (!plGuid || !glId)
3186 return false;
3188 Guild* targetGuild = objmgr.GetGuildById (glId);
3189 if (!targetGuild)
3190 return false;
3192 uint32 newrank = uint32 (atoi (par2));
3193 if (newrank > targetGuild->GetLowestRank ())
3194 return false;
3196 targetGuild->ChangeRank (plGuid,newrank);
3198 return true;
3201 bool ChatHandler::HandleGuildDeleteCommand(const char* args)
3203 if (!*args)
3204 return false;
3206 char* par1 = strtok ((char*)args, " ");
3207 if (!par1)
3208 return false;
3210 std::string gld = par1;
3212 Guild* targetGuild = objmgr.GetGuildByName (gld);
3213 if (!targetGuild)
3214 return false;
3216 targetGuild->Disband ();
3218 return true;
3221 bool ChatHandler::HandleGetDistanceCommand(const char* /*args*/)
3223 Unit* pUnit = getSelectedUnit();
3225 if(!pUnit)
3227 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
3228 SetSentErrorMessage(true);
3229 return false;
3232 PSendSysMessage(LANG_DISTANCE, m_session->GetPlayer()->GetDistance(pUnit),m_session->GetPlayer()->GetDistance2d(pUnit));
3234 return true;
3237 // FIX-ME!!!
3239 bool ChatHandler::HandleAddWeaponCommand(const char* /*args*/)
3241 /*if (!*args)
3242 return false;
3244 uint64 guid = m_session->GetPlayer()->GetSelection();
3245 if (guid == 0)
3247 SendSysMessage(LANG_NO_SELECTION);
3248 return true;
3251 Creature *pCreature = ObjectAccessor::GetCreature(*m_session->GetPlayer(), guid);
3253 if(!pCreature)
3255 SendSysMessage(LANG_SELECT_CREATURE);
3256 return true;
3259 char* pSlotID = strtok((char*)args, " ");
3260 if (!pSlotID)
3261 return false;
3263 char* pItemID = strtok(NULL, " ");
3264 if (!pItemID)
3265 return false;
3267 uint32 ItemID = atoi(pItemID);
3268 uint32 SlotID = atoi(pSlotID);
3270 ItemPrototype* tmpItem = objmgr.GetItemPrototype(ItemID);
3272 bool added = false;
3273 if(tmpItem)
3275 switch(SlotID)
3277 case 1:
3278 pCreature->SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_DISPLAY, ItemID);
3279 added = true;
3280 break;
3281 case 2:
3282 pCreature->SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_DISPLAY_01, ItemID);
3283 added = true;
3284 break;
3285 case 3:
3286 pCreature->SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_DISPLAY_02, ItemID);
3287 added = true;
3288 break;
3289 default:
3290 PSendSysMessage(LANG_ITEM_SLOT_NOT_EXIST,SlotID);
3291 added = false;
3292 break;
3294 if(added)
3296 PSendSysMessage(LANG_ITEM_ADDED_TO_SLOT,ItemID,tmpItem->Name1,SlotID);
3299 else
3301 PSendSysMessage(LANG_ITEM_NOT_FOUND,ItemID);
3302 return true;
3305 return true;
3308 bool ChatHandler::HandleDieCommand(const char* /*args*/)
3310 Unit* target = getSelectedUnit();
3312 if(!target || !m_session->GetPlayer()->GetSelection())
3314 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
3315 SetSentErrorMessage(true);
3316 return false;
3319 if(target->GetTypeId()==TYPEID_PLAYER)
3321 if(HasLowerSecurity((Player*)target,0,false))
3322 return false;
3325 if( target->isAlive() )
3327 m_session->GetPlayer()->DealDamage(target, target->GetHealth(), NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
3330 return true;
3333 bool ChatHandler::HandleDamageCommand(const char * args)
3335 if (!*args)
3336 return false;
3338 Unit* target = getSelectedUnit();
3340 if(!target || !m_session->GetPlayer()->GetSelection())
3342 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
3343 SetSentErrorMessage(true);
3344 return false;
3347 if( !target->isAlive() )
3348 return true;
3350 char* damageStr = strtok((char*)args, " ");
3351 if(!damageStr)
3352 return false;
3354 int32 damage = atoi((char*)damageStr);
3355 if(damage <=0)
3356 return true;
3358 char* schoolStr = strtok((char*)NULL, " ");
3360 // flat melee damage without resistence/etc reduction
3361 if(!schoolStr)
3363 m_session->GetPlayer()->DealDamage(target, damage, NULL, DIRECT_DAMAGE, SPELL_SCHOOL_MASK_NORMAL, NULL, false);
3364 m_session->GetPlayer()->SendAttackStateUpdate (HITINFO_NORMALSWING2, target, 1, SPELL_SCHOOL_MASK_NORMAL, damage, 0, 0, VICTIMSTATE_NORMAL, 0);
3365 return true;
3368 uint32 school = schoolStr ? atoi((char*)schoolStr) : SPELL_SCHOOL_NORMAL;
3369 if(school >= MAX_SPELL_SCHOOL)
3370 return false;
3372 SpellSchoolMask schoolmask = SpellSchoolMask(1 << school);
3374 if ( schoolmask & SPELL_SCHOOL_MASK_NORMAL )
3375 damage = m_session->GetPlayer()->CalcArmorReducedDamage(target, damage);
3377 char* spellStr = strtok((char*)NULL, " ");
3379 // melee damage by specific school
3380 if(!spellStr)
3382 uint32 absorb = 0;
3383 uint32 resist = 0;
3385 m_session->GetPlayer()->CalcAbsorbResist(target,schoolmask, SPELL_DIRECT_DAMAGE, damage, &absorb, &resist);
3387 if (damage <= absorb + resist)
3388 return true;
3390 damage -= absorb + resist;
3392 m_session->GetPlayer()->DealDamage(target, damage, NULL, DIRECT_DAMAGE, schoolmask, NULL, false);
3393 m_session->GetPlayer()->SendAttackStateUpdate (HITINFO_NORMALSWING2, target, 1, schoolmask, damage, absorb, resist, VICTIMSTATE_NORMAL, 0);
3394 return true;
3397 // non-melee damage
3399 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
3400 uint32 spellid = extractSpellIdFromLink((char*)args);
3401 if(!spellid || !sSpellStore.LookupEntry(spellid))
3402 return false;
3404 m_session->GetPlayer()->SpellNonMeleeDamageLog(target, spellid, damage, false);
3405 return true;
3408 bool ChatHandler::HandleModifyArenaCommand(const char * args)
3410 if (!*args)
3411 return false;
3413 Player *target = getSelectedPlayer();
3414 if(!target)
3416 SendSysMessage(LANG_PLAYER_NOT_FOUND);
3417 SetSentErrorMessage(true);
3418 return false;
3421 int32 amount = (uint32)atoi(args);
3423 target->ModifyArenaPoints(amount);
3425 PSendSysMessage(LANG_COMMAND_MODIFY_ARENA, GetNameLink(target).c_str(), target->GetArenaPoints());
3427 return true;
3430 bool ChatHandler::HandleReviveCommand(const char* args)
3432 Player* SelectedPlayer = NULL;
3434 if (*args)
3436 std::string name = extractPlayerNameFromLink((char*)args);
3437 if(name.empty())
3439 SendSysMessage(LANG_PLAYER_NOT_FOUND);
3440 SetSentErrorMessage(true);
3441 return false;
3444 SelectedPlayer = objmgr.GetPlayer(name.c_str());
3446 else
3447 SelectedPlayer = getSelectedPlayer();
3449 if(!SelectedPlayer)
3451 SendSysMessage(LANG_NO_CHAR_SELECTED);
3452 SetSentErrorMessage(true);
3453 return false;
3456 SelectedPlayer->ResurrectPlayer(0.5f);
3457 SelectedPlayer->SpawnCorpseBones();
3458 SelectedPlayer->SaveToDB();
3459 return true;
3462 bool ChatHandler::HandleAuraCommand(const char* args)
3464 Unit *target = getSelectedUnit();
3465 if(!target)
3467 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
3468 SetSentErrorMessage(true);
3469 return false;
3472 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
3473 uint32 spellID = extractSpellIdFromLink((char*)args);
3475 SpellEntry const *spellInfo = sSpellStore.LookupEntry( spellID );
3476 if(spellInfo)
3478 for(uint32 i = 0;i<3;i++)
3480 uint8 eff = spellInfo->Effect[i];
3481 if (eff>=TOTAL_SPELL_EFFECTS)
3482 continue;
3483 if( IsAreaAuraEffect(eff) ||
3484 eff == SPELL_EFFECT_APPLY_AURA ||
3485 eff == SPELL_EFFECT_PERSISTENT_AREA_AURA )
3487 Aura *Aur = CreateAura(spellInfo, i, NULL, target);
3488 target->AddAura(Aur);
3493 return true;
3496 bool ChatHandler::HandleUnAuraCommand(const char* args)
3498 Unit *target = getSelectedUnit();
3499 if(!target)
3501 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
3502 SetSentErrorMessage(true);
3503 return false;
3506 std::string argstr = args;
3507 if (argstr == "all")
3509 target->RemoveAllAuras();
3510 return true;
3513 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
3514 uint32 spellID = extractSpellIdFromLink((char*)args);
3515 if(!spellID)
3516 return false;
3518 target->RemoveAurasDueToSpell(spellID);
3520 return true;
3523 bool ChatHandler::HandleLinkGraveCommand(const char* args)
3525 if(!*args)
3526 return false;
3528 char* px = strtok((char*)args, " ");
3529 if (!px)
3530 return false;
3532 uint32 g_id = (uint32)atoi(px);
3534 uint32 g_team;
3536 char* px2 = strtok(NULL, " ");
3538 if (!px2)
3539 g_team = 0;
3540 else if (strncmp(px2,"horde",6)==0)
3541 g_team = HORDE;
3542 else if (strncmp(px2,"alliance",9)==0)
3543 g_team = ALLIANCE;
3544 else
3545 return false;
3547 WorldSafeLocsEntry const* graveyard = sWorldSafeLocsStore.LookupEntry(g_id);
3549 if(!graveyard )
3551 PSendSysMessage(LANG_COMMAND_GRAVEYARDNOEXIST, g_id);
3552 SetSentErrorMessage(true);
3553 return false;
3556 Player* player = m_session->GetPlayer();
3558 uint32 zoneId = player->GetZoneId();
3560 AreaTableEntry const *areaEntry = GetAreaEntryByAreaID(zoneId);
3561 if(!areaEntry || areaEntry->zone !=0 )
3563 PSendSysMessage(LANG_COMMAND_GRAVEYARDWRONGZONE, g_id,zoneId);
3564 SetSentErrorMessage(true);
3565 return false;
3568 if(objmgr.AddGraveYardLink(g_id,player->GetZoneId(),g_team))
3569 PSendSysMessage(LANG_COMMAND_GRAVEYARDLINKED, g_id,zoneId);
3570 else
3571 PSendSysMessage(LANG_COMMAND_GRAVEYARDALRLINKED, g_id,zoneId);
3573 return true;
3576 bool ChatHandler::HandleNearGraveCommand(const char* args)
3578 uint32 g_team;
3580 size_t argslen = strlen(args);
3582 if(!*args)
3583 g_team = 0;
3584 else if (strncmp((char*)args,"horde",argslen)==0)
3585 g_team = HORDE;
3586 else if (strncmp((char*)args,"alliance",argslen)==0)
3587 g_team = ALLIANCE;
3588 else
3589 return false;
3591 Player* player = m_session->GetPlayer();
3593 WorldSafeLocsEntry const* graveyard = objmgr.GetClosestGraveYard(
3594 player->GetPositionX(), player->GetPositionY(), player->GetPositionZ(),player->GetMapId(),g_team);
3596 if(graveyard)
3598 uint32 g_id = graveyard->ID;
3600 GraveYardData const* data = objmgr.FindGraveYardData(g_id,player->GetZoneId());
3601 if (!data)
3603 PSendSysMessage(LANG_COMMAND_GRAVEYARDERROR,g_id);
3604 SetSentErrorMessage(true);
3605 return false;
3608 g_team = data->team;
3610 std::string team_name = GetMangosString(LANG_COMMAND_GRAVEYARD_NOTEAM);
3612 if(g_team == 0)
3613 team_name = GetMangosString(LANG_COMMAND_GRAVEYARD_ANY);
3614 else if(g_team == HORDE)
3615 team_name = GetMangosString(LANG_COMMAND_GRAVEYARD_HORDE);
3616 else if(g_team == ALLIANCE)
3617 team_name = GetMangosString(LANG_COMMAND_GRAVEYARD_ALLIANCE);
3619 PSendSysMessage(LANG_COMMAND_GRAVEYARDNEAREST, g_id,team_name.c_str(),player->GetZoneId());
3621 else
3623 std::string team_name;
3625 if(g_team == 0)
3626 team_name = GetMangosString(LANG_COMMAND_GRAVEYARD_ANY);
3627 else if(g_team == HORDE)
3628 team_name = GetMangosString(LANG_COMMAND_GRAVEYARD_HORDE);
3629 else if(g_team == ALLIANCE)
3630 team_name = GetMangosString(LANG_COMMAND_GRAVEYARD_ALLIANCE);
3632 if(g_team == ~uint32(0))
3633 PSendSysMessage(LANG_COMMAND_ZONENOGRAVEYARDS, player->GetZoneId());
3634 else
3635 PSendSysMessage(LANG_COMMAND_ZONENOGRAFACTION, player->GetZoneId(),team_name.c_str());
3638 return true;
3641 //play npc emote
3642 bool ChatHandler::HandleNpcPlayEmoteCommand(const char* args)
3644 uint32 emote = atoi((char*)args);
3646 Creature* target = getSelectedCreature();
3647 if(!target)
3649 SendSysMessage(LANG_SELECT_CREATURE);
3650 SetSentErrorMessage(true);
3651 return false;
3654 target->SetUInt32Value(UNIT_NPC_EMOTESTATE,emote);
3656 return true;
3659 bool ChatHandler::HandleNpcInfoCommand(const char* /*args*/)
3661 Creature* target = getSelectedCreature();
3663 if(!target)
3665 SendSysMessage(LANG_SELECT_CREATURE);
3666 SetSentErrorMessage(true);
3667 return false;
3670 uint32 faction = target->getFaction();
3671 uint32 npcflags = target->GetUInt32Value(UNIT_NPC_FLAGS);
3672 uint32 displayid = target->GetDisplayId();
3673 uint32 nativeid = target->GetNativeDisplayId();
3674 uint32 Entry = target->GetEntry();
3675 CreatureInfo const* cInfo = target->GetCreatureInfo();
3677 int32 curRespawnDelay = target->GetRespawnTimeEx()-time(NULL);
3678 if(curRespawnDelay < 0)
3679 curRespawnDelay = 0;
3680 std::string curRespawnDelayStr = secsToTimeString(curRespawnDelay,true);
3681 std::string defRespawnDelayStr = secsToTimeString(target->GetRespawnDelay(),true);
3683 PSendSysMessage(LANG_NPCINFO_CHAR, target->GetDBTableGUIDLow(), faction, npcflags, Entry, displayid, nativeid);
3684 PSendSysMessage(LANG_NPCINFO_LEVEL, target->getLevel());
3685 PSendSysMessage(LANG_NPCINFO_HEALTH,target->GetCreateHealth(), target->GetMaxHealth(), target->GetHealth());
3686 PSendSysMessage(LANG_NPCINFO_FLAGS, target->GetUInt32Value(UNIT_FIELD_FLAGS), target->GetUInt32Value(UNIT_DYNAMIC_FLAGS), target->getFaction());
3687 PSendSysMessage(LANG_COMMAND_RAWPAWNTIMES, defRespawnDelayStr.c_str(),curRespawnDelayStr.c_str());
3688 PSendSysMessage(LANG_NPCINFO_LOOT, cInfo->lootid,cInfo->pickpocketLootId,cInfo->SkinLootId);
3689 PSendSysMessage(LANG_NPCINFO_DUNGEON_ID, target->GetInstanceId());
3690 PSendSysMessage(LANG_NPCINFO_POSITION,float(target->GetPositionX()), float(target->GetPositionY()), float(target->GetPositionZ()));
3692 if ((npcflags & UNIT_NPC_FLAG_VENDOR) )
3694 SendSysMessage(LANG_NPCINFO_VENDOR);
3696 if ((npcflags & UNIT_NPC_FLAG_TRAINER) )
3698 SendSysMessage(LANG_NPCINFO_TRAINER);
3701 return true;
3704 bool ChatHandler::HandleExploreCheatCommand(const char* args)
3706 if (!*args)
3707 return false;
3709 int flag = atoi((char*)args);
3711 Player *chr = getSelectedPlayer();
3712 if (chr == NULL)
3714 SendSysMessage(LANG_NO_CHAR_SELECTED);
3715 SetSentErrorMessage(true);
3716 return false;
3719 if (flag != 0)
3721 PSendSysMessage(LANG_YOU_SET_EXPLORE_ALL, GetNameLink(chr).c_str());
3722 if (needReportToTarget(chr))
3723 ChatHandler(chr).PSendSysMessage(LANG_YOURS_EXPLORE_SET_ALL,GetNameLink().c_str());
3725 else
3727 PSendSysMessage(LANG_YOU_SET_EXPLORE_NOTHING, GetNameLink(chr).c_str());
3728 if (needReportToTarget(chr))
3729 ChatHandler(chr).PSendSysMessage(LANG_YOURS_EXPLORE_SET_NOTHING,GetNameLink().c_str());
3732 for (uint8 i=0; i<128; i++)
3734 if (flag != 0)
3736 m_session->GetPlayer()->SetFlag(PLAYER_EXPLORED_ZONES_1+i,0xFFFFFFFF);
3738 else
3740 m_session->GetPlayer()->SetFlag(PLAYER_EXPLORED_ZONES_1+i,0);
3744 return true;
3747 bool ChatHandler::HandleHoverCommand(const char* args)
3749 char* px = strtok((char*)args, " ");
3750 uint32 flag;
3751 if (!px)
3752 flag = 1;
3753 else
3754 flag = atoi(px);
3756 m_session->GetPlayer()->SetHover(flag);
3758 if (flag)
3759 SendSysMessage(LANG_HOVER_ENABLED);
3760 else
3761 SendSysMessage(LANG_HOVER_DISABLED);
3763 return true;
3766 bool ChatHandler::HandleLevelUpCommand(const char* args)
3768 char* px = strtok((char*)args, " ");
3769 char* py = strtok((char*)NULL, " ");
3771 // command format parsing
3772 char* pname = (char*)NULL;
3773 int addlevel = 1;
3775 if(px && py) // .levelup name level
3777 addlevel = atoi(py);
3778 pname = px;
3780 else if(px && !py) // .levelup name OR .levelup level
3782 if(isalpha(px[0])) // .levelup name
3783 pname = px;
3784 else // .levelup level
3785 addlevel = atoi(px);
3787 // else .levelup - nothing do for preparing
3789 // player
3790 Player *chr = NULL;
3791 uint64 chr_guid = 0;
3793 std::string name;
3795 if(pname) // player by name
3797 name = extractPlayerNameFromLink(pname);
3798 if(name.empty())
3800 SendSysMessage(LANG_PLAYER_NOT_FOUND);
3801 SetSentErrorMessage(true);
3802 return false;
3805 chr = objmgr.GetPlayer(name.c_str());
3806 if(!chr) // not in game
3808 chr_guid = objmgr.GetPlayerGUIDByName(name);
3809 if (chr_guid == 0)
3811 SendSysMessage(LANG_PLAYER_NOT_FOUND);
3812 SetSentErrorMessage(true);
3813 return false;
3817 else // player by selection
3819 chr = getSelectedPlayer();
3821 if (chr == NULL)
3823 SendSysMessage(LANG_NO_CHAR_SELECTED);
3824 SetSentErrorMessage(true);
3825 return false;
3828 name = GetNameLink(chr);
3831 assert(chr || chr_guid);
3833 int32 oldlevel = chr ? chr->getLevel() : Player::GetUInt32ValueFromDB(UNIT_FIELD_LEVEL,chr_guid);
3834 int32 newlevel = oldlevel + addlevel;
3835 if(newlevel < 1)
3836 newlevel = 1;
3837 if(newlevel > STRONG_MAX_LEVEL) // hardcoded maximum level
3838 newlevel = STRONG_MAX_LEVEL;
3840 if(chr)
3842 chr->GiveLevel(newlevel);
3843 chr->InitTalentForLevel();
3844 chr->SetUInt32Value(PLAYER_XP,0);
3846 if(oldlevel == newlevel)
3847 ChatHandler(chr).SendSysMessage(LANG_YOURS_LEVEL_PROGRESS_RESET);
3848 else
3849 if(oldlevel < newlevel)
3850 ChatHandler(chr).PSendSysMessage(LANG_YOURS_LEVEL_UP,newlevel-oldlevel);
3851 else
3852 if(oldlevel > newlevel)
3853 ChatHandler(chr).PSendSysMessage(LANG_YOURS_LEVEL_DOWN,newlevel-oldlevel);
3855 else
3857 // update level and XP at level, all other will be updated at loading
3858 Tokens values;
3859 Player::LoadValuesArrayFromDB(values,chr_guid);
3860 Player::SetUInt32ValueInArray(values,UNIT_FIELD_LEVEL,newlevel);
3861 Player::SetUInt32ValueInArray(values,PLAYER_XP,0);
3862 Player::SaveValuesArrayInDB(values,chr_guid);
3865 if(m_session->GetPlayer() != chr) // including chr==NULL
3867 std::string nameLink = playerLink(name);
3868 PSendSysMessage(LANG_YOU_CHANGE_LVL,nameLink.c_str(),newlevel);
3870 return true;
3873 bool ChatHandler::HandleShowAreaCommand(const char* args)
3875 if (!*args)
3876 return false;
3878 Player *chr = getSelectedPlayer();
3879 if (chr == NULL)
3881 SendSysMessage(LANG_NO_CHAR_SELECTED);
3882 SetSentErrorMessage(true);
3883 return false;
3886 int area = GetAreaFlagByAreaID(atoi((char*)args));
3887 int offset = area / 32;
3888 uint32 val = (uint32)(1 << (area % 32));
3890 if(area<0 || offset >= 128)
3892 SendSysMessage(LANG_BAD_VALUE);
3893 SetSentErrorMessage(true);
3894 return false;
3897 uint32 currFields = chr->GetUInt32Value(PLAYER_EXPLORED_ZONES_1 + offset);
3898 chr->SetUInt32Value(PLAYER_EXPLORED_ZONES_1 + offset, (uint32)(currFields | val));
3900 SendSysMessage(LANG_EXPLORE_AREA);
3901 return true;
3904 bool ChatHandler::HandleHideAreaCommand(const char* args)
3906 if (!*args)
3907 return false;
3909 Player *chr = getSelectedPlayer();
3910 if (chr == NULL)
3912 SendSysMessage(LANG_NO_CHAR_SELECTED);
3913 SetSentErrorMessage(true);
3914 return false;
3917 int area = GetAreaFlagByAreaID(atoi((char*)args));
3918 int offset = area / 32;
3919 uint32 val = (uint32)(1 << (area % 32));
3921 if(area<0 || offset >= 128)
3923 SendSysMessage(LANG_BAD_VALUE);
3924 SetSentErrorMessage(true);
3925 return false;
3928 uint32 currFields = chr->GetUInt32Value(PLAYER_EXPLORED_ZONES_1 + offset);
3929 chr->SetUInt32Value(PLAYER_EXPLORED_ZONES_1 + offset, (uint32)(currFields ^ val));
3931 SendSysMessage(LANG_UNEXPLORE_AREA);
3932 return true;
3935 bool ChatHandler::HandleUpdate(const char* args)
3937 if(!*args)
3938 return false;
3940 uint32 updateIndex;
3941 uint32 value;
3943 char* pUpdateIndex = strtok((char*)args, " ");
3945 Unit* chr = getSelectedUnit();
3946 if (chr == NULL)
3948 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
3949 SetSentErrorMessage(true);
3950 return false;
3953 if(!pUpdateIndex)
3955 return true;
3957 updateIndex = atoi(pUpdateIndex);
3958 //check updateIndex
3959 if(chr->GetTypeId() == TYPEID_PLAYER)
3961 if (updateIndex>=PLAYER_END) return true;
3963 else
3965 if (updateIndex>=UNIT_END) return true;
3968 char* pvalue = strtok(NULL, " ");
3969 if (!pvalue)
3971 value=chr->GetUInt32Value(updateIndex);
3973 PSendSysMessage(LANG_UPDATE, chr->GetGUIDLow(),updateIndex,value);
3974 return true;
3977 value=atoi(pvalue);
3979 PSendSysMessage(LANG_UPDATE_CHANGE, chr->GetGUIDLow(),updateIndex,value);
3981 chr->SetUInt32Value(updateIndex,value);
3983 return true;
3986 bool ChatHandler::HandleBankCommand(const char* /*args*/)
3988 m_session->SendShowBank( m_session->GetPlayer()->GetGUID() );
3990 return true;
3993 bool ChatHandler::HandleChangeWeather(const char* args)
3995 if(!*args)
3996 return false;
3998 //Weather is OFF
3999 if (!sWorld.getConfig(CONFIG_WEATHER))
4001 SendSysMessage(LANG_WEATHER_DISABLED);
4002 SetSentErrorMessage(true);
4003 return false;
4006 //*Change the weather of a cell
4007 char* px = strtok((char*)args, " ");
4008 char* py = strtok(NULL, " ");
4010 if (!px || !py)
4011 return false;
4013 uint32 type = (uint32)atoi(px); //0 to 3, 0: fine, 1: rain, 2: snow, 3: sand
4014 float grade = (float)atof(py); //0 to 1, sending -1 is instand good weather
4016 Player *player = m_session->GetPlayer();
4017 uint32 zoneid = player->GetZoneId();
4019 Weather* wth = sWorld.FindWeather(zoneid);
4021 if(!wth)
4022 wth = sWorld.AddWeather(zoneid);
4023 if(!wth)
4025 SendSysMessage(LANG_NO_WEATHER);
4026 SetSentErrorMessage(true);
4027 return false;
4030 wth->SetWeather(WeatherType(type), grade);
4032 return true;
4035 bool ChatHandler::HandleSetValue(const char* args)
4037 if(!*args)
4038 return false;
4040 char* px = strtok((char*)args, " ");
4041 char* py = strtok(NULL, " ");
4042 char* pz = strtok(NULL, " ");
4044 if (!px || !py)
4045 return false;
4047 Unit* target = getSelectedUnit();
4048 if(!target)
4050 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
4051 SetSentErrorMessage(true);
4052 return false;
4055 uint64 guid = target->GetGUID();
4057 uint32 Opcode = (uint32)atoi(px);
4058 if(Opcode >= target->GetValuesCount())
4060 PSendSysMessage(LANG_TOO_BIG_INDEX, Opcode, GUID_LOPART(guid), target->GetValuesCount());
4061 return false;
4063 uint32 iValue;
4064 float fValue;
4065 bool isint32 = true;
4066 if(pz)
4067 isint32 = (bool)atoi(pz);
4068 if(isint32)
4070 iValue = (uint32)atoi(py);
4071 sLog.outDebug(GetMangosString(LANG_SET_UINT), GUID_LOPART(guid), Opcode, iValue);
4072 target->SetUInt32Value( Opcode , iValue );
4073 PSendSysMessage(LANG_SET_UINT_FIELD, GUID_LOPART(guid), Opcode,iValue);
4075 else
4077 fValue = (float)atof(py);
4078 sLog.outDebug(GetMangosString(LANG_SET_FLOAT), GUID_LOPART(guid), Opcode, fValue);
4079 target->SetFloatValue( Opcode , fValue );
4080 PSendSysMessage(LANG_SET_FLOAT_FIELD, GUID_LOPART(guid), Opcode,fValue);
4083 return true;
4086 bool ChatHandler::HandleGetValue(const char* args)
4088 if(!*args)
4089 return false;
4091 char* px = strtok((char*)args, " ");
4092 char* pz = strtok(NULL, " ");
4094 if (!px)
4095 return false;
4097 Unit* target = getSelectedUnit();
4098 if(!target)
4100 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
4101 SetSentErrorMessage(true);
4102 return false;
4105 uint64 guid = target->GetGUID();
4107 uint32 Opcode = (uint32)atoi(px);
4108 if(Opcode >= target->GetValuesCount())
4110 PSendSysMessage(LANG_TOO_BIG_INDEX, Opcode, GUID_LOPART(guid), target->GetValuesCount());
4111 return false;
4113 uint32 iValue;
4114 float fValue;
4115 bool isint32 = true;
4116 if(pz)
4117 isint32 = (bool)atoi(pz);
4119 if(isint32)
4121 iValue = target->GetUInt32Value( Opcode );
4122 sLog.outDebug(GetMangosString(LANG_GET_UINT), GUID_LOPART(guid), Opcode, iValue);
4123 PSendSysMessage(LANG_GET_UINT_FIELD, GUID_LOPART(guid), Opcode, iValue);
4125 else
4127 fValue = target->GetFloatValue( Opcode );
4128 sLog.outDebug(GetMangosString(LANG_GET_FLOAT), GUID_LOPART(guid), Opcode, fValue);
4129 PSendSysMessage(LANG_GET_FLOAT_FIELD, GUID_LOPART(guid), Opcode, fValue);
4132 return true;
4135 bool ChatHandler::HandleSet32Bit(const char* args)
4137 if(!*args)
4138 return false;
4140 char* px = strtok((char*)args, " ");
4141 char* py = strtok(NULL, " ");
4143 if (!px || !py)
4144 return false;
4146 uint32 Opcode = (uint32)atoi(px);
4147 uint32 Value = (uint32)atoi(py);
4148 if (Value > 32) //uint32 = 32 bits
4149 return false;
4151 sLog.outDebug(GetMangosString(LANG_SET_32BIT), Opcode, Value);
4153 m_session->GetPlayer( )->SetUInt32Value( Opcode , 2^Value );
4155 PSendSysMessage(LANG_SET_32BIT_FIELD, Opcode,1);
4156 return true;
4159 bool ChatHandler::HandleMod32Value(const char* args)
4161 if(!*args)
4162 return false;
4164 char* px = strtok((char*)args, " ");
4165 char* py = strtok(NULL, " ");
4167 if (!px || !py)
4168 return false;
4170 uint32 Opcode = (uint32)atoi(px);
4171 int Value = atoi(py);
4173 if(Opcode >= m_session->GetPlayer()->GetValuesCount())
4175 PSendSysMessage(LANG_TOO_BIG_INDEX, Opcode, m_session->GetPlayer()->GetGUIDLow(), m_session->GetPlayer( )->GetValuesCount());
4176 return false;
4179 sLog.outDebug(GetMangosString(LANG_CHANGE_32BIT), Opcode, Value);
4181 int CurrentValue = (int)m_session->GetPlayer( )->GetUInt32Value( Opcode );
4183 CurrentValue += Value;
4184 m_session->GetPlayer( )->SetUInt32Value( Opcode , (uint32)CurrentValue );
4186 PSendSysMessage(LANG_CHANGE_32BIT_FIELD, Opcode,CurrentValue);
4188 return true;
4191 bool ChatHandler::HandleAddTeleCommand(const char * args)
4193 if(!*args)
4194 return false;
4196 Player *player=m_session->GetPlayer();
4197 if (!player)
4198 return false;
4200 std::string name = args;
4202 if(objmgr.GetGameTele(name))
4204 SendSysMessage(LANG_COMMAND_TP_ALREADYEXIST);
4205 SetSentErrorMessage(true);
4206 return false;
4209 GameTele tele;
4210 tele.position_x = player->GetPositionX();
4211 tele.position_y = player->GetPositionY();
4212 tele.position_z = player->GetPositionZ();
4213 tele.orientation = player->GetOrientation();
4214 tele.mapId = player->GetMapId();
4215 tele.name = name;
4217 if(objmgr.AddGameTele(tele))
4219 SendSysMessage(LANG_COMMAND_TP_ADDED);
4221 else
4223 SendSysMessage(LANG_COMMAND_TP_ADDEDERR);
4224 SetSentErrorMessage(true);
4225 return false;
4228 return true;
4231 bool ChatHandler::HandleDelTeleCommand(const char * args)
4233 if(!*args)
4234 return false;
4236 std::string name = args;
4238 if(!objmgr.DeleteGameTele(name))
4240 SendSysMessage(LANG_COMMAND_TELE_NOTFOUND);
4241 SetSentErrorMessage(true);
4242 return false;
4245 SendSysMessage(LANG_COMMAND_TP_DELETED);
4246 return true;
4249 bool ChatHandler::HandleListAurasCommand (const char * /*args*/)
4251 Unit *unit = getSelectedUnit();
4252 if(!unit)
4254 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
4255 SetSentErrorMessage(true);
4256 return false;
4259 char const* talentStr = GetMangosString(LANG_TALENT);
4260 char const* passiveStr = GetMangosString(LANG_PASSIVE);
4262 Unit::AuraMap const& uAuras = unit->GetAuras();
4263 PSendSysMessage(LANG_COMMAND_TARGET_LISTAURAS, uAuras.size());
4264 for (Unit::AuraMap::const_iterator itr = uAuras.begin(); itr != uAuras.end(); ++itr)
4266 bool talent = GetTalentSpellCost(itr->second->GetId()) > 0;
4268 char const* name = itr->second->GetSpellProto()->SpellName[m_session->GetSessionDbcLocale()];
4270 if (m_session)
4272 std::ostringstream ss_name;
4273 ss_name << "|cffffffff|Hspell:" << itr->second->GetId() << "|h[" << name << "]|h|r";
4275 PSendSysMessage(LANG_COMMAND_TARGET_AURADETAIL, itr->second->GetId(), itr->second->GetEffIndex(),
4276 itr->second->GetModifier()->m_auraname, itr->second->GetAuraDuration(), itr->second->GetAuraMaxDuration(),
4277 ss_name.str().c_str(),
4278 (itr->second->IsPassive() ? passiveStr : ""),(talent ? talentStr : ""),
4279 IS_PLAYER_GUID(itr->second->GetCasterGUID()) ? "player" : "creature",GUID_LOPART(itr->second->GetCasterGUID()));
4281 else
4283 PSendSysMessage(LANG_COMMAND_TARGET_AURADETAIL, itr->second->GetId(), itr->second->GetEffIndex(),
4284 itr->second->GetModifier()->m_auraname, itr->second->GetAuraDuration(), itr->second->GetAuraMaxDuration(),
4285 name,
4286 (itr->second->IsPassive() ? passiveStr : ""),(talent ? talentStr : ""),
4287 IS_PLAYER_GUID(itr->second->GetCasterGUID()) ? "player" : "creature",GUID_LOPART(itr->second->GetCasterGUID()));
4290 for (int i = 0; i < TOTAL_AURAS; i++)
4292 Unit::AuraList const& uAuraList = unit->GetAurasByType(AuraType(i));
4293 if (uAuraList.empty()) continue;
4294 PSendSysMessage(LANG_COMMAND_TARGET_LISTAURATYPE, uAuraList.size(), i);
4295 for (Unit::AuraList::const_iterator itr = uAuraList.begin(); itr != uAuraList.end(); ++itr)
4297 bool talent = GetTalentSpellCost((*itr)->GetId()) > 0;
4299 char const* name = (*itr)->GetSpellProto()->SpellName[m_session->GetSessionDbcLocale()];
4301 if (m_session)
4303 std::ostringstream ss_name;
4304 ss_name << "|cffffffff|Hspell:" << (*itr)->GetId() << "|h[" << name << "]|h|r";
4306 PSendSysMessage(LANG_COMMAND_TARGET_AURASIMPLE, (*itr)->GetId(), (*itr)->GetEffIndex(),
4307 ss_name.str().c_str(),((*itr)->IsPassive() ? passiveStr : ""),(talent ? talentStr : ""),
4308 IS_PLAYER_GUID((*itr)->GetCasterGUID()) ? "player" : "creature",GUID_LOPART((*itr)->GetCasterGUID()));
4310 else
4312 PSendSysMessage(LANG_COMMAND_TARGET_AURASIMPLE, (*itr)->GetId(), (*itr)->GetEffIndex(),
4313 name,((*itr)->IsPassive() ? passiveStr : ""),(talent ? talentStr : ""),
4314 IS_PLAYER_GUID((*itr)->GetCasterGUID()) ? "player" : "creature",GUID_LOPART((*itr)->GetCasterGUID()));
4318 return true;
4321 bool ChatHandler::HandleResetAchievementsCommand (const char * args)
4323 char* pName = strtok((char*)args, "");
4324 Player *player = NULL;
4325 uint64 guid = 0;
4326 if (pName)
4328 std::string name = extractPlayerNameFromLink(pName);
4329 if(name.empty())
4331 SendSysMessage(LANG_PLAYER_NOT_FOUND);
4332 SetSentErrorMessage(true);
4333 return false;
4336 guid = objmgr.GetPlayerGUIDByName(name);
4337 player = objmgr.GetPlayer(guid);
4339 else
4341 player = getSelectedPlayer();
4342 if(player)
4343 guid = player->GetGUID();
4346 if(!player && !guid)
4348 SendSysMessage(LANG_NO_CHAR_SELECTED);
4349 return true;
4352 if(player)
4353 player->GetAchievementMgr().Reset();
4354 else if(guid)
4355 AchievementMgr::DeleteFromDB(GUID_LOPART(guid));
4357 return true;
4360 bool ChatHandler::HandleResetHonorCommand (const char * args)
4362 char* pName = strtok((char*)args, "");
4363 Player *player = NULL;
4364 if (pName)
4366 std::string name = extractPlayerNameFromLink(pName);
4367 if(name.empty())
4369 SendSysMessage(LANG_PLAYER_NOT_FOUND);
4370 SetSentErrorMessage(true);
4371 return false;
4374 uint64 guid = objmgr.GetPlayerGUIDByName(name);
4375 player = objmgr.GetPlayer(guid);
4377 else
4378 player = getSelectedPlayer();
4380 if(!player)
4382 SendSysMessage(LANG_NO_CHAR_SELECTED);
4383 return true;
4386 player->SetUInt32Value(PLAYER_FIELD_KILLS, 0);
4387 player->SetUInt32Value(PLAYER_FIELD_LIFETIME_HONORBALE_KILLS, 0);
4388 player->SetUInt32Value(PLAYER_FIELD_HONOR_CURRENCY, 0);
4389 player->SetUInt32Value(PLAYER_FIELD_TODAY_CONTRIBUTION, 0);
4390 player->SetUInt32Value(PLAYER_FIELD_YESTERDAY_CONTRIBUTION, 0);
4392 return true;
4395 static bool HandleResetStatsOrLevelHelper(Player* player)
4397 PlayerInfo const *info = objmgr.GetPlayerInfo(player->getRace(), player->getClass());
4398 if(!info) return false;
4400 ChrClassesEntry const* cEntry = sChrClassesStore.LookupEntry(player->getClass());
4401 if(!cEntry)
4403 sLog.outError("Class %u not found in DBC (Wrong DBC files?)",player->getClass());
4404 return false;
4407 uint8 powertype = cEntry->powerType;
4409 // reset m_form if no aura
4410 if(!player->HasAuraType(SPELL_AURA_MOD_SHAPESHIFT))
4411 player->m_form = FORM_NONE;
4413 player->SetFloatValue(UNIT_FIELD_BOUNDINGRADIUS, DEFAULT_WORLD_OBJECT_SIZE );
4414 player->SetFloatValue(UNIT_FIELD_COMBATREACH, 1.5f );
4416 player->setFactionForRace(player->getRace());
4418 player->SetUInt32Value(UNIT_FIELD_BYTES_0, ( ( player->getRace() ) | ( player->getClass() << 8 ) | ( player->getGender() << 16 ) | ( powertype << 24 ) ) );
4420 // reset only if player not in some form;
4421 if(player->m_form==FORM_NONE)
4423 switch(player->getGender())
4425 case GENDER_FEMALE:
4426 player->SetDisplayId(info->displayId_f);
4427 player->SetNativeDisplayId(info->displayId_f);
4428 break;
4429 case GENDER_MALE:
4430 player->SetDisplayId(info->displayId_m);
4431 player->SetNativeDisplayId(info->displayId_m);
4432 break;
4433 default:
4434 break;
4438 player->SetByteValue(UNIT_FIELD_BYTES_2, 1, UNIT_BYTE2_FLAG_PVP );
4439 player->SetByteValue(UNIT_FIELD_BYTES_2, 3, player->m_form);
4441 player->SetUInt32Value(UNIT_FIELD_FLAGS, UNIT_FLAG_PVP_ATTACKABLE);
4443 //-1 is default value
4444 player->SetUInt32Value(PLAYER_FIELD_WATCHED_FACTION_INDEX, uint32(-1));
4446 //player->SetUInt32Value(PLAYER_FIELD_BYTES, 0xEEE00000 );
4447 return true;
4450 bool ChatHandler::HandleResetLevelCommand(const char * args)
4452 char* pName = strtok((char*)args, "");
4453 Player *player = NULL;
4454 if (pName)
4456 std::string name = extractPlayerNameFromLink(pName);
4457 if(name.empty())
4459 SendSysMessage(LANG_PLAYER_NOT_FOUND);
4460 SetSentErrorMessage(true);
4461 return false;
4464 uint64 guid = objmgr.GetPlayerGUIDByName(name);
4465 player = objmgr.GetPlayer(guid);
4467 else
4468 player = getSelectedPlayer();
4470 if(!player)
4472 SendSysMessage(LANG_NO_CHAR_SELECTED);
4473 SetSentErrorMessage(true);
4474 return false;
4477 if(!HandleResetStatsOrLevelHelper(player))
4478 return false;
4480 // set starting level
4481 uint32 start_level = player->getClass() != CLASS_DEATH_KNIGHT
4482 ? sWorld.getConfig(CONFIG_START_PLAYER_LEVEL)
4483 : sWorld.getConfig(CONFIG_START_HEROIC_PLAYER_LEVEL);
4485 player->SetLevel(start_level);
4486 player->InitRunes();
4487 player->InitStatsForLevel(true);
4488 player->InitTaxiNodesForLevel();
4489 player->InitGlyphsForLevel();
4490 player->InitTalentForLevel();
4491 player->SetUInt32Value(PLAYER_XP,0);
4493 // reset level to summoned pet
4494 Pet* pet = player->GetPet();
4495 if(pet && pet->getPetType()==SUMMON_PET)
4497 pet->InitStatsForLevel(1);
4498 pet->InitTalentForLevel();
4500 return true;
4503 bool ChatHandler::HandleResetStatsCommand(const char * args)
4505 char* pName = strtok((char*)args, "");
4506 Player *player = NULL;
4507 if (pName)
4509 std::string name = extractPlayerNameFromLink(pName);
4510 if(name.empty())
4512 SendSysMessage(LANG_PLAYER_NOT_FOUND);
4513 SetSentErrorMessage(true);
4514 return false;
4517 uint64 guid = objmgr.GetPlayerGUIDByName(name);
4518 player = objmgr.GetPlayer(guid);
4520 else
4521 player = getSelectedPlayer();
4523 if(!player)
4525 SendSysMessage(LANG_NO_CHAR_SELECTED);
4526 SetSentErrorMessage(true);
4527 return false;
4530 if(!HandleResetStatsOrLevelHelper(player))
4531 return false;
4533 player->InitRunes();
4534 player->InitStatsForLevel(true);
4535 player->InitTaxiNodesForLevel();
4536 player->InitGlyphsForLevel();
4537 player->InitTalentForLevel();
4539 return true;
4542 bool ChatHandler::HandleResetSpellsCommand(const char * args)
4544 char* pName = strtok((char*)args, "");
4545 Player *player = NULL;
4546 uint64 playerGUID = 0;
4547 if (pName)
4549 std::string name = extractPlayerNameFromLink(pName);
4550 if(name.empty())
4552 SendSysMessage(LANG_PLAYER_NOT_FOUND);
4553 SetSentErrorMessage(true);
4554 return false;
4557 player = objmgr.GetPlayer(name.c_str());
4558 if(!player)
4559 playerGUID = objmgr.GetPlayerGUIDByName(name);
4561 else
4562 player = getSelectedPlayer();
4564 if(!player && !playerGUID)
4566 SendSysMessage(LANG_NO_CHAR_SELECTED);
4567 SetSentErrorMessage(true);
4568 return false;
4571 if(player)
4573 player->resetSpells();
4575 ChatHandler(player).SendSysMessage(LANG_RESET_SPELLS);
4576 if(m_session->GetPlayer()!=player)
4577 PSendSysMessage(LANG_RESET_SPELLS_ONLINE,GetNameLink(player).c_str());
4579 else
4581 CharacterDatabase.PExecute("UPDATE characters SET at_login = at_login | '%u' WHERE guid = '%u'",uint32(AT_LOGIN_RESET_SPELLS), GUID_LOPART(playerGUID));
4582 PSendSysMessage(LANG_RESET_SPELLS_OFFLINE,pName);
4585 return true;
4588 bool ChatHandler::HandleResetTalentsCommand(const char * args)
4590 char* pName = strtok((char*)args, "");
4591 Player *player = NULL;
4592 uint64 playerGUID = 0;
4593 if (pName)
4595 std::string name = extractPlayerNameFromLink(pName);
4596 if(name.empty())
4598 SendSysMessage(LANG_PLAYER_NOT_FOUND);
4599 SetSentErrorMessage(true);
4600 return false;
4603 player = objmgr.GetPlayer(name.c_str());
4604 if(!player)
4605 playerGUID = objmgr.GetPlayerGUIDByName(name);
4607 else
4608 player = getSelectedPlayer();
4610 if(player)
4612 player->resetTalents(true);
4614 ChatHandler(player).SendSysMessage(LANG_RESET_TALENTS);
4615 if(m_session->GetPlayer()!=player)
4616 PSendSysMessage(LANG_RESET_TALENTS_ONLINE,GetNameLink(player).c_str());
4618 return true;
4620 else if (playerGUID)
4622 CharacterDatabase.PExecute("UPDATE characters SET at_login = at_login | '%u' WHERE guid = '%u'",uint32(AT_LOGIN_RESET_TALENTS), GUID_LOPART(playerGUID) );
4623 std::string nameLink = playerLink(pName);
4624 PSendSysMessage(LANG_RESET_TALENTS_OFFLINE,nameLink.c_str());
4625 return true;
4627 // Try reset talenents as Hunter Pet
4628 Creature* creature = getSelectedCreature();
4629 if (creature && creature->isPet() && ((Pet *)creature)->getPetType() == HUNTER_PET)
4631 ((Pet *)creature)->resetTalents(true);
4632 Unit *owner = creature->GetOwner();
4633 if (owner && owner->GetTypeId() == TYPEID_PLAYER)
4635 player = (Player *)owner;
4636 ChatHandler(player).SendSysMessage(LANG_RESET_TALENTS);
4637 if(m_session->GetPlayer()!=player)
4638 PSendSysMessage(LANG_RESET_TALENTS_ONLINE,GetNameLink(player).c_str());
4640 return true;
4643 SendSysMessage(LANG_NO_CHAR_SELECTED);
4644 SetSentErrorMessage(true);
4645 return false;
4648 bool ChatHandler::HandleResetAllCommand(const char * args)
4650 if(!*args)
4651 return false;
4653 std::string casename = args;
4655 AtLoginFlags atLogin;
4657 // Command specially created as single command to prevent using short case names
4658 if(casename=="spells")
4660 atLogin = AT_LOGIN_RESET_SPELLS;
4661 sWorld.SendWorldText(LANG_RESETALL_SPELLS);
4663 else if(casename=="talents")
4665 atLogin = AT_LOGIN_RESET_TALENTS;
4666 sWorld.SendWorldText(LANG_RESETALL_TALENTS);
4668 else
4670 PSendSysMessage(LANG_RESETALL_UNKNOWN_CASE,args);
4671 SetSentErrorMessage(true);
4672 return false;
4675 CharacterDatabase.PExecute("UPDATE characters SET at_login = at_login | '%u' WHERE (at_login & '%u') = '0'",atLogin,atLogin);
4676 HashMapHolder<Player>::MapType const& plist = ObjectAccessor::Instance().GetPlayers();
4677 for(HashMapHolder<Player>::MapType::const_iterator itr = plist.begin(); itr != plist.end(); ++itr)
4678 itr->second->SetAtLoginFlag(atLogin);
4680 return true;
4683 bool ChatHandler::HandleServerShutDownCancelCommand(const char* args)
4685 sWorld.ShutdownCancel();
4686 return true;
4689 bool ChatHandler::HandleServerShutDownCommand(const char* args)
4691 if(!*args)
4692 return false;
4694 char* time_str = strtok ((char*) args, " ");
4695 char* exitcode_str = strtok (NULL, "");
4697 int32 time = atoi (time_str);
4699 ///- Prevent interpret wrong arg value as 0 secs shutdown time
4700 if(time == 0 && (time_str[0]!='0' || time_str[1]!='\0') || time < 0)
4701 return false;
4703 if (exitcode_str)
4705 int32 exitcode = atoi (exitcode_str);
4707 // Handle atoi() errors
4708 if (exitcode == 0 && (exitcode_str[0] != '0' || exitcode_str[1] != '\0'))
4709 return false;
4711 // Exit code should be in range of 0-125, 126-255 is used
4712 // in many shells for their own return codes and code > 255
4713 // is not supported in many others
4714 if (exitcode < 0 || exitcode > 125)
4715 return false;
4717 sWorld.ShutdownServ (time, 0, exitcode);
4719 else
4720 sWorld.ShutdownServ(time,0,SHUTDOWN_EXIT_CODE);
4721 return true;
4724 bool ChatHandler::HandleServerRestartCommand(const char* args)
4726 if(!*args)
4727 return false;
4729 char* time_str = strtok ((char*) args, " ");
4730 char* exitcode_str = strtok (NULL, "");
4732 int32 time = atoi (time_str);
4734 ///- Prevent interpret wrong arg value as 0 secs shutdown time
4735 if(time == 0 && (time_str[0]!='0' || time_str[1]!='\0') || time < 0)
4736 return false;
4738 if (exitcode_str)
4740 int32 exitcode = atoi (exitcode_str);
4742 // Handle atoi() errors
4743 if (exitcode == 0 && (exitcode_str[0] != '0' || exitcode_str[1] != '\0'))
4744 return false;
4746 // Exit code should be in range of 0-125, 126-255 is used
4747 // in many shells for their own return codes and code > 255
4748 // is not supported in many others
4749 if (exitcode < 0 || exitcode > 125)
4750 return false;
4752 sWorld.ShutdownServ (time, SHUTDOWN_MASK_RESTART, exitcode);
4754 else
4755 sWorld.ShutdownServ(time, SHUTDOWN_MASK_RESTART, RESTART_EXIT_CODE);
4756 return true;
4759 bool ChatHandler::HandleServerIdleRestartCommand(const char* args)
4761 if(!*args)
4762 return false;
4764 char* time_str = strtok ((char*) args, " ");
4765 char* exitcode_str = strtok (NULL, "");
4767 int32 time = atoi (time_str);
4769 ///- Prevent interpret wrong arg value as 0 secs shutdown time
4770 if(time == 0 && (time_str[0]!='0' || time_str[1]!='\0') || time < 0)
4771 return false;
4773 if (exitcode_str)
4775 int32 exitcode = atoi (exitcode_str);
4777 // Handle atoi() errors
4778 if (exitcode == 0 && (exitcode_str[0] != '0' || exitcode_str[1] != '\0'))
4779 return false;
4781 // Exit code should be in range of 0-125, 126-255 is used
4782 // in many shells for their own return codes and code > 255
4783 // is not supported in many others
4784 if (exitcode < 0 || exitcode > 125)
4785 return false;
4787 sWorld.ShutdownServ (time, SHUTDOWN_MASK_RESTART|SHUTDOWN_MASK_IDLE, exitcode);
4789 else
4790 sWorld.ShutdownServ(time,SHUTDOWN_MASK_RESTART|SHUTDOWN_MASK_IDLE,RESTART_EXIT_CODE);
4791 return true;
4794 bool ChatHandler::HandleServerIdleShutDownCommand(const char* args)
4796 if(!*args)
4797 return false;
4799 char* time_str = strtok ((char*) args, " ");
4800 char* exitcode_str = strtok (NULL, "");
4802 int32 time = atoi (time_str);
4804 ///- Prevent interpret wrong arg value as 0 secs shutdown time
4805 if(time == 0 && (time_str[0]!='0' || time_str[1]!='\0') || time < 0)
4806 return false;
4808 if (exitcode_str)
4810 int32 exitcode = atoi (exitcode_str);
4812 // Handle atoi() errors
4813 if (exitcode == 0 && (exitcode_str[0] != '0' || exitcode_str[1] != '\0'))
4814 return false;
4816 // Exit code should be in range of 0-125, 126-255 is used
4817 // in many shells for their own return codes and code > 255
4818 // is not supported in many others
4819 if (exitcode < 0 || exitcode > 125)
4820 return false;
4822 sWorld.ShutdownServ (time, SHUTDOWN_MASK_IDLE, exitcode);
4824 else
4825 sWorld.ShutdownServ(time,SHUTDOWN_MASK_IDLE,SHUTDOWN_EXIT_CODE);
4826 return true;
4829 bool ChatHandler::HandleAddQuest(const char* args)
4831 Player* player = getSelectedPlayer();
4832 if(!player)
4834 SendSysMessage(LANG_NO_CHAR_SELECTED);
4835 SetSentErrorMessage(true);
4836 return false;
4839 // .addquest #entry'
4840 // number or [name] Shift-click form |color|Hquest:quest_id|h[name]|h|r
4841 char* cId = extractKeyFromLink((char*)args,"Hquest");
4842 if(!cId)
4843 return false;
4845 uint32 entry = atol(cId);
4847 Quest const* pQuest = objmgr.GetQuestTemplate(entry);
4849 if(!pQuest)
4851 PSendSysMessage(LANG_COMMAND_QUEST_NOTFOUND,entry);
4852 SetSentErrorMessage(true);
4853 return false;
4856 // check item starting quest (it can work incorrectly if added without item in inventory)
4857 for (uint32 id = 0; id < sItemStorage.MaxEntry; id++)
4859 ItemPrototype const *pProto = sItemStorage.LookupEntry<ItemPrototype>(id);
4860 if (!pProto)
4861 continue;
4863 if (pProto->StartQuest == entry)
4865 PSendSysMessage(LANG_COMMAND_QUEST_STARTFROMITEM, entry, pProto->ItemId);
4866 SetSentErrorMessage(true);
4867 return false;
4871 // ok, normal (creature/GO starting) quest
4872 if( player->CanAddQuest( pQuest, true ) )
4874 player->AddQuest( pQuest, NULL );
4876 if ( player->CanCompleteQuest( entry ) )
4877 player->CompleteQuest( entry );
4880 return true;
4883 bool ChatHandler::HandleRemoveQuest(const char* args)
4885 Player* player = getSelectedPlayer();
4886 if(!player)
4888 SendSysMessage(LANG_NO_CHAR_SELECTED);
4889 SetSentErrorMessage(true);
4890 return false;
4893 // .removequest #entry'
4894 // number or [name] Shift-click form |color|Hquest:quest_id|h[name]|h|r
4895 char* cId = extractKeyFromLink((char*)args,"Hquest");
4896 if(!cId)
4897 return false;
4899 uint32 entry = atol(cId);
4901 Quest const* pQuest = objmgr.GetQuestTemplate(entry);
4903 if(!pQuest)
4905 PSendSysMessage(LANG_COMMAND_QUEST_NOTFOUND, entry);
4906 SetSentErrorMessage(true);
4907 return false;
4910 // remove all quest entries for 'entry' from quest log
4911 for(uint8 slot = 0; slot < MAX_QUEST_LOG_SIZE; ++slot )
4913 uint32 quest = player->GetQuestSlotQuestId(slot);
4914 if(quest==entry)
4916 player->SetQuestSlot(slot,0);
4918 // we ignore unequippable quest items in this case, its' still be equipped
4919 player->TakeQuestSourceItem( quest, false );
4923 // set quest status to not started (will updated in DB at next save)
4924 player->SetQuestStatus( entry, QUEST_STATUS_NONE);
4926 // reset rewarded for restart repeatable quest
4927 player->getQuestStatusMap()[entry].m_rewarded = false;
4929 SendSysMessage(LANG_COMMAND_QUEST_REMOVED);
4930 return true;
4933 bool ChatHandler::HandleCompleteQuest(const char* args)
4935 Player* player = getSelectedPlayer();
4936 if(!player)
4938 SendSysMessage(LANG_NO_CHAR_SELECTED);
4939 SetSentErrorMessage(true);
4940 return false;
4943 // .quest complete #entry
4944 // number or [name] Shift-click form |color|Hquest:quest_id|h[name]|h|r
4945 char* cId = extractKeyFromLink((char*)args,"Hquest");
4946 if(!cId)
4947 return false;
4949 uint32 entry = atol(cId);
4951 Quest const* pQuest = objmgr.GetQuestTemplate(entry);
4953 // If player doesn't have the quest
4954 if(!pQuest || player->GetQuestStatus(entry) == QUEST_STATUS_NONE)
4956 PSendSysMessage(LANG_COMMAND_QUEST_NOTFOUND, entry);
4957 SetSentErrorMessage(true);
4958 return false;
4961 // Add quest items for quests that require items
4962 for(uint8 x = 0; x < QUEST_OBJECTIVES_COUNT; ++x)
4964 uint32 id = pQuest->ReqItemId[x];
4965 uint32 count = pQuest->ReqItemCount[x];
4966 if(!id || !count)
4967 continue;
4969 uint32 curItemCount = player->GetItemCount(id,true);
4971 ItemPosCountVec dest;
4972 uint8 msg = player->CanStoreNewItem( NULL_BAG, NULL_SLOT, dest, id, count-curItemCount );
4973 if( msg == EQUIP_ERR_OK )
4975 Item* item = player->StoreNewItem( dest, id, true);
4976 player->SendNewItem(item,count-curItemCount,true,false);
4980 // All creature/GO slain/casted (not required, but otherwise it will display "Creature slain 0/10")
4981 for(uint8 i = 0; i < QUEST_OBJECTIVES_COUNT; i++)
4983 uint32 creature = pQuest->ReqCreatureOrGOId[i];
4984 uint32 creaturecount = pQuest->ReqCreatureOrGOCount[i];
4986 if(uint32 spell_id = pQuest->ReqSpell[i])
4988 for(uint16 z = 0; z < creaturecount; ++z)
4989 player->CastedCreatureOrGO(creature,0,spell_id);
4991 else if(creature > 0)
4993 for(uint16 z = 0; z < creaturecount; ++z)
4994 player->KilledMonster(creature,0);
4996 else if(creature < 0)
4998 for(uint16 z = 0; z < creaturecount; ++z)
4999 player->CastedCreatureOrGO(creature,0,0);
5003 // If the quest requires reputation to complete
5004 if(uint32 repFaction = pQuest->GetRepObjectiveFaction())
5006 uint32 repValue = pQuest->GetRepObjectiveValue();
5007 uint32 curRep = player->GetReputation(repFaction);
5008 if(curRep < repValue)
5010 FactionEntry const *factionEntry = sFactionStore.LookupEntry(repFaction);
5011 player->SetFactionReputation(factionEntry,repValue);
5015 // If the quest requires money
5016 int32 ReqOrRewMoney = pQuest->GetRewOrReqMoney();
5017 if(ReqOrRewMoney < 0)
5018 player->ModifyMoney(-ReqOrRewMoney);
5020 player->CompleteQuest(entry);
5021 return true;
5024 bool ChatHandler::HandleBanAccountCommand(const char* args)
5026 return HandleBanHelper(BAN_ACCOUNT,args);
5029 bool ChatHandler::HandleBanCharacterCommand(const char* args)
5031 return HandleBanHelper(BAN_CHARACTER,args);
5034 bool ChatHandler::HandleBanIPCommand(const char* args)
5036 return HandleBanHelper(BAN_IP,args);
5039 bool ChatHandler::HandleBanHelper(BanMode mode, const char* args)
5041 if(!args)
5042 return false;
5044 char* cnameOrIP = strtok ((char*)args, " ");
5045 if (!cnameOrIP)
5046 return false;
5048 std::string nameOrIP = cnameOrIP;
5050 char* duration = strtok (NULL," ");
5051 if(!duration || !atoi(duration))
5052 return false;
5054 char* reason = strtok (NULL,"");
5055 if(!reason)
5056 return false;
5058 switch(mode)
5060 case BAN_ACCOUNT:
5061 if(!AccountMgr::normilizeString(nameOrIP))
5063 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,nameOrIP.c_str());
5064 SetSentErrorMessage(true);
5065 return false;
5067 break;
5068 case BAN_CHARACTER:
5069 if(!normalizePlayerName(nameOrIP))
5071 SendSysMessage(LANG_PLAYER_NOT_FOUND);
5072 SetSentErrorMessage(true);
5073 return false;
5075 break;
5076 case BAN_IP:
5077 if(!IsIPAddress(nameOrIP.c_str()))
5078 return false;
5079 break;
5082 switch(sWorld.BanAccount(mode, nameOrIP, duration, reason,m_session ? m_session->GetPlayerName() : ""))
5084 case BAN_SUCCESS:
5085 if(atoi(duration)>0)
5086 PSendSysMessage(LANG_BAN_YOUBANNED,nameOrIP.c_str(),secsToTimeString(TimeStringToSecs(duration),true).c_str(),reason);
5087 else
5088 PSendSysMessage(LANG_BAN_YOUPERMBANNED,nameOrIP.c_str(),reason);
5089 break;
5090 case BAN_SYNTAX_ERROR:
5091 return false;
5092 case BAN_NOTFOUND:
5093 switch(mode)
5095 default:
5096 PSendSysMessage(LANG_BAN_NOTFOUND,"account",nameOrIP.c_str());
5097 break;
5098 case BAN_CHARACTER:
5099 PSendSysMessage(LANG_BAN_NOTFOUND,"character",nameOrIP.c_str());
5100 break;
5101 case BAN_IP:
5102 PSendSysMessage(LANG_BAN_NOTFOUND,"ip",nameOrIP.c_str());
5103 break;
5105 SetSentErrorMessage(true);
5106 return false;
5109 return true;
5112 bool ChatHandler::HandleUnBanAccountCommand(const char* args)
5114 return HandleUnBanHelper(BAN_ACCOUNT,args);
5117 bool ChatHandler::HandleUnBanCharacterCommand(const char* args)
5119 return HandleUnBanHelper(BAN_CHARACTER,args);
5122 bool ChatHandler::HandleUnBanIPCommand(const char* args)
5124 return HandleUnBanHelper(BAN_IP,args);
5127 bool ChatHandler::HandleUnBanHelper(BanMode mode, const char* args)
5129 if(!args)
5130 return false;
5132 char* cnameOrIP = strtok ((char*)args, " ");
5133 if(!cnameOrIP)
5134 return false;
5136 std::string nameOrIP = cnameOrIP;
5138 switch(mode)
5140 case BAN_ACCOUNT:
5141 if(!AccountMgr::normilizeString(nameOrIP))
5143 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,nameOrIP.c_str());
5144 SetSentErrorMessage(true);
5145 return false;
5147 break;
5148 case BAN_CHARACTER:
5149 if(!normalizePlayerName(nameOrIP))
5151 SendSysMessage(LANG_PLAYER_NOT_FOUND);
5152 SetSentErrorMessage(true);
5153 return false;
5155 break;
5156 case BAN_IP:
5157 if(!IsIPAddress(nameOrIP.c_str()))
5158 return false;
5159 break;
5162 if(sWorld.RemoveBanAccount(mode,nameOrIP))
5163 PSendSysMessage(LANG_UNBAN_UNBANNED,nameOrIP.c_str());
5164 else
5165 PSendSysMessage(LANG_UNBAN_ERROR,nameOrIP.c_str());
5167 return true;
5170 bool ChatHandler::HandleBanInfoAccountCommand(const char* args)
5172 if(!args)
5173 return false;
5175 char* cname = strtok((char*)args, "");
5176 if(!cname)
5177 return false;
5179 std::string account_name = cname;
5180 if(!AccountMgr::normilizeString(account_name))
5182 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
5183 SetSentErrorMessage(true);
5184 return false;
5187 uint32 accountid = accmgr.GetId(account_name);
5188 if(!accountid)
5190 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
5191 return true;
5194 return HandleBanInfoHelper(accountid,account_name.c_str());
5197 bool ChatHandler::HandleBanInfoCharacterCommand(const char* args)
5199 if(!args)
5200 return false;
5202 std::string name = extractPlayerNameFromLink((char*)args);
5203 if(name.empty())
5205 SendSysMessage(LANG_PLAYER_NOT_FOUND);
5206 SetSentErrorMessage(true);
5207 return false;
5210 uint32 accountid = objmgr.GetPlayerAccountIdByPlayerName(name);
5211 if(!accountid)
5213 SendSysMessage(LANG_PLAYER_NOT_FOUND);
5214 SetSentErrorMessage(true);
5215 return false;
5218 std::string accountname;
5219 if(!accmgr.GetName(accountid,accountname))
5221 PSendSysMessage(LANG_BANINFO_NOCHARACTER);
5222 return true;
5225 return HandleBanInfoHelper(accountid,accountname.c_str());
5228 bool ChatHandler::HandleBanInfoHelper(uint32 accountid, char const* accountname)
5230 QueryResult *result = loginDatabase.PQuery("SELECT FROM_UNIXTIME(bandate), unbandate-bandate, active, unbandate,banreason,bannedby FROM account_banned WHERE id = '%u' ORDER BY bandate ASC",accountid);
5231 if(!result)
5233 PSendSysMessage(LANG_BANINFO_NOACCOUNTBAN, accountname);
5234 return true;
5237 PSendSysMessage(LANG_BANINFO_BANHISTORY,accountname);
5240 Field* fields = result->Fetch();
5242 time_t unbandate = time_t(fields[3].GetUInt64());
5243 bool active = false;
5244 if(fields[2].GetBool() && (fields[1].GetUInt64() == (uint64)0 ||unbandate >= time(NULL)) )
5245 active = true;
5246 bool permanent = (fields[1].GetUInt64() == (uint64)0);
5247 std::string bantime = permanent?GetMangosString(LANG_BANINFO_INFINITE):secsToTimeString(fields[1].GetUInt64(), true);
5248 PSendSysMessage(LANG_BANINFO_HISTORYENTRY,
5249 fields[0].GetString(), bantime.c_str(), active ? GetMangosString(LANG_BANINFO_YES):GetMangosString(LANG_BANINFO_NO), fields[4].GetString(), fields[5].GetString());
5250 }while (result->NextRow());
5252 delete result;
5253 return true;
5256 bool ChatHandler::HandleBanInfoIPCommand(const char* args)
5258 if(!args)
5259 return false;
5261 char* cIP = strtok ((char*)args, "");
5262 if(!cIP)
5263 return false;
5265 if (!IsIPAddress(cIP))
5266 return false;
5268 std::string IP = cIP;
5270 loginDatabase.escape_string(IP);
5271 QueryResult *result = loginDatabase.PQuery("SELECT ip, FROM_UNIXTIME(bandate), FROM_UNIXTIME(unbandate), unbandate-UNIX_TIMESTAMP(), banreason,bannedby,unbandate-bandate FROM ip_banned WHERE ip = '%s'",IP.c_str());
5272 if(!result)
5274 PSendSysMessage(LANG_BANINFO_NOIP);
5275 return true;
5278 Field *fields = result->Fetch();
5279 bool permanent = !fields[6].GetUInt64();
5280 PSendSysMessage(LANG_BANINFO_IPENTRY,
5281 fields[0].GetString(), fields[1].GetString(), permanent ? GetMangosString(LANG_BANINFO_NEVER):fields[2].GetString(),
5282 permanent ? GetMangosString(LANG_BANINFO_INFINITE):secsToTimeString(fields[3].GetUInt64(), true).c_str(), fields[4].GetString(), fields[5].GetString());
5283 delete result;
5284 return true;
5287 bool ChatHandler::HandleBanListCharacterCommand(const char* args)
5289 loginDatabase.Execute("DELETE FROM ip_banned WHERE unbandate<=UNIX_TIMESTAMP() AND unbandate<>bandate");
5291 char* cFilter = strtok ((char*)args, " ");
5292 if(!cFilter)
5293 return false;
5295 std::string filter = cFilter;
5296 loginDatabase.escape_string(filter);
5297 QueryResult* result = CharacterDatabase.PQuery("SELECT account FROM characters WHERE name "_LIKE_" "_CONCAT3_("'%%'","'%s'","'%%'"),filter.c_str());
5298 if (!result)
5300 PSendSysMessage(LANG_BANLIST_NOCHARACTER);
5301 return true;
5304 return HandleBanListHelper(result);
5307 bool ChatHandler::HandleBanListAccountCommand(const char* args)
5309 loginDatabase.Execute("DELETE FROM ip_banned WHERE unbandate<=UNIX_TIMESTAMP() AND unbandate<>bandate");
5311 char* cFilter = strtok((char*)args, " ");
5312 std::string filter = cFilter ? cFilter : "";
5313 loginDatabase.escape_string(filter);
5315 QueryResult* result;
5317 if(filter.empty())
5319 result = loginDatabase.Query("SELECT account.id, username FROM account, account_banned"
5320 " WHERE account.id = account_banned.id AND active = 1 GROUP BY account.id");
5322 else
5324 result = loginDatabase.PQuery("SELECT account.id, username FROM account, account_banned"
5325 " WHERE account.id = account_banned.id AND active = 1 AND username "_LIKE_" "_CONCAT3_("'%%'","'%s'","'%%'")" GROUP BY account.id",
5326 filter.c_str());
5329 if (!result)
5331 PSendSysMessage(LANG_BANLIST_NOACCOUNT);
5332 return true;
5335 return HandleBanListHelper(result);
5338 bool ChatHandler::HandleBanListHelper(QueryResult* result)
5340 PSendSysMessage(LANG_BANLIST_MATCHINGACCOUNT);
5342 // Chat short output
5343 if(m_session)
5347 Field* fields = result->Fetch();
5348 uint32 accountid = fields[0].GetUInt32();
5350 QueryResult* banresult = loginDatabase.PQuery("SELECT account.username FROM account,account_banned WHERE account_banned.id='%u' AND account_banned.id=account.id",accountid);
5351 if(banresult)
5353 Field* fields2 = banresult->Fetch();
5354 PSendSysMessage("%s",fields2[0].GetString());
5355 delete banresult;
5357 } while (result->NextRow());
5359 // Console wide output
5360 else
5362 SendSysMessage(LANG_BANLIST_ACCOUNTS);
5363 SendSysMessage("===============================================================================");
5364 SendSysMessage(LANG_BANLIST_ACCOUNTS_HEADER);
5367 SendSysMessage("-------------------------------------------------------------------------------");
5368 Field *fields = result->Fetch();
5369 uint32 account_id = fields[0].GetUInt32 ();
5371 std::string account_name;
5373 // "account" case, name can be get in same query
5374 if(result->GetFieldCount() > 1)
5375 account_name = fields[1].GetCppString();
5376 // "character" case, name need extract from another DB
5377 else
5378 accmgr.GetName (account_id,account_name);
5380 // No SQL injection. id is uint32.
5381 QueryResult *banInfo = loginDatabase.PQuery("SELECT bandate,unbandate,bannedby,banreason FROM account_banned WHERE id = %u ORDER BY unbandate", account_id);
5382 if (banInfo)
5384 Field *fields2 = banInfo->Fetch();
5387 time_t t_ban = fields2[0].GetUInt64();
5388 tm* aTm_ban = localtime(&t_ban);
5390 if (fields2[0].GetUInt64() == fields2[1].GetUInt64())
5392 PSendSysMessage("|%-15.15s|%02d-%02d-%02d %02d:%02d| permanent |%-15.15s|%-15.15s|",
5393 account_name.c_str(),aTm_ban->tm_year%100, aTm_ban->tm_mon+1, aTm_ban->tm_mday, aTm_ban->tm_hour, aTm_ban->tm_min,
5394 fields2[2].GetString(),fields2[3].GetString());
5396 else
5398 time_t t_unban = fields2[1].GetUInt64();
5399 tm* aTm_unban = localtime(&t_unban);
5400 PSendSysMessage("|%-15.15s|%02d-%02d-%02d %02d:%02d|%02d-%02d-%02d %02d:%02d|%-15.15s|%-15.15s|",
5401 account_name.c_str(),aTm_ban->tm_year%100, aTm_ban->tm_mon+1, aTm_ban->tm_mday, aTm_ban->tm_hour, aTm_ban->tm_min,
5402 aTm_unban->tm_year%100, aTm_unban->tm_mon+1, aTm_unban->tm_mday, aTm_unban->tm_hour, aTm_unban->tm_min,
5403 fields2[2].GetString(),fields2[3].GetString());
5405 }while ( banInfo->NextRow() );
5406 delete banInfo;
5408 }while( result->NextRow() );
5409 SendSysMessage("===============================================================================");
5412 delete result;
5413 return true;
5416 bool ChatHandler::HandleBanListIPCommand(const char* args)
5418 loginDatabase.Execute("DELETE FROM ip_banned WHERE unbandate<=UNIX_TIMESTAMP() AND unbandate<>bandate");
5420 char* cFilter = strtok((char*)args, " ");
5421 std::string filter = cFilter ? cFilter : "";
5422 loginDatabase.escape_string(filter);
5424 QueryResult* result;
5426 if(filter.empty())
5428 result = loginDatabase.Query ("SELECT ip,bandate,unbandate,bannedby,banreason FROM ip_banned"
5429 " WHERE (bandate=unbandate OR unbandate>UNIX_TIMESTAMP())"
5430 " ORDER BY unbandate" );
5432 else
5434 result = loginDatabase.PQuery( "SELECT ip,bandate,unbandate,bannedby,banreason FROM ip_banned"
5435 " WHERE (bandate=unbandate OR unbandate>UNIX_TIMESTAMP()) AND ip "_LIKE_" "_CONCAT3_("'%%'","'%s'","'%%'")
5436 " ORDER BY unbandate",filter.c_str() );
5439 if(!result)
5441 PSendSysMessage(LANG_BANLIST_NOIP);
5442 return true;
5445 PSendSysMessage(LANG_BANLIST_MATCHINGIP);
5446 // Chat short output
5447 if(m_session)
5451 Field* fields = result->Fetch();
5452 PSendSysMessage("%s",fields[0].GetString());
5453 } while (result->NextRow());
5455 // Console wide output
5456 else
5458 SendSysMessage(LANG_BANLIST_IPS);
5459 SendSysMessage("===============================================================================");
5460 SendSysMessage(LANG_BANLIST_IPS_HEADER);
5463 SendSysMessage("-------------------------------------------------------------------------------");
5464 Field *fields = result->Fetch();
5465 time_t t_ban = fields[1].GetUInt64();
5466 tm* aTm_ban = localtime(&t_ban);
5467 if ( fields[1].GetUInt64() == fields[2].GetUInt64() )
5469 PSendSysMessage("|%-15.15s|%02d-%02d-%02d %02d:%02d| permanent |%-15.15s|%-15.15s|",
5470 fields[0].GetString(), aTm_ban->tm_year%100, aTm_ban->tm_mon+1, aTm_ban->tm_mday, aTm_ban->tm_hour, aTm_ban->tm_min,
5471 fields[3].GetString(), fields[4].GetString());
5473 else
5475 time_t t_unban = fields[2].GetUInt64();
5476 tm* aTm_unban = localtime(&t_unban);
5477 PSendSysMessage("|%-15.15s|%02d-%02d-%02d %02d:%02d|%02d-%02d-%02d %02d:%02d|%-15.15s|%-15.15s|",
5478 fields[0].GetString(), aTm_ban->tm_year%100, aTm_ban->tm_mon+1, aTm_ban->tm_mday, aTm_ban->tm_hour, aTm_ban->tm_min,
5479 aTm_unban->tm_year%100, aTm_unban->tm_mon+1, aTm_unban->tm_mday, aTm_unban->tm_hour, aTm_unban->tm_min,
5480 fields[3].GetString(), fields[4].GetString());
5482 }while( result->NextRow() );
5483 SendSysMessage("===============================================================================");
5486 delete result;
5487 return true;
5490 bool ChatHandler::HandleRespawnCommand(const char* /*args*/)
5492 Player* pl = m_session->GetPlayer();
5494 // accept only explicitly selected target (not implicitly self targeting case)
5495 Unit* target = getSelectedUnit();
5496 if(pl->GetSelection() && target)
5498 if(target->GetTypeId()!=TYPEID_UNIT)
5500 SendSysMessage(LANG_SELECT_CREATURE);
5501 SetSentErrorMessage(true);
5502 return false;
5505 if(target->isDead())
5506 ((Creature*)target)->Respawn();
5507 return true;
5510 CellPair p(MaNGOS::ComputeCellPair(pl->GetPositionX(), pl->GetPositionY()));
5511 Cell cell(p);
5512 cell.data.Part.reserved = ALL_DISTRICT;
5513 cell.SetNoCreate();
5515 MaNGOS::RespawnDo u_do;
5516 MaNGOS::WorldObjectWorker<MaNGOS::RespawnDo> worker(pl,u_do);
5518 TypeContainerVisitor<MaNGOS::WorldObjectWorker<MaNGOS::RespawnDo>, GridTypeMapContainer > obj_worker(worker);
5519 CellLock<GridReadGuard> cell_lock(cell, p);
5520 cell_lock->Visit(cell_lock, obj_worker, *pl->GetMap());
5522 return true;
5525 bool ChatHandler::HandleFlyModeCommand(const char* args)
5527 if(!args)
5528 return false;
5530 Player *target = getSelectedPlayer();
5531 if (!target)
5532 target = m_session->GetPlayer();
5534 WorldPacket data(12);
5535 if (strncmp(args, "on", 3) == 0)
5536 data.SetOpcode(SMSG_MOVE_SET_CAN_FLY);
5537 else if (strncmp(args, "off", 4) == 0)
5538 data.SetOpcode(SMSG_MOVE_UNSET_CAN_FLY);
5539 else
5541 SendSysMessage(LANG_USE_BOL);
5542 return false;
5544 data.append(target->GetPackGUID());
5545 data << uint32(0); // unknown
5546 target->SendMessageToSet(&data, true);
5547 PSendSysMessage(LANG_COMMAND_FLYMODE_STATUS, GetNameLink(target).c_str(), args);
5548 return true;
5551 bool ChatHandler::HandleLoadPDumpCommand(const char *args)
5553 if(!args)
5554 return false;
5556 char * file = strtok((char*)args, " ");
5557 if(!file)
5558 return false;
5560 char * account = strtok(NULL, " ");
5561 if(!account)
5562 return false;
5564 std::string account_name = account;
5565 if(!AccountMgr::normilizeString(account_name))
5567 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
5568 SetSentErrorMessage(true);
5569 return false;
5572 uint32 account_id = accmgr.GetId(account_name);
5573 if(!account_id)
5575 account_id = atoi(account); // use original string
5576 if(!account_id)
5578 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
5579 SetSentErrorMessage(true);
5580 return false;
5584 if(!accmgr.GetName(account_id,account_name))
5586 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
5587 SetSentErrorMessage(true);
5588 return false;
5591 char* guid_str = NULL;
5592 char* name_str = strtok(NULL, " ");
5594 std::string name;
5595 if(name_str)
5597 name = name_str;
5598 // normalize the name if specified and check if it exists
5599 if(!normalizePlayerName(name))
5601 PSendSysMessage(LANG_INVALID_CHARACTER_NAME);
5602 SetSentErrorMessage(true);
5603 return false;
5606 if(!ObjectMgr::IsValidName(name,true))
5608 PSendSysMessage(LANG_INVALID_CHARACTER_NAME);
5609 SetSentErrorMessage(true);
5610 return false;
5613 guid_str = strtok(NULL, " ");
5616 uint32 guid = 0;
5618 if(guid_str)
5620 guid = atoi(guid_str);
5621 if(!guid)
5623 PSendSysMessage(LANG_INVALID_CHARACTER_GUID);
5624 SetSentErrorMessage(true);
5625 return false;
5628 if(objmgr.GetPlayerAccountIdByGUID(guid))
5630 PSendSysMessage(LANG_CHARACTER_GUID_IN_USE,guid);
5631 SetSentErrorMessage(true);
5632 return false;
5636 switch(PlayerDumpReader().LoadDump(file, account_id, name, guid))
5638 case DUMP_SUCCESS:
5639 PSendSysMessage(LANG_COMMAND_IMPORT_SUCCESS);
5640 break;
5641 case DUMP_FILE_OPEN_ERROR:
5642 PSendSysMessage(LANG_FILE_OPEN_FAIL,file);
5643 SetSentErrorMessage(true);
5644 return false;
5645 case DUMP_FILE_BROKEN:
5646 PSendSysMessage(LANG_DUMP_BROKEN,file);
5647 SetSentErrorMessage(true);
5648 return false;
5649 case DUMP_TOO_MANY_CHARS:
5650 PSendSysMessage(LANG_ACCOUNT_CHARACTER_LIST_FULL,account_name.c_str(),account_id);
5651 SetSentErrorMessage(true);
5652 return false;
5653 default:
5654 PSendSysMessage(LANG_COMMAND_IMPORT_FAILED);
5655 SetSentErrorMessage(true);
5656 return false;
5659 return true;
5662 bool ChatHandler::HandleNpcChangeEntryCommand(const char *args)
5664 if(!args)
5665 return false;
5667 uint32 newEntryNum = atoi(args);
5668 if(!newEntryNum)
5669 return false;
5671 Unit* unit = getSelectedUnit();
5672 if(!unit || unit->GetTypeId() != TYPEID_UNIT)
5674 SendSysMessage(LANG_SELECT_CREATURE);
5675 SetSentErrorMessage(true);
5676 return false;
5678 Creature* creature = (Creature*)unit;
5679 if(creature->UpdateEntry(newEntryNum))
5680 SendSysMessage(LANG_DONE);
5681 else
5682 SendSysMessage(LANG_ERROR);
5683 return true;
5686 bool ChatHandler::HandleWritePDumpCommand(const char *args)
5688 if(!args)
5689 return false;
5691 char* file = strtok((char*)args, " ");
5692 char* p2 = strtok(NULL, " ");
5694 if(!file || !p2)
5695 return false;
5697 uint32 guid;
5698 // character name can't start from number
5699 if (isNumeric(p2[0]))
5700 guid = atoi(p2);
5701 else
5703 std::string name = extractPlayerNameFromLink(p2);
5704 if(name.empty())
5706 SendSysMessage(LANG_PLAYER_NOT_FOUND);
5707 SetSentErrorMessage(true);
5708 return false;
5711 guid = objmgr.GetPlayerGUIDByName(name);
5714 if(!objmgr.GetPlayerAccountIdByGUID(guid))
5716 PSendSysMessage(LANG_PLAYER_NOT_FOUND);
5717 SetSentErrorMessage(true);
5718 return false;
5721 switch(PlayerDumpWriter().WriteDump(file, guid))
5723 case DUMP_SUCCESS:
5724 PSendSysMessage(LANG_COMMAND_EXPORT_SUCCESS);
5725 break;
5726 case DUMP_FILE_OPEN_ERROR:
5727 PSendSysMessage(LANG_FILE_OPEN_FAIL,file);
5728 SetSentErrorMessage(true);
5729 return false;
5730 default:
5731 PSendSysMessage(LANG_COMMAND_EXPORT_FAILED);
5732 SetSentErrorMessage(true);
5733 return false;
5736 return true;
5739 bool ChatHandler::HandleMovegensCommand(const char* /*args*/)
5741 Unit* unit = getSelectedUnit();
5742 if(!unit)
5744 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
5745 SetSentErrorMessage(true);
5746 return false;
5749 PSendSysMessage(LANG_MOVEGENS_LIST,(unit->GetTypeId()==TYPEID_PLAYER ? "Player" : "Creature" ),unit->GetGUIDLow());
5751 MotionMaster* mm = unit->GetMotionMaster();
5752 for(MotionMaster::const_iterator itr = mm->begin(); itr != mm->end(); ++itr)
5754 switch((*itr)->GetMovementGeneratorType())
5756 case IDLE_MOTION_TYPE: SendSysMessage(LANG_MOVEGENS_IDLE); break;
5757 case RANDOM_MOTION_TYPE: SendSysMessage(LANG_MOVEGENS_RANDOM); break;
5758 case WAYPOINT_MOTION_TYPE: SendSysMessage(LANG_MOVEGENS_WAYPOINT); break;
5759 case ANIMAL_RANDOM_MOTION_TYPE: SendSysMessage(LANG_MOVEGENS_ANIMAL_RANDOM); break;
5760 case CONFUSED_MOTION_TYPE: SendSysMessage(LANG_MOVEGENS_CONFUSED); break;
5761 case TARGETED_MOTION_TYPE:
5763 if(unit->GetTypeId()==TYPEID_PLAYER)
5765 TargetedMovementGenerator<Player> const* mgen = static_cast<TargetedMovementGenerator<Player> const*>(*itr);
5766 Unit* target = mgen->GetTarget();
5767 if(target)
5768 PSendSysMessage(LANG_MOVEGENS_TARGETED_PLAYER,target->GetName(),target->GetGUIDLow());
5769 else
5770 SendSysMessage(LANG_MOVEGENS_TARGETED_NULL);
5772 else
5774 TargetedMovementGenerator<Creature> const* mgen = static_cast<TargetedMovementGenerator<Creature> const*>(*itr);
5775 Unit* target = mgen->GetTarget();
5776 if(target)
5777 PSendSysMessage(LANG_MOVEGENS_TARGETED_CREATURE,target->GetName(),target->GetGUIDLow());
5778 else
5779 SendSysMessage(LANG_MOVEGENS_TARGETED_NULL);
5781 break;
5783 case HOME_MOTION_TYPE:
5784 if(unit->GetTypeId()==TYPEID_UNIT)
5786 float x,y,z;
5787 (*itr)->GetDestination(x,y,z);
5788 PSendSysMessage(LANG_MOVEGENS_HOME_CREATURE,x,y,z);
5790 else
5791 SendSysMessage(LANG_MOVEGENS_HOME_PLAYER);
5792 break;
5793 case FLIGHT_MOTION_TYPE: SendSysMessage(LANG_MOVEGENS_FLIGHT); break;
5794 case POINT_MOTION_TYPE:
5796 float x,y,z;
5797 (*itr)->GetDestination(x,y,z);
5798 PSendSysMessage(LANG_MOVEGENS_POINT,x,y,z);
5799 break;
5801 case FLEEING_MOTION_TYPE: SendSysMessage(LANG_MOVEGENS_FEAR); break;
5802 case DISTRACT_MOTION_TYPE: SendSysMessage(LANG_MOVEGENS_DISTRACT); break;
5803 default:
5804 PSendSysMessage(LANG_MOVEGENS_UNKNOWN,(*itr)->GetMovementGeneratorType());
5805 break;
5808 return true;
5811 bool ChatHandler::HandlePLimitCommand(const char *args)
5813 if(*args)
5815 char* param = strtok((char*)args, " ");
5816 if(!param)
5817 return false;
5819 int l = strlen(param);
5821 if( strncmp(param,"player",l) == 0 )
5822 sWorld.SetPlayerLimit(-SEC_PLAYER);
5823 else if(strncmp(param,"moderator",l) == 0 )
5824 sWorld.SetPlayerLimit(-SEC_MODERATOR);
5825 else if(strncmp(param,"gamemaster",l) == 0 )
5826 sWorld.SetPlayerLimit(-SEC_GAMEMASTER);
5827 else if(strncmp(param,"administrator",l) == 0 )
5828 sWorld.SetPlayerLimit(-SEC_ADMINISTRATOR);
5829 else if(strncmp(param,"reset",l) == 0 )
5830 sWorld.SetPlayerLimit( sConfig.GetIntDefault("PlayerLimit", DEFAULT_PLAYER_LIMIT) );
5831 else
5833 int val = atoi(param);
5834 if(val < -SEC_ADMINISTRATOR) val = -SEC_ADMINISTRATOR;
5836 sWorld.SetPlayerLimit(val);
5839 // kick all low security level players
5840 if(sWorld.GetPlayerAmountLimit() > SEC_PLAYER)
5841 sWorld.KickAllLess(sWorld.GetPlayerSecurityLimit());
5844 uint32 pLimit = sWorld.GetPlayerAmountLimit();
5845 AccountTypes allowedAccountType = sWorld.GetPlayerSecurityLimit();
5846 char const* secName = "";
5847 switch(allowedAccountType)
5849 case SEC_PLAYER: secName = "Player"; break;
5850 case SEC_MODERATOR: secName = "Moderator"; break;
5851 case SEC_GAMEMASTER: secName = "Gamemaster"; break;
5852 case SEC_ADMINISTRATOR: secName = "Administrator"; break;
5853 default: secName = "<unknown>"; break;
5856 PSendSysMessage("Player limits: amount %u, min. security level %s.",pLimit,secName);
5858 return true;
5861 bool ChatHandler::HandleCastCommand(const char* args)
5863 if(!*args)
5864 return false;
5866 Unit* target = getSelectedUnit();
5868 if(!target)
5870 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
5871 SetSentErrorMessage(true);
5872 return false;
5875 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
5876 uint32 spell = extractSpellIdFromLink((char*)args);
5877 if(!spell)
5878 return false;
5880 SpellEntry const* spellInfo = sSpellStore.LookupEntry(spell);
5881 if(!spellInfo)
5882 return false;
5884 if(!SpellMgr::IsSpellValid(spellInfo,m_session->GetPlayer()))
5886 PSendSysMessage(LANG_COMMAND_SPELL_BROKEN,spell);
5887 SetSentErrorMessage(true);
5888 return false;
5891 char* trig_str = strtok(NULL, " ");
5892 if(trig_str)
5894 int l = strlen(trig_str);
5895 if(strncmp(trig_str,"triggered",l) != 0 )
5896 return false;
5899 bool triggered = (trig_str != NULL);
5901 m_session->GetPlayer()->CastSpell(target,spell,triggered);
5903 return true;
5906 bool ChatHandler::HandleCastBackCommand(const char* args)
5908 Creature* caster = getSelectedCreature();
5910 if(!caster)
5912 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
5913 SetSentErrorMessage(true);
5914 return false;
5917 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r
5918 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
5919 uint32 spell = extractSpellIdFromLink((char*)args);
5920 if(!spell || !sSpellStore.LookupEntry(spell))
5921 return false;
5923 char* trig_str = strtok(NULL, " ");
5924 if(trig_str)
5926 int l = strlen(trig_str);
5927 if(strncmp(trig_str,"triggered",l) != 0 )
5928 return false;
5931 bool triggered = (trig_str != NULL);
5933 // update orientation at server
5934 caster->SetOrientation(caster->GetAngle(m_session->GetPlayer()));
5936 // and client
5937 WorldPacket data;
5938 caster->BuildHeartBeatMsg(&data);
5939 caster->SendMessageToSet(&data,true);
5941 caster->CastSpell(m_session->GetPlayer(),spell,triggered);
5943 return true;
5946 bool ChatHandler::HandleCastDistCommand(const char* args)
5948 if(!*args)
5949 return false;
5951 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
5952 uint32 spell = extractSpellIdFromLink((char*)args);
5953 if(!spell)
5954 return false;
5956 SpellEntry const* spellInfo = sSpellStore.LookupEntry(spell);
5957 if(!spellInfo)
5958 return false;
5960 if(!SpellMgr::IsSpellValid(spellInfo,m_session->GetPlayer()))
5962 PSendSysMessage(LANG_COMMAND_SPELL_BROKEN,spell);
5963 SetSentErrorMessage(true);
5964 return false;
5967 char *distStr = strtok(NULL, " ");
5969 float dist = 0;
5971 if(distStr)
5972 sscanf(distStr, "%f", &dist);
5974 char* trig_str = strtok(NULL, " ");
5975 if(trig_str)
5977 int l = strlen(trig_str);
5978 if(strncmp(trig_str,"triggered",l) != 0 )
5979 return false;
5982 bool triggered = (trig_str != NULL);
5984 float x,y,z;
5985 m_session->GetPlayer()->GetClosePoint(x,y,z,dist);
5987 m_session->GetPlayer()->CastSpell(x,y,z,spell,triggered);
5988 return true;
5991 bool ChatHandler::HandleCastTargetCommand(const char* args)
5993 Creature* caster = getSelectedCreature();
5995 if(!caster)
5997 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
5998 SetSentErrorMessage(true);
5999 return false;
6002 if(!caster->getVictim())
6004 SendSysMessage(LANG_SELECTED_TARGET_NOT_HAVE_VICTIM);
6005 SetSentErrorMessage(true);
6006 return false;
6009 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
6010 uint32 spell = extractSpellIdFromLink((char*)args);
6011 if(!spell || !sSpellStore.LookupEntry(spell))
6012 return false;
6014 char* trig_str = strtok(NULL, " ");
6015 if(trig_str)
6017 int l = strlen(trig_str);
6018 if(strncmp(trig_str,"triggered",l) != 0 )
6019 return false;
6022 bool triggered = (trig_str != NULL);
6024 // update orientation at server
6025 caster->SetOrientation(caster->GetAngle(m_session->GetPlayer()));
6027 // and client
6028 WorldPacket data;
6029 caster->BuildHeartBeatMsg(&data);
6030 caster->SendMessageToSet(&data,true);
6032 caster->CastSpell(caster->getVictim(),spell,triggered);
6034 return true;
6038 ComeToMe command REQUIRED for 3rd party scripting library to have access to PointMovementGenerator
6039 Without this function 3rd party scripting library will get linking errors (unresolved external)
6040 when attempting to use the PointMovementGenerator
6042 bool ChatHandler::HandleComeToMeCommand(const char *args)
6044 Creature* caster = getSelectedCreature();
6046 if(!caster)
6048 SendSysMessage(LANG_SELECT_CREATURE);
6049 SetSentErrorMessage(true);
6050 return false;
6053 char* newFlagStr = strtok((char*)args, " ");
6055 if(!newFlagStr)
6056 return false;
6058 uint32 newFlags = atoi(newFlagStr);
6060 caster->SetUnitMovementFlags(newFlags);
6062 Player* pl = m_session->GetPlayer();
6064 caster->GetMotionMaster()->MovePoint(0, pl->GetPositionX(), pl->GetPositionY(), pl->GetPositionZ());
6065 return true;
6068 bool ChatHandler::HandleCastSelfCommand(const char* args)
6070 if(!*args)
6071 return false;
6073 Unit* target = getSelectedUnit();
6075 if(!target)
6077 SendSysMessage(LANG_SELECT_CHAR_OR_CREATURE);
6078 SetSentErrorMessage(true);
6079 return false;
6082 // number or [name] Shift-click form |color|Hspell:spell_id|h[name]|h|r or Htalent form
6083 uint32 spell = extractSpellIdFromLink((char*)args);
6084 if(!spell)
6085 return false;
6087 SpellEntry const* spellInfo = sSpellStore.LookupEntry(spell);
6088 if(!spellInfo)
6089 return false;
6091 if(!SpellMgr::IsSpellValid(spellInfo,m_session->GetPlayer()))
6093 PSendSysMessage(LANG_COMMAND_SPELL_BROKEN,spell);
6094 SetSentErrorMessage(true);
6095 return false;
6098 target->CastSpell(target,spell,false);
6100 return true;
6103 std::string GetTimeString(uint32 time)
6105 uint16 days = time / DAY, hours = (time % DAY) / HOUR, minute = (time % HOUR) / MINUTE;
6106 std::ostringstream ss;
6107 if(days) ss << days << "d ";
6108 if(hours) ss << hours << "h ";
6109 ss << minute << "m";
6110 return ss.str();
6113 bool ChatHandler::HandleInstanceListBindsCommand(const char* /*args*/)
6115 Player* player = getSelectedPlayer();
6116 if (!player) player = m_session->GetPlayer();
6117 uint32 counter = 0;
6118 for(uint8 i = 0; i < TOTAL_DIFFICULTIES; i++)
6120 Player::BoundInstancesMap &binds = player->GetBoundInstances(i);
6121 for(Player::BoundInstancesMap::iterator itr = binds.begin(); itr != binds.end(); ++itr)
6123 InstanceSave *save = itr->second.save;
6124 std::string timeleft = GetTimeString(save->GetResetTime() - time(NULL));
6125 PSendSysMessage("map: %d inst: %d perm: %s diff: %s canReset: %s TTR: %s", itr->first, save->GetInstanceId(), itr->second.perm ? "yes" : "no", save->GetDifficulty() == DIFFICULTY_NORMAL ? "normal" : "heroic", save->CanReset() ? "yes" : "no", timeleft.c_str());
6126 counter++;
6129 PSendSysMessage("player binds: %d", counter);
6130 counter = 0;
6131 Group *group = player->GetGroup();
6132 if(group)
6134 for(uint8 i = 0; i < TOTAL_DIFFICULTIES; i++)
6136 Group::BoundInstancesMap &binds = group->GetBoundInstances(i);
6137 for(Group::BoundInstancesMap::iterator itr = binds.begin(); itr != binds.end(); ++itr)
6139 InstanceSave *save = itr->second.save;
6140 std::string timeleft = GetTimeString(save->GetResetTime() - time(NULL));
6141 PSendSysMessage("map: %d inst: %d perm: %s diff: %s canReset: %s TTR: %s", itr->first, save->GetInstanceId(), itr->second.perm ? "yes" : "no", save->GetDifficulty() == DIFFICULTY_NORMAL ? "normal" : "heroic", save->CanReset() ? "yes" : "no", timeleft.c_str());
6142 counter++;
6146 PSendSysMessage("group binds: %d", counter);
6148 return true;
6151 bool ChatHandler::HandleInstanceUnbindCommand(const char* args)
6153 if(!*args)
6154 return false;
6156 std::string cmd = args;
6157 if(cmd == "all")
6159 Player* player = getSelectedPlayer();
6160 if (!player) player = m_session->GetPlayer();
6161 uint32 counter = 0;
6162 for(uint8 i = 0; i < TOTAL_DIFFICULTIES; i++)
6164 Player::BoundInstancesMap &binds = player->GetBoundInstances(i);
6165 for(Player::BoundInstancesMap::iterator itr = binds.begin(); itr != binds.end();)
6167 if(itr->first != player->GetMapId())
6169 InstanceSave *save = itr->second.save;
6170 std::string timeleft = GetTimeString(save->GetResetTime() - time(NULL));
6171 PSendSysMessage("unbinding map: %d inst: %d perm: %s diff: %s canReset: %s TTR: %s", itr->first, save->GetInstanceId(), itr->second.perm ? "yes" : "no", save->GetDifficulty() == DIFFICULTY_NORMAL ? "normal" : "heroic", save->CanReset() ? "yes" : "no", timeleft.c_str());
6172 player->UnbindInstance(itr, i);
6173 counter++;
6175 else
6176 ++itr;
6179 PSendSysMessage("instances unbound: %d", counter);
6181 return true;
6184 bool ChatHandler::HandleInstanceStatsCommand(const char* /*args*/)
6186 PSendSysMessage("instances loaded: %d", MapManager::Instance().GetNumInstances());
6187 PSendSysMessage("players in instances: %d", MapManager::Instance().GetNumPlayersInInstances());
6188 PSendSysMessage("instance saves: %d", sInstanceSaveManager.GetNumInstanceSaves());
6189 PSendSysMessage("players bound: %d", sInstanceSaveManager.GetNumBoundPlayersTotal());
6190 PSendSysMessage("groups bound: %d", sInstanceSaveManager.GetNumBoundGroupsTotal());
6191 return true;
6194 bool ChatHandler::HandleInstanceSaveDataCommand(const char * /*args*/)
6196 Player* pl = m_session->GetPlayer();
6198 Map* map = pl->GetMap();
6199 if (!map->IsDungeon())
6201 PSendSysMessage("Map is not a dungeon.");
6202 SetSentErrorMessage(true);
6203 return false;
6206 if (!((InstanceMap*)map)->GetInstanceData())
6208 PSendSysMessage("Map has no instance data.");
6209 SetSentErrorMessage(true);
6210 return false;
6213 ((InstanceMap*)map)->GetInstanceData()->SaveToDB();
6214 return true;
6217 /// Display the list of GMs
6218 bool ChatHandler::HandleGMListFullCommand(const char* /*args*/)
6220 ///- Get the accounts with GM Level >0
6221 QueryResult *result = loginDatabase.Query( "SELECT username,gmlevel FROM account WHERE gmlevel > 0" );
6222 if(result)
6224 SendSysMessage(LANG_GMLIST);
6225 SendSysMessage("========================");
6226 SendSysMessage(LANG_GMLIST_HEADER);
6227 SendSysMessage("========================");
6229 ///- Circle through them. Display username and GM level
6232 Field *fields = result->Fetch();
6233 PSendSysMessage("|%15s|%6s|", fields[0].GetString(),fields[1].GetString());
6234 }while( result->NextRow() );
6236 PSendSysMessage("========================");
6237 delete result;
6239 else
6240 PSendSysMessage(LANG_GMLIST_EMPTY);
6241 return true;
6244 /// Define the 'Message of the day' for the realm
6245 bool ChatHandler::HandleServerSetMotdCommand(const char* args)
6247 sWorld.SetMotd(args);
6248 PSendSysMessage(LANG_MOTD_NEW, args);
6249 return true;
6252 /// Set/Unset the expansion level for an account
6253 bool ChatHandler::HandleAccountSetAddonCommand(const char* args)
6255 ///- Get the command line arguments
6256 char *szAcc = strtok((char*)args," ");
6257 char *szExp = strtok(NULL," ");
6259 if(!szAcc)
6260 return false;
6262 std::string account_name;
6263 uint32 account_id;
6265 if(!szExp)
6267 Player* player = getSelectedPlayer();
6268 if(!player)
6269 return false;
6271 account_id = player->GetSession()->GetAccountId();
6272 accmgr.GetName(account_id,account_name);
6273 szExp = szAcc;
6275 else
6277 ///- Convert Account name to Upper Format
6278 account_name = szAcc;
6279 if(!AccountMgr::normilizeString(account_name))
6281 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
6282 SetSentErrorMessage(true);
6283 return false;
6286 account_id = accmgr.GetId(account_name);
6287 if(!account_id)
6289 PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str());
6290 SetSentErrorMessage(true);
6291 return false;
6296 // Let set addon state only for lesser (strong) security level
6297 // or to self account
6298 if (m_session && m_session->GetAccountId () != account_id &&
6299 HasLowerSecurityAccount (NULL,account_id,true))
6300 return false;
6302 int lev=atoi(szExp); //get int anyway (0 if error)
6303 if(lev < 0)
6304 return false;
6306 // No SQL injection
6307 loginDatabase.PExecute("UPDATE account SET expansion = '%d' WHERE id = '%u'",lev,account_id);
6308 PSendSysMessage(LANG_ACCOUNT_SETADDON,account_name.c_str(),account_id,lev);
6309 return true;
6312 //Send items by mail
6313 bool ChatHandler::HandleSendItemsCommand(const char* args)
6315 if(!*args)
6316 return false;
6318 // format: name "subject text" "mail text" item1[:count1] item2[:count2] ... item12[:count12]
6320 std::string name = extractPlayerNameFromLink((char*)args);
6321 if(name.empty())
6323 SendSysMessage(LANG_PLAYER_NOT_FOUND);
6324 SetSentErrorMessage(true);
6325 return false;
6328 char* tail1 = strtok(NULL, "");
6329 if(!tail1)
6330 return false;
6332 char* msgSubject;
6333 if(*tail1=='"')
6334 msgSubject = strtok(tail1+1, "\"");
6335 else
6337 char* space = strtok(tail1, "\"");
6338 if(!space)
6339 return false;
6340 msgSubject = strtok(NULL, "\"");
6343 if (!msgSubject)
6344 return false;
6346 char* tail2 = strtok(NULL, "");
6347 if(!tail2)
6348 return false;
6350 char* msgText;
6351 if(*tail2=='"')
6352 msgText = strtok(tail2+1, "\"");
6353 else
6355 char* space = strtok(tail2, "\"");
6356 if(!space)
6357 return false;
6358 msgText = strtok(NULL, "\"");
6361 if (!msgText)
6362 return false;
6364 // msgSubject, msgText isn't NUL after prev. check
6365 std::string subject = msgSubject;
6366 std::string text = msgText;
6368 // extract items
6369 typedef std::pair<uint32,uint32> ItemPair;
6370 typedef std::list< ItemPair > ItemPairs;
6371 ItemPairs items;
6373 // get all tail string
6374 char* tail = strtok(NULL, "");
6376 // get from tail next item str
6377 while(char* itemStr = strtok(tail, " "))
6379 // and get new tail
6380 tail = strtok(NULL, "");
6382 // parse item str
6383 char* itemIdStr = strtok(itemStr, ":");
6384 char* itemCountStr = strtok(NULL, " ");
6386 uint32 item_id = atoi(itemIdStr);
6387 if(!item_id)
6388 return false;
6390 ItemPrototype const* item_proto = objmgr.GetItemPrototype(item_id);
6391 if(!item_proto)
6393 PSendSysMessage(LANG_COMMAND_ITEMIDINVALID, item_id);
6394 SetSentErrorMessage(true);
6395 return false;
6398 uint32 item_count = itemCountStr ? atoi(itemCountStr) : 1;
6399 if(item_count < 1 || item_proto->MaxCount > 0 && item_count > uint32(item_proto->MaxCount))
6401 PSendSysMessage(LANG_COMMAND_INVALID_ITEM_COUNT, item_count,item_id);
6402 SetSentErrorMessage(true);
6403 return false;
6406 while(item_count > item_proto->GetMaxStackSize())
6408 items.push_back(ItemPair(item_id,item_proto->GetMaxStackSize()));
6409 item_count -= item_proto->GetMaxStackSize();
6412 items.push_back(ItemPair(item_id,item_count));
6414 if(items.size() > MAX_MAIL_ITEMS)
6416 PSendSysMessage(LANG_COMMAND_MAIL_ITEMS_LIMIT, MAX_MAIL_ITEMS);
6417 SetSentErrorMessage(true);
6418 return false;
6422 uint64 receiver_guid = objmgr.GetPlayerGUIDByName(name);
6423 if(!receiver_guid)
6425 SendSysMessage(LANG_PLAYER_NOT_FOUND);
6426 SetSentErrorMessage(true);
6427 return false;
6430 // from console show not existed sender
6431 uint32 sender_guidlo = m_session ? m_session->GetPlayer()->GetGUIDLow() : 0;
6433 uint32 messagetype = MAIL_NORMAL;
6434 uint32 stationery = MAIL_STATIONERY_GM;
6435 uint32 itemTextId = !text.empty() ? objmgr.CreateItemText( text ) : 0;
6437 Player *receiver = objmgr.GetPlayer(receiver_guid);
6439 // fill mail
6440 MailItemsInfo mi; // item list preparing
6442 for(ItemPairs::const_iterator itr = items.begin(); itr != items.end(); ++itr)
6444 if(Item* item = Item::CreateItem(itr->first,itr->second,m_session ? m_session->GetPlayer() : 0))
6446 item->SaveToDB(); // save for prevent lost at next mail load, if send fail then item will deleted
6447 mi.AddItem(item->GetGUIDLow(), item->GetEntry(), item);
6451 WorldSession::SendMailTo(receiver,messagetype, stationery, sender_guidlo, GUID_LOPART(receiver_guid), subject, itemTextId, &mi, 0, 0, MAIL_CHECK_MASK_NONE);
6453 std::string nameLink = playerLink(name);
6454 PSendSysMessage(LANG_MAIL_SENT, nameLink.c_str());
6455 return true;
6458 ///Send money by mail
6459 bool ChatHandler::HandleSendMoneyCommand(const char* args)
6461 if (!*args)
6462 return false;
6464 /// format: name "subject text" "mail text" money
6466 std::string name = extractPlayerNameFromLink((char*)args);
6467 if(name.empty())
6469 SendSysMessage(LANG_PLAYER_NOT_FOUND);
6470 SetSentErrorMessage(true);
6471 return false;
6474 char* tail1 = strtok(NULL, "");
6475 if (!tail1)
6476 return false;
6478 char* msgSubject;
6479 if (*tail1=='"')
6480 msgSubject = strtok(tail1+1, "\"");
6481 else
6483 char* space = strtok(tail1, "\"");
6484 if (!space)
6485 return false;
6486 msgSubject = strtok(NULL, "\"");
6489 if (!msgSubject)
6490 return false;
6492 char* tail2 = strtok(NULL, "");
6493 if (!tail2)
6494 return false;
6496 char* msgText;
6497 if (*tail2=='"')
6498 msgText = strtok(tail2+1, "\"");
6499 else
6501 char* space = strtok(tail2, "\"");
6502 if (!space)
6503 return false;
6504 msgText = strtok(NULL, "\"");
6507 if (!msgText)
6508 return false;
6510 char* money_str = strtok(NULL, "");
6511 int32 money = money_str ? atoi(money_str) : 0;
6512 if (money <= 0)
6513 return false;
6515 // msgSubject, msgText isn't NUL after prev. check
6516 std::string subject = msgSubject;
6517 std::string text = msgText;
6519 uint64 receiver_guid = objmgr.GetPlayerGUIDByName(name);
6520 if (!receiver_guid)
6522 SendSysMessage(LANG_PLAYER_NOT_FOUND);
6523 SetSentErrorMessage(true);
6524 return false;
6527 uint32 mailId = objmgr.GenerateMailID();
6529 // from console show not existed sender
6530 uint32 sender_guidlo = m_session ? m_session->GetPlayer()->GetGUIDLow() : 0;
6532 uint32 messagetype = MAIL_NORMAL;
6533 uint32 stationery = MAIL_STATIONERY_GM;
6534 uint32 itemTextId = !text.empty() ? objmgr.CreateItemText( text ) : 0;
6536 Player *receiver = objmgr.GetPlayer(receiver_guid);
6538 WorldSession::SendMailTo(receiver,messagetype, stationery, sender_guidlo, GUID_LOPART(receiver_guid), subject, itemTextId, NULL, money, 0, MAIL_CHECK_MASK_NONE);
6540 std::string nameLink = playerLink(name);
6541 PSendSysMessage(LANG_MAIL_SENT, nameLink.c_str());
6542 return true;
6545 /// Send a message to a player in game
6546 bool ChatHandler::HandleSendMessageCommand(const char* args)
6548 ///- Get the command line arguments
6549 std::string name = extractPlayerNameFromLink((char*)args);
6550 if(name.empty())
6552 SendSysMessage(LANG_PLAYER_NOT_FOUND);
6553 SetSentErrorMessage(true);
6554 return false;
6557 char* msg_str = strtok(NULL, "");
6558 if(!msg_str)
6559 return false;
6561 ///- Find the player and check that he is not logging out.
6562 Player *rPlayer = objmgr.GetPlayer(name.c_str());
6563 if(!rPlayer)
6565 SendSysMessage(LANG_PLAYER_NOT_FOUND);
6566 SetSentErrorMessage(true);
6567 return false;
6570 if(rPlayer->GetSession()->isLogingOut())
6572 SendSysMessage(LANG_PLAYER_NOT_FOUND);
6573 SetSentErrorMessage(true);
6574 return false;
6577 ///- Send the message
6578 //Use SendAreaTriggerMessage for fastest delivery.
6579 rPlayer->GetSession()->SendAreaTriggerMessage("%s", msg_str);
6580 rPlayer->GetSession()->SendAreaTriggerMessage("|cffff0000[Message from administrator]:|r");
6582 //Confirmation message
6583 std::string nameLink = playerLink(name);
6584 PSendSysMessage(LANG_SENDMESSAGE,nameLink.c_str(),msg_str);
6585 return true;
6588 bool ChatHandler::HandleFlushArenaPointsCommand(const char * /*args*/)
6590 sBattleGroundMgr.DistributeArenaPoints();
6591 return true;
6594 bool ChatHandler::HandleModifyGenderCommand(const char *args)
6596 if(!*args)
6597 return false;
6599 Player *player = getSelectedPlayer();
6601 if(!player)
6603 PSendSysMessage(LANG_NO_PLAYER);
6604 SetSentErrorMessage(true);
6605 return false;
6608 PlayerInfo const* info = objmgr.GetPlayerInfo(player->getRace(), player->getClass());
6609 if(!info)
6610 return false;
6612 char const* gender_str = (char*)args;
6613 int gender_len = strlen(gender_str);
6615 Gender gender;
6617 if(!strncmp(gender_str, "male", gender_len)) // MALE
6619 if(player->getGender() == GENDER_MALE)
6620 return true;
6622 gender = GENDER_MALE;
6624 else if (!strncmp(gender_str, "female", gender_len)) // FEMALE
6626 if(player->getGender() == GENDER_FEMALE)
6627 return true;
6629 gender = GENDER_FEMALE;
6631 else
6633 SendSysMessage(LANG_MUST_MALE_OR_FEMALE);
6634 SetSentErrorMessage(true);
6635 return false;
6638 // Set gender
6639 player->SetByteValue(UNIT_FIELD_BYTES_0, 2, gender);
6640 player->SetByteValue(PLAYER_BYTES_3, 0, gender);
6642 // Change display ID
6643 player->SetDisplayId(gender ? info->displayId_f : info->displayId_m);
6644 player->SetNativeDisplayId(gender ? info->displayId_f : info->displayId_m);
6646 char const* gender_full = gender ? "female" : "male";
6648 PSendSysMessage(LANG_YOU_CHANGE_GENDER, GetNameLink(player).c_str(), gender_full);
6650 if (needReportToTarget(player))
6651 ChatHandler(player).PSendSysMessage(LANG_YOUR_GENDER_CHANGED, gender_full, GetNameLink().c_str());
6653 return true;