aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorTeleqraph <nyrdeveloper@gmail.com>2022-07-03 16:00:14 +0200
committerGitHub <noreply@github.com>2022-07-03 16:00:14 +0200
commitebf1b6eb5cbfd1dc8f1b0d26c29ae1423784cabb (patch)
treef2e27de6472c4ef1f76fac1ae9422d3470589e1b /src
parent9fcf920d0e69df5c8ca5078d3687f3843b51fcbd (diff)
Core/Creatures: Implemented sending different creature id for summoner (#28066)
Co-authored-by: Shauren <shauren.trinity@gmail.com>
Diffstat (limited to 'src')
-rw-r--r--src/server/game/Entities/Creature/CreatureData.h8
-rw-r--r--src/server/game/Entities/Creature/TemporarySummon.cpp14
-rw-r--r--src/server/game/Entities/Creature/TemporarySummon.h4
-rw-r--r--src/server/game/Entities/Object/Updates/UpdateFields.cpp4
-rw-r--r--src/server/game/Entities/Object/Updates/UpdateFields.h1
-rw-r--r--src/server/game/Entities/Object/Updates/ViewerDependentValues.h32
-rw-r--r--src/server/game/Globals/ObjectMgr.cpp71
-rw-r--r--src/server/game/Globals/ObjectMgr.h3
8 files changed, 135 insertions, 2 deletions
diff --git a/src/server/game/Entities/Creature/CreatureData.h b/src/server/game/Entities/Creature/CreatureData.h
index e01d020120c..d11577da3bd 100644
--- a/src/server/game/Entities/Creature/CreatureData.h
+++ b/src/server/game/Entities/Creature/CreatureData.h
@@ -20,6 +20,7 @@
#include "Common.h"
#include "DBCEnums.h"
+#include "Optional.h"
#include "SharedDefines.h"
#include "SpawnData.h"
#include "UnitDefines.h"
@@ -605,6 +606,13 @@ struct CreatureModelInfo
bool is_trigger;
};
+struct CreatureSummonedData
+{
+ Optional<uint32> CreatureIDVisibleToSummoner;
+ Optional<uint32> GroundMountDisplayID;
+ Optional<uint32> FlyingMountDisplayID;
+};
+
enum InhabitTypeValues
{
INHABIT_GROUND = 1,
diff --git a/src/server/game/Entities/Creature/TemporarySummon.cpp b/src/server/game/Entities/Creature/TemporarySummon.cpp
index a389ff5f8fc..249edcf3e15 100644
--- a/src/server/game/Entities/Creature/TemporarySummon.cpp
+++ b/src/server/game/Entities/Creature/TemporarySummon.cpp
@@ -25,6 +25,7 @@
#include "Log.h"
#include "Map.h"
#include "ObjectAccessor.h"
+#include "ObjectMgr.h"
#include "Pet.h"
#include "Player.h"
#include "SmoothPhasing.h"
@@ -194,6 +195,19 @@ void TempSummon::InitStats(uint32 duration)
if (owner->GetTypeId() == TYPEID_PLAYER)
m_ControlledByPlayer = true;
+ if (owner && owner->IsPlayer())
+ {
+ if (CreatureSummonedData const* summonedData = sObjectMgr->GetCreatureSummonedData(GetEntry()))
+ {
+ m_creatureIdVisibleToSummoner = summonedData->CreatureIDVisibleToSummoner;
+ if (summonedData->CreatureIDVisibleToSummoner)
+ {
+ CreatureTemplate const* creatureTemplateVisibleToSummoner = ASSERT_NOTNULL(sObjectMgr->GetCreatureTemplate(*summonedData->CreatureIDVisibleToSummoner));
+ m_displayIdVisibleToSummoner = ObjectMgr::ChooseDisplayId(creatureTemplateVisibleToSummoner, nullptr)->CreatureDisplayID;
+ }
+ }
+ }
+
if (!m_Properties)
return;
diff --git a/src/server/game/Entities/Creature/TemporarySummon.h b/src/server/game/Entities/Creature/TemporarySummon.h
index d9501cce342..27dfea28506 100644
--- a/src/server/game/Entities/Creature/TemporarySummon.h
+++ b/src/server/game/Entities/Creature/TemporarySummon.h
@@ -61,6 +61,8 @@ class TC_GAME_API TempSummon : public Creature
ObjectGuid GetSummonerGUID() const { return m_summonerGUID; }
TempSummonType GetSummonType() const { return m_type; }
uint32 GetTimer() const { return m_timer; }
+ Optional<uint32> GetCreatureIdVisibleToSummoner() const { return m_creatureIdVisibleToSummoner; }
+ Optional<uint32> GetDisplayIdVisibleToSummoner() const { return m_displayIdVisibleToSummoner; }
bool CanFollowOwner() const { return m_canFollowOwner; }
void SetCanFollowOwner(bool can) { m_canFollowOwner = can; }
@@ -72,6 +74,8 @@ class TC_GAME_API TempSummon : public Creature
uint32 m_timer;
uint32 m_lifetime;
ObjectGuid m_summonerGUID;
+ Optional<uint32> m_creatureIdVisibleToSummoner;
+ Optional<uint32> m_displayIdVisibleToSummoner;
bool m_canFollowOwner;
};
diff --git a/src/server/game/Entities/Object/Updates/UpdateFields.cpp b/src/server/game/Entities/Object/Updates/UpdateFields.cpp
index 70e228847b4..c3146b13bdc 100644
--- a/src/server/game/Entities/Object/Updates/UpdateFields.cpp
+++ b/src/server/game/Entities/Object/Updates/UpdateFields.cpp
@@ -37,7 +37,7 @@ namespace UF
{
void ObjectData::WriteCreate(ByteBuffer& data, EnumFlag<UpdateFieldFlag> fieldVisibilityFlags, Object const* owner, Player const* receiver) const
{
- data << int32(EntryID);
+ data << int32(ViewerDependentValue<EntryIDTag>::GetValue(this, owner, receiver));
data << uint32(ViewerDependentValue<DynamicFlagsTag>::GetValue(this, owner, receiver));
data << float(Scale);
}
@@ -56,7 +56,7 @@ void ObjectData::WriteUpdate(ByteBuffer& data, Mask const& changesMask, bool ign
{
if (changesMask[1])
{
- data << int32(EntryID);
+ data << int32(ViewerDependentValue<EntryIDTag>::GetValue(this, owner, receiver));
}
if (changesMask[2])
{
diff --git a/src/server/game/Entities/Object/Updates/UpdateFields.h b/src/server/game/Entities/Object/Updates/UpdateFields.h
index a4fcd0b65dd..5beb9c4b93a 100644
--- a/src/server/game/Entities/Object/Updates/UpdateFields.h
+++ b/src/server/game/Entities/Object/Updates/UpdateFields.h
@@ -47,6 +47,7 @@ namespace UF
struct ObjectData : public IsUpdateFieldStructureTag, public HasChangesMask<4>
{
UpdateField<int32, 0, 1> EntryID;
+ struct EntryIDTag : ViewerDependentValueTag<int32> {};
UpdateField<uint32, 0, 2> DynamicFlags;
struct DynamicFlagsTag : ViewerDependentValueTag<uint32> {};
UpdateField<float, 0, 3> Scale;
diff --git a/src/server/game/Entities/Object/Updates/ViewerDependentValues.h b/src/server/game/Entities/Object/Updates/ViewerDependentValues.h
index 564b31a9b86..028fdd91a26 100644
--- a/src/server/game/Entities/Object/Updates/ViewerDependentValues.h
+++ b/src/server/game/Entities/Object/Updates/ViewerDependentValues.h
@@ -26,6 +26,7 @@
#include "Player.h"
#include "SpellInfo.h"
#include "SpellMgr.h"
+#include "TemporarySummon.h"
#include "World.h"
#include "WorldSession.h"
@@ -37,6 +38,25 @@ class ViewerDependentValue
};
template<>
+class ViewerDependentValue<UF::ObjectData::EntryIDTag>
+{
+public:
+ using value_type = UF::ObjectData::EntryIDTag::value_type;
+
+ static value_type GetValue(UF::ObjectData const* objectData, Object const* object, Player const* receiver)
+ {
+ value_type entryId = objectData->EntryID;
+
+ if (Unit const* unit = object->ToUnit())
+ if (TempSummon const* summon = unit->ToTempSummon())
+ if (summon->GetSummonerGUID() == receiver->GetGUID() && summon->GetCreatureIdVisibleToSummoner())
+ entryId = *summon->GetCreatureIdVisibleToSummoner();
+
+ return entryId;
+ }
+};
+
+template<>
class ViewerDependentValue<UF::ObjectData::DynamicFlagsTag>
{
public:
@@ -121,6 +141,18 @@ public:
{
CreatureTemplate const* cinfo = unit->ToCreature()->GetCreatureTemplate();
+ if (TempSummon const* summon = unit->ToTempSummon())
+ {
+ if (summon->GetSummonerGUID() == receiver->GetGUID())
+ {
+ if (summon->GetCreatureIdVisibleToSummoner())
+ cinfo = sObjectMgr->GetCreatureTemplate(*summon->GetCreatureIdVisibleToSummoner());
+
+ if (summon->GetDisplayIdVisibleToSummoner())
+ displayId = *summon->GetDisplayIdVisibleToSummoner();
+ }
+ }
+
// this also applies for transform auras
if (SpellInfo const* transform = sSpellMgr->GetSpellInfo(unit->GetTransformSpell(), unit->GetMap()->GetDifficultyID()))
{
diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp
index de8e1092919..cae5700ef64 100644
--- a/src/server/game/Globals/ObjectMgr.cpp
+++ b/src/server/game/Globals/ObjectMgr.cpp
@@ -391,6 +391,8 @@ void ObjectMgr::LoadCreatureTemplates()
// We load the creature models after loading but before checking
LoadCreatureTemplateModels();
+ LoadCreatureSummonedData();
+
// Checking needs to be done after loading because of the difficulty self referencing
for (auto const& ctPair : _creatureTemplateStore)
CheckCreatureTemplate(&ctPair.second);
@@ -642,6 +644,70 @@ void ObjectMgr::LoadCreatureTemplateModels()
TC_LOG_INFO("server.loading", ">> Loaded %u creature template models in %u ms", count, GetMSTimeDiffToNow(oldMSTime));
}
+void ObjectMgr::LoadCreatureSummonedData()
+{
+ uint32 oldMSTime = getMSTime();
+
+ // 0 1 2 3
+ QueryResult result = WorldDatabase.Query("SELECT CreatureID, CreatureIDVisibleToSummoner, GroundMountDisplayID, FlyingMountDisplayID FROM creature_summoned_data");
+
+ if (!result)
+ {
+ TC_LOG_INFO("server.loading", ">> Loaded 0 creature summoned data definitions. DB table `creature_summoned_data` is empty.");
+ return;
+ }
+
+ do
+ {
+ Field* fields = result->Fetch();
+
+ uint32 creatureId = fields[0].GetUInt32();
+ if (!GetCreatureTemplate(creatureId))
+ {
+ TC_LOG_ERROR("sql.sql", "Table `creature_summoned_data` references non-existing creature %u, skipped", creatureId);
+ continue;
+ }
+
+ CreatureSummonedData& summonedData = _creatureSummonedDataStore[creatureId];
+
+ if (!fields[1].IsNull())
+ {
+ summonedData.CreatureIDVisibleToSummoner = fields[1].GetUInt32();
+ if (!GetCreatureTemplate(*summonedData.CreatureIDVisibleToSummoner))
+ {
+ TC_LOG_ERROR("sql.sql", "Table `creature_summoned_data` references non-existing creature %u in CreatureIDVisibleToSummoner for creature %u, set to 0",
+ *summonedData.CreatureIDVisibleToSummoner, creatureId);
+ summonedData.CreatureIDVisibleToSummoner.reset();
+ }
+ }
+
+ if (!fields[2].IsNull())
+ {
+ summonedData.GroundMountDisplayID = fields[2].GetUInt32();
+ if (!sCreatureDisplayInfoStore.LookupEntry(*summonedData.GroundMountDisplayID))
+ {
+ TC_LOG_ERROR("sql.sql", "Table `creature_summoned_data` references non-existing display id %u in GroundMountDisplayID for creature %u, set to 0",
+ *summonedData.GroundMountDisplayID, creatureId);
+ summonedData.CreatureIDVisibleToSummoner.reset();
+ }
+ }
+
+ if (!fields[3].IsNull())
+ {
+ summonedData.FlyingMountDisplayID = fields[3].GetUInt32();
+ if (!sCreatureDisplayInfoStore.LookupEntry(*summonedData.FlyingMountDisplayID))
+ {
+ TC_LOG_ERROR("sql.sql", "Table `creature_summoned_data` references non-existing display id %u in FlyingMountDisplayID for creature %u, set to 0",
+ *summonedData.FlyingMountDisplayID, creatureId);
+ summonedData.GroundMountDisplayID.reset();
+ }
+ }
+
+ } while (result->NextRow());
+
+ TC_LOG_INFO("server.loading", ">> Loaded " SZFMTD " creature summoned data definitions in %u ms", _creatureSummonedDataStore.size(), GetMSTimeDiffToNow(oldMSTime));
+}
+
void ObjectMgr::LoadCreatureTemplateAddons()
{
uint32 oldMSTime = getMSTime();
@@ -1616,6 +1682,11 @@ CreatureModelInfo const* ObjectMgr::GetCreatureModelInfo(uint32 modelId) const
return nullptr;
}
+CreatureSummonedData const* ObjectMgr::GetCreatureSummonedData(uint32 entryId) const
+{
+ return Trinity::Containers::MapGetValuePtr(_creatureSummonedDataStore, entryId);
+}
+
CreatureModel const* ObjectMgr::ChooseDisplayId(CreatureTemplate const* cinfo, CreatureData const* data /*= nullptr*/)
{
// Load creature model (display id)
diff --git a/src/server/game/Globals/ObjectMgr.h b/src/server/game/Globals/ObjectMgr.h
index 9a93903ebc3..047002d74a0 100644
--- a/src/server/game/Globals/ObjectMgr.h
+++ b/src/server/game/Globals/ObjectMgr.h
@@ -1140,6 +1140,7 @@ class TC_GAME_API ObjectMgr
CreatureTemplateContainer const& GetCreatureTemplates() const { return _creatureTemplateStore; }
CreatureModelInfo const* GetCreatureModelInfo(uint32 modelId) const;
CreatureModelInfo const* GetCreatureModelRandomGender(CreatureModel* model, CreatureTemplate const* creatureTemplate) const;
+ CreatureSummonedData const* GetCreatureSummonedData(uint32 entryId) const;
static CreatureModel const* ChooseDisplayId(CreatureTemplate const* cinfo, CreatureData const* data = nullptr);
static void ChooseCreatureFlags(CreatureTemplate const* cInfo, uint64* npcFlags, uint32* unitFlags, uint32* unitFlags2, uint32* unitFlags3, uint32* dynamicFlags, CreatureData const* data = nullptr);
EquipmentInfo const* GetEquipmentInfo(uint32 entry, int8& id) const;
@@ -1318,6 +1319,7 @@ class TC_GAME_API ObjectMgr
void LoadCreatureTemplateResistances();
void LoadCreatureTemplateSpells();
void LoadCreatureTemplateModels();
+ void LoadCreatureSummonedData();
void LoadCreatureScalingData();
void CheckCreatureTemplate(CreatureTemplate const* cInfo);
void CheckCreatureMovement(char const* table, uint64 id, CreatureMovementData& creatureMovement);
@@ -1908,6 +1910,7 @@ class TC_GAME_API ObjectMgr
CreatureDataContainer _creatureDataStore;
CreatureTemplateContainer _creatureTemplateStore;
CreatureModelContainer _creatureModelStore;
+ std::unordered_map<uint32, CreatureSummonedData> _creatureSummonedDataStore;
CreatureAddonContainer _creatureAddonStore;
CreatureTemplateAddonContainer _creatureTemplateAddonStore;
std::unordered_map<ObjectGuid::LowType, CreatureMovementData> _creatureMovementOverrides;