aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/server/game/Entities/Creature/Creature.cpp58
-rw-r--r--src/server/game/Entities/Creature/Creature.h2
-rw-r--r--src/server/game/Entities/GameObject/GameObject.cpp48
-rw-r--r--src/server/game/Entities/GameObject/GameObject.h2
-rw-r--r--src/server/game/Entities/Pet/Pet.h4
-rw-r--r--src/server/game/Maps/Map.cpp8
-rw-r--r--src/server/game/Maps/Map.h9
-rw-r--r--src/server/game/OutdoorPvP/OutdoorPvP.cpp44
-rw-r--r--src/server/scripts/Commands/cs_gobject.cpp62
-rw-r--r--src/server/scripts/Commands/cs_misc.cpp2
-rw-r--r--src/server/scripts/Commands/cs_npc.cpp57
-rw-r--r--src/server/scripts/Commands/cs_wp.cpp67
12 files changed, 163 insertions, 200 deletions
diff --git a/src/server/game/Entities/Creature/Creature.cpp b/src/server/game/Entities/Creature/Creature.cpp
index 81c4791e2a5..ce5222b5195 100644
--- a/src/server/game/Entities/Creature/Creature.cpp
+++ b/src/server/game/Entities/Creature/Creature.cpp
@@ -35,6 +35,7 @@
#include "InstanceScript.h"
#include "Log.h"
#include "LootMgr.h"
+#include "MapManager.h"
#include "MiscPackets.h"
#include "MotionMaster.h"
#include "ObjectAccessor.h"
@@ -1888,70 +1889,79 @@ bool Creature::hasInvolvedQuest(uint32 quest_id) const
return false;
}
-void Creature::DeleteFromDB()
+/*static*/ bool Creature::DeleteFromDB(ObjectGuid::LowType spawnId)
{
- if (!m_spawnId)
- {
- TC_LOG_ERROR("entities.unit", "Trying to delete not saved %s!", GetGUID().ToString().c_str());
- return;
- }
+ CreatureData const* data = sObjectMgr->GetCreatureData(spawnId);
+ if (!data)
+ return false;
+
+ CharacterDatabaseTransaction charTrans = CharacterDatabase.BeginTransaction();
+
+ sMapMgr->DoForAllMapsWithMapId(data->spawnPoint.GetMapId(),
+ [spawnId, charTrans](Map* map) -> void
+ {
+ // despawn all active creatures, and remove their respawns
+ std::vector<Creature*> toUnload;
+ for (auto const& pair : Trinity::Containers::MapEqualRange(map->GetCreatureBySpawnIdStore(), spawnId))
+ toUnload.push_back(pair.second);
+ for (Creature* creature : toUnload)
+ map->AddObjectToRemoveList(creature);
+ map->RemoveRespawnTime(SPAWN_TYPE_CREATURE, spawnId, false, charTrans);
+ }
+ );
- // remove any scheduled respawns
- GetMap()->RemoveRespawnTime(SPAWN_TYPE_CREATURE, m_spawnId);
+ // delete data from memory ...
+ sObjectMgr->DeleteCreatureData(spawnId);
- // delete data from memory
- sObjectMgr->DeleteCreatureData(m_spawnId);
+ CharacterDatabase.CommitTransaction(charTrans);
- // delete data and all its associations from DB
WorldDatabaseTransaction trans = WorldDatabase.BeginTransaction();
+ // ... and the database
WorldDatabasePreparedStatement* stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_CREATURE);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_SPAWNGROUP_MEMBER);
stmt->setUInt8(0, uint8(SPAWN_TYPE_CREATURE));
- stmt->setUInt64(1, m_spawnId);
+ stmt->setUInt64(1, spawnId);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_CREATURE_ADDON);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_GAME_EVENT_CREATURE);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_GAME_EVENT_MODEL_EQUIP);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_LINKED_RESPAWN);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
stmt->setUInt32(1, LINKED_RESPAWN_CREATURE_TO_CREATURE);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_LINKED_RESPAWN);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
stmt->setUInt32(1, LINKED_RESPAWN_CREATURE_TO_GO);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_LINKED_RESPAWN_MASTER);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
stmt->setUInt32(1, LINKED_RESPAWN_CREATURE_TO_CREATURE);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_LINKED_RESPAWN_MASTER);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
stmt->setUInt32(1, LINKED_RESPAWN_GO_TO_CREATURE);
trans->Append(stmt);
WorldDatabase.CommitTransaction(trans);
- // then delete any active instances of the creature
- auto const& spawnMap = GetMap()->GetCreatureBySpawnIdStore();
- for (auto it = spawnMap.find(m_spawnId); it != spawnMap.end(); it = spawnMap.find(m_spawnId))
- it->second->AddObjectToRemoveList();
+ return true;
}
bool Creature::IsInvisibleDueToDespawn() const
diff --git a/src/server/game/Entities/Creature/Creature.h b/src/server/game/Entities/Creature/Creature.h
index b4d2228bb2e..a108630811c 100644
--- a/src/server/game/Entities/Creature/Creature.h
+++ b/src/server/game/Entities/Creature/Creature.h
@@ -214,7 +214,7 @@ class TC_GAME_API Creature : public Unit, public GridObject<Creature>, public Ma
void SaveToDB();
// overriden in Pet
virtual void SaveToDB(uint32 mapid, std::vector<Difficulty> const& spawnDifficulties);
- virtual void DeleteFromDB(); // overriden in Pet
+ static bool DeleteFromDB(ObjectGuid::LowType spawnId);
Loot loot;
void StartPickPocketRefillTimer();
diff --git a/src/server/game/Entities/GameObject/GameObject.cpp b/src/server/game/Entities/GameObject/GameObject.cpp
index e36ec3016ba..0d20d360d55 100644
--- a/src/server/game/Entities/GameObject/GameObject.cpp
+++ b/src/server/game/Entities/GameObject/GameObject.cpp
@@ -34,6 +34,8 @@
#include "Item.h"
#include "Log.h"
#include "LootMgr.h"
+#include "Map.h"
+#include "MapManager.h"
#include "MiscPackets.h"
#include "ObjectAccessor.h"
#include "ObjectMgr.h"
@@ -1261,51 +1263,75 @@ bool GameObject::LoadFromDB(ObjectGuid::LowType spawnId, Map* map, bool addToMap
return true;
}
-void GameObject::DeleteFromDB()
+/*static*/ bool GameObject::DeleteFromDB(ObjectGuid::LowType spawnId)
{
- GetMap()->RemoveRespawnTime(SPAWN_TYPE_GAMEOBJECT, m_spawnId);
- sObjectMgr->DeleteGameObjectData(m_spawnId);
+ GameObjectData const* data = sObjectMgr->GetGameObjectData(spawnId);
+ if (!data)
+ return false;
+
+ CharacterDatabaseTransaction charTrans = CharacterDatabase.BeginTransaction();
+
+ sMapMgr->DoForAllMapsWithMapId(data->spawnPoint.GetMapId(),
+ [spawnId, charTrans](Map* map) -> void
+ {
+ // despawn all active objects, and remove their respawns
+ std::vector<GameObject*> toUnload;
+ for (auto const& pair : Trinity::Containers::MapEqualRange(map->GetGameObjectBySpawnIdStore(), spawnId))
+ toUnload.push_back(pair.second);
+ for (GameObject* obj : toUnload)
+ map->AddObjectToRemoveList(obj);
+ map->RemoveRespawnTime(SPAWN_TYPE_GAMEOBJECT, spawnId, false, charTrans);
+ }
+ );
+
+ // delete data from memory
+ sObjectMgr->DeleteGameObjectData(spawnId);
+
+ CharacterDatabase.CommitTransaction(charTrans);
WorldDatabaseTransaction trans = WorldDatabase.BeginTransaction();
+ // ... and the database
WorldDatabasePreparedStatement* stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_GAMEOBJECT);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_SPAWNGROUP_MEMBER);
stmt->setUInt8(0, uint8(SPAWN_TYPE_GAMEOBJECT));
- stmt->setUInt64(1, m_spawnId);
+ stmt->setUInt64(1, spawnId);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_EVENT_GAMEOBJECT);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_LINKED_RESPAWN);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
stmt->setUInt32(1, LINKED_RESPAWN_GO_TO_GO);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_LINKED_RESPAWN);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
stmt->setUInt32(1, LINKED_RESPAWN_GO_TO_CREATURE);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_LINKED_RESPAWN_MASTER);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
stmt->setUInt32(1, LINKED_RESPAWN_GO_TO_GO);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_LINKED_RESPAWN_MASTER);
- stmt->setUInt64(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
stmt->setUInt32(1, LINKED_RESPAWN_CREATURE_TO_GO);
trans->Append(stmt);
stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_GAMEOBJECT_ADDON);
- stmt->setUInt32(0, m_spawnId);
+ stmt->setUInt64(0, spawnId);
trans->Append(stmt);
WorldDatabase.CommitTransaction(trans);
+
+ return true;
}
/*********************************************************/
diff --git a/src/server/game/Entities/GameObject/GameObject.h b/src/server/game/Entities/GameObject/GameObject.h
index 16af03dcfb7..72f466aa327 100644
--- a/src/server/game/Entities/GameObject/GameObject.h
+++ b/src/server/game/Entities/GameObject/GameObject.h
@@ -131,7 +131,7 @@ class TC_GAME_API GameObject : public WorldObject, public GridObject<GameObject>
void SaveToDB();
void SaveToDB(uint32 mapid, std::vector<Difficulty> const& spawnDifficulties);
bool LoadFromDB(ObjectGuid::LowType spawnId, Map* map, bool addToMap, bool = true); // arg4 is unused, only present to match the signature on Creature
- void DeleteFromDB();
+ static bool DeleteFromDB(ObjectGuid::LowType spawnId);
void SetOwnerGUID(ObjectGuid owner)
{
diff --git a/src/server/game/Entities/Pet/Pet.h b/src/server/game/Entities/Pet/Pet.h
index 047df2581ae..8a6f6571105 100644
--- a/src/server/game/Entities/Pet/Pet.h
+++ b/src/server/game/Entities/Pet/Pet.h
@@ -166,9 +166,5 @@ class TC_GAME_API Pet : public Guardian
{
ABORT();
}
- void DeleteFromDB() override // override of Creature::DeleteFromDB - must not be called
- {
- ABORT();
- }
};
#endif
diff --git a/src/server/game/Maps/Map.cpp b/src/server/game/Maps/Map.cpp
index 8d8a6f2d4bd..dbc3ba69480 100644
--- a/src/server/game/Maps/Map.cpp
+++ b/src/server/game/Maps/Map.cpp
@@ -3218,9 +3218,9 @@ void Map::DoRespawn(SpawnObjectType type, ObjectGuid::LowType spawnId, uint32 gr
}
}
-void Map::Respawn(RespawnInfo* info, bool force, CharacterDatabaseTransaction dbTrans)
+void Map::Respawn(RespawnInfo* info, CharacterDatabaseTransaction dbTrans)
{
- if (!force && !CheckRespawn(info))
+ if (!CheckRespawn(info))
{
if (info->respawnTime)
SaveRespawnTime(info->type, info->spawnId, info->entry, info->respawnTime, info->zoneId, info->gridId, true, true, dbTrans);
@@ -3237,11 +3237,11 @@ void Map::Respawn(RespawnInfo* info, bool force, CharacterDatabaseTransaction db
DoRespawn(type, spawnId, gridId);
}
-void Map::Respawn(std::vector<RespawnInfo*>& respawnData, bool force, CharacterDatabaseTransaction dbTrans)
+void Map::Respawn(std::vector<RespawnInfo*>& respawnData, CharacterDatabaseTransaction dbTrans)
{
CharacterDatabaseTransaction trans = dbTrans ? dbTrans : CharacterDatabase.BeginTransaction();
for (RespawnInfo* info : respawnData)
- Respawn(info, force, trans);
+ Respawn(info, trans);
if (!dbTrans)
CharacterDatabase.CommitTransaction(trans);
}
diff --git a/src/server/game/Maps/Map.h b/src/server/game/Maps/Map.h
index cf273e36c00..b678a82ff71 100644
--- a/src/server/game/Maps/Map.h
+++ b/src/server/game/Maps/Map.h
@@ -720,8 +720,8 @@ class TC_GAME_API Map : public GridRefManager<NGridType>
// if return value is false and info->respawnTime is nonzero, it is guaranteed to be greater than time(NULL)
bool CheckRespawn(RespawnInfo* info);
void DoRespawn(SpawnObjectType type, ObjectGuid::LowType spawnId, uint32 gridId);
- void Respawn(RespawnInfo* info, bool force = false, CharacterDatabaseTransaction dbTrans = nullptr);
- void Respawn(std::vector<RespawnInfo*>& respawnData, bool force = false, CharacterDatabaseTransaction dbTrans = nullptr);
+ void Respawn(RespawnInfo* info, CharacterDatabaseTransaction dbTrans = nullptr);
+ void Respawn(std::vector<RespawnInfo*>& respawnData, CharacterDatabaseTransaction dbTrans = nullptr);
void AddRespawnInfo(RespawnInfo& info, bool replace = false);
void DeleteRespawnInfo();
void DeleteRespawnInfo(RespawnInfo* info);
@@ -747,11 +747,6 @@ class TC_GAME_API Map : public GridRefManager<NGridType>
public:
void GetRespawnInfo(std::vector<RespawnInfo*>& respawnData, SpawnObjectTypeMask types, uint32 zoneId = 0) const;
RespawnInfo* GetRespawnInfo(SpawnObjectType type, ObjectGuid::LowType spawnId) const;
- void ForceRespawn(SpawnObjectType type, ObjectGuid::LowType spawnId)
- {
- if (RespawnInfo* info = GetRespawnInfo(type, spawnId))
- Respawn(info, true);
- }
void RemoveRespawnTime(RespawnInfo* info, bool doRespawn = false, CharacterDatabaseTransaction dbTrans = nullptr);
void RemoveRespawnTime(std::vector<RespawnInfo*>& respawnData, bool doRespawn = false, CharacterDatabaseTransaction dbTrans = nullptr);
void RemoveRespawnTime(SpawnObjectTypeMask types = SPAWN_TYPEMASK_ALL, uint32 zoneId = 0, bool doRespawn = false, CharacterDatabaseTransaction dbTrans = nullptr)
diff --git a/src/server/game/OutdoorPvP/OutdoorPvP.cpp b/src/server/game/OutdoorPvP/OutdoorPvP.cpp
index 5fc95c3740f..ccb7311c30f 100644
--- a/src/server/game/OutdoorPvP/OutdoorPvP.cpp
+++ b/src/server/game/OutdoorPvP/OutdoorPvP.cpp
@@ -165,56 +165,24 @@ bool OPvPCapturePoint::DelCreature(uint32 type)
TC_LOG_DEBUG("outdoorpvp", "opvp creature type %u was already deleted", type);
return false;
}
-
- auto bounds = m_PvP->GetMap()->GetCreatureBySpawnIdStore().equal_range(spawnId);
- for (auto itr = bounds.first; itr != bounds.second;)
- {
- Creature* c = itr->second;
- ++itr;
- // Don't save respawn time
- c->SetRespawnTime(0);
- c->DespawnOrUnsummon();
- c->AddObjectToRemoveList();
- }
-
TC_LOG_DEBUG("outdoorpvp", "deleting opvp creature type %u", type);
- // explicit removal from map
- // beats me why this is needed, but with the recent removal "cleanup" some creatures stay in the map if "properly" deleted
- // so this is a big fat workaround, if AddObjectToRemoveList and DoDelayedMovesAndRemoves worked correctly, this wouldn't be needed
- //if (Map* map = sMapMgr->FindMap(cr->GetMapId()))
- // map->Remove(cr, false);
- // delete respawn time for this creature
- CharacterDatabasePreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_DEL_CREATURE_RESPAWN);
- stmt->setUInt64(0, spawnId);
- stmt->setUInt16(1, m_PvP->GetMap()->GetId());
- stmt->setUInt32(2, 0); // instance id, always 0 for world maps
- CharacterDatabase.Execute(stmt);
-
- sObjectMgr->DeleteCreatureData(spawnId);
m_CreatureTypes[m_Creatures[type]] = 0;
m_Creatures[type] = 0;
- return true;
+
+ return Creature::DeleteFromDB(spawnId);
}
bool OPvPCapturePoint::DelObject(uint32 type)
{
- if (!m_Objects[type])
+ uint32 spawnId = m_Objects[type];
+ if (!spawnId)
return false;
- ObjectGuid::LowType spawnId = m_Objects[type];
- auto bounds = m_PvP->GetMap()->GetGameObjectBySpawnIdStore().equal_range(spawnId);
- for (auto itr = bounds.first; itr != bounds.second;)
- {
- GameObject* go = itr->second;
- ++itr;
- // Don't save respawn time
- go->SetRespawnTime(0);
- go->Delete();
- }
sObjectMgr->DeleteGameObjectData(spawnId);
m_ObjectTypes[m_Objects[type]] = 0;
m_Objects[type] = 0;
- return true;
+
+ return GameObject::DeleteFromDB(spawnId);
}
bool OPvPCapturePoint::DelCapturePoint()
diff --git a/src/server/scripts/Commands/cs_gobject.cpp b/src/server/scripts/Commands/cs_gobject.cpp
index 324d6ede64c..0647eb8e3c9 100644
--- a/src/server/scripts/Commands/cs_gobject.cpp
+++ b/src/server/scripts/Commands/cs_gobject.cpp
@@ -49,6 +49,7 @@ EndScriptData */
bool HandleNpcSpawnGroup(ChatHandler* handler, char const* args);
bool HandleNpcDespawnGroup(ChatHandler* handler, char const* args);
+using namespace Trinity::ChatCommands;
class gobject_commandscript : public CommandScript
{
public:
@@ -340,49 +341,36 @@ public:
}
//delete object by selection or guid
- static bool HandleGameObjectDeleteCommand(ChatHandler* handler, char const* args)
+ static bool HandleGameObjectDeleteCommand(ChatHandler* handler, Variant<Hyperlink<gameobject>, ObjectGuid::LowType> spawnId)
{
- // number or [name] Shift-click form |color|Hgameobject:go_guid|h[name]|h|r
- char* id = handler->extractKeyFromLink((char*)args, "Hgameobject");
- if (!id)
- return false;
-
- ObjectGuid::LowType guidLow = atoull(id);
- if (!guidLow)
- return false;
-
- Player const* const player = handler->GetSession()->GetPlayer();
- // force respawn to make sure we find something
- player->GetMap()->ForceRespawn(SPAWN_TYPE_GAMEOBJECT, guidLow);
- GameObject* object = handler->GetObjectFromPlayerMapByDbGuid(guidLow);
- if (!object)
+ if (GameObject* object = handler->GetObjectFromPlayerMapByDbGuid(spawnId))
{
- handler->PSendSysMessage(LANG_COMMAND_OBJNOTFOUND, std::to_string(guidLow).c_str());
- handler->SetSentErrorMessage(true);
- return false;
- }
-
- ObjectGuid ownerGuid = object->GetOwnerGUID();
- if (!ownerGuid.IsEmpty())
- {
- Unit* owner = ObjectAccessor::GetUnit(*player, ownerGuid);
- if (!owner || !ownerGuid.IsPlayer())
+ Player const* const player = handler->GetSession()->GetPlayer();
+ ObjectGuid ownerGuid = object->GetOwnerGUID();
+ if (!ownerGuid.IsEmpty())
{
- handler->PSendSysMessage(LANG_COMMAND_DELOBJREFERCREATURE, ownerGuid.ToString().c_str(), object->GetGUID().ToString().c_str());
- handler->SetSentErrorMessage(true);
- return false;
+ Unit* owner = ObjectAccessor::GetUnit(*player, ownerGuid);
+ if (!owner || !ownerGuid.IsPlayer())
+ {
+ handler->PSendSysMessage(LANG_COMMAND_DELOBJREFERCREATURE, ownerGuid.GetCounter(), spawnId);
+ handler->SetSentErrorMessage(true);
+ return false;
+ }
+ owner->RemoveGameObject(object, false);
}
-
- owner->RemoveGameObject(object, false);
}
- object->SetRespawnTime(0); // not save respawn time
- object->Delete();
- object->DeleteFromDB();
-
- handler->PSendSysMessage(LANG_COMMAND_DELOBJMESSAGE, std::to_string(guidLow).c_str());
-
- return true;
+ if (GameObject::DeleteFromDB(spawnId))
+ {
+ handler->PSendSysMessage(LANG_COMMAND_DELOBJMESSAGE, std::to_string(spawnId));
+ return true;
+ }
+ else
+ {
+ handler->PSendSysMessage(LANG_COMMAND_OBJNOTFOUND, std::to_string(spawnId));
+ handler->SetSentErrorMessage(true);
+ return false;
+ }
}
//turn selected object
diff --git a/src/server/scripts/Commands/cs_misc.cpp b/src/server/scripts/Commands/cs_misc.cpp
index b487a319a22..793b4f02838 100644
--- a/src/server/scripts/Commands/cs_misc.cpp
+++ b/src/server/scripts/Commands/cs_misc.cpp
@@ -1983,7 +1983,7 @@ public:
uint32 const gridId = Trinity::ComputeGridCoord(player->GetPositionX(), player->GetPositionY()).GetId();
for (RespawnInfo* info : data)
if (info->gridId == gridId)
- player->GetMap()->ForceRespawn(info->type, info->spawnId);
+ player->GetMap()->RemoveRespawnTime(info, true);
}
return true;
diff --git a/src/server/scripts/Commands/cs_npc.cpp b/src/server/scripts/Commands/cs_npc.cpp
index 64330b8aa64..6530652fe71 100644
--- a/src/server/scripts/Commands/cs_npc.cpp
+++ b/src/server/scripts/Commands/cs_npc.cpp
@@ -128,6 +128,7 @@ bool HandleNpcDespawnGroup(ChatHandler* handler, char const* args)
return true;
}
+using namespace Trinity::ChatCommands;
class npc_commandscript : public CommandScript
{
public:
@@ -429,48 +430,40 @@ public:
return true;
}
- static bool HandleNpcDeleteCommand(ChatHandler* handler, char const* args)
+ static bool HandleNpcDeleteCommand(ChatHandler* handler, Optional<Variant<Hyperlink<creature>, ObjectGuid::LowType>> spawnIdArg)
{
- Creature* creature = nullptr;
-
- if (*args)
+ ObjectGuid::LowType spawnId;
+ if (spawnIdArg)
+ spawnId = *spawnIdArg;
+ else
{
- // number or [name] Shift-click form |color|Hcreature:creature_guid|h[name]|h|r
- char* cId = handler->extractKeyFromLink((char*)args, "Hcreature");
- if (!cId)
- return false;
-
- ObjectGuid::LowType lowguid = atoull(cId);
- if (!lowguid)
+ Creature* creature = handler->getSelectedCreature();
+ if (!creature || creature->IsPet() || creature->IsTotem())
+ {
+ handler->SendSysMessage(LANG_SELECT_CREATURE);
+ handler->SetSentErrorMessage(true);
return false;
- // force respawn to make sure we find something
- handler->GetSession()->GetPlayer()->GetMap()->ForceRespawn(SPAWN_TYPE_CREATURE, lowguid);
- // then try to find it
- creature = handler->GetCreatureFromPlayerMapByDbGuid(lowguid);
+ }
+ if (TempSummon* summon = creature->ToTempSummon())
+ {
+ summon->UnSummon();
+ handler->SendSysMessage(LANG_COMMAND_DELCREATMESSAGE);
+ return true;
+ }
+ spawnId = creature->GetSpawnId();
}
- else
- creature = handler->getSelectedCreature();
- if (!creature || creature->IsPet() || creature->IsTotem())
+ if (Creature::DeleteFromDB(spawnId))
{
- handler->SendSysMessage(LANG_SELECT_CREATURE);
- handler->SetSentErrorMessage(true);
- return false;
+ handler->SendSysMessage(LANG_COMMAND_DELCREATMESSAGE);
+ return true;
}
-
- if (TempSummon* summon = creature->ToTempSummon())
- summon->UnSummon();
else
{
- // Delete the creature
- creature->CombatStop();
- creature->DeleteFromDB();
- creature->AddObjectToRemoveList();
+ handler->PSendSysMessage(LANG_COMMAND_CREATGUIDNOTFOUND, std::to_string(spawnId));
+ handler->SetSentErrorMessage(true);
+ return false;
}
-
- handler->SendSysMessage(LANG_COMMAND_DELCREATMESSAGE);
-
- return true;
}
//del item from vendor list
diff --git a/src/server/scripts/Commands/cs_wp.cpp b/src/server/scripts/Commands/cs_wp.cpp
index ad3ccf37669..949061302e6 100644
--- a/src/server/scripts/Commands/cs_wp.cpp
+++ b/src/server/scripts/Commands/cs_wp.cpp
@@ -637,21 +637,27 @@ public:
{
handler->PSendSysMessage("|cff00ff00DEBUG: wp modify del, PathID: |r|cff00ffff%u|r", pathid);
- target->DeleteFromDB();
- target->AddObjectToRemoveList();
-
- stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_WAYPOINT_DATA);
- stmt->setUInt32(0, pathid);
- stmt->setUInt32(1, point);
- WorldDatabase.Execute(stmt);
+ if (Creature::DeleteFromDB(target->GetSpawnId()))
+ {
+ stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_WAYPOINT_DATA);
+ stmt->setUInt32(0, pathid);
+ stmt->setUInt32(1, point);
+ WorldDatabase.Execute(stmt);
- stmt = WorldDatabase.GetPreparedStatement(WORLD_UPD_WAYPOINT_DATA_POINT);
- stmt->setUInt32(0, pathid);
- stmt->setUInt32(1, point);
- WorldDatabase.Execute(stmt);
+ stmt = WorldDatabase.GetPreparedStatement(WORLD_UPD_WAYPOINT_DATA_POINT);
+ stmt->setUInt32(0, pathid);
+ stmt->setUInt32(1, point);
+ WorldDatabase.Execute(stmt);
- handler->PSendSysMessage(LANG_WAYPOINT_REMOVED);
- return true;
+ handler->SendSysMessage(LANG_WAYPOINT_REMOVED);
+ return true;
+ }
+ else
+ {
+ handler->SendSysMessage(LANG_WAYPOINT_NOTREMOVED);
+ handler->SetSentErrorMessage(true);
+ return false;
+ }
} // del
if (show == "move")
@@ -663,8 +669,12 @@ public:
// What to do:
// Move the visual spawnpoint
// Respawn the owner of the waypoints
- target->DeleteFromDB();
- target->AddObjectToRemoveList();
+ if (!Creature::DeleteFromDB(target->GetSpawnId()))
+ {
+ handler->PSendSysMessage(LANG_WAYPOINT_VP_NOTCREATED, VISUAL_WAYPOINT);
+ handler->SetSentErrorMessage(true);
+ return false;
+ }
// re-create
Creature* wpCreature = Creature::CreateCreature(VISUAL_WAYPOINT, map, chr->GetPosition());
@@ -842,22 +852,10 @@ public:
{
Field* fields = result2->Fetch();
ObjectGuid::LowType wpguid = fields[0].GetUInt64();
- Creature* creature = handler->GetCreatureFromPlayerMapByDbGuid(wpguid);
-
- if (!creature)
+ if (!Creature::DeleteFromDB(wpguid))
{
handler->PSendSysMessage(LANG_WAYPOINT_NOTREMOVED, std::to_string(wpguid).c_str());
hasError = true;
-
- stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_CREATURE);
- stmt->setUInt64(0, wpguid);
- WorldDatabase.Execute(stmt);
- }
- else
- {
- creature->CombatStop();
- creature->DeleteFromDB();
- creature->AddObjectToRemoveList();
}
}
@@ -1061,21 +1059,10 @@ public:
Field* fields = result->Fetch();
ObjectGuid::LowType lowguid = fields[0].GetUInt64();
- Creature* creature = handler->GetCreatureFromPlayerMapByDbGuid(lowguid);
- if (!creature)
+ if (!Creature::DeleteFromDB(lowguid))
{
handler->PSendSysMessage(LANG_WAYPOINT_NOTREMOVED, std::to_string(lowguid).c_str());
hasError = true;
-
- stmt = WorldDatabase.GetPreparedStatement(WORLD_DEL_CREATURE);
- stmt->setUInt64(0, lowguid);
- WorldDatabase.Execute(stmt);
- }
- else
- {
- creature->CombatStop();
- creature->DeleteFromDB();
- creature->AddObjectToRemoveList();
}
}
while (result->NextRow());