diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/common/Utilities/Util.h | 2 | ||||
-rw-r--r-- | src/server/game/Entities/Creature/Creature.cpp | 4 | ||||
-rw-r--r-- | src/server/game/Entities/Creature/CreatureData.h | 2 | ||||
-rw-r--r-- | src/server/game/Entities/GameObject/GameObject.cpp | 4 | ||||
-rw-r--r-- | src/server/game/Entities/GameObject/GameObjectData.h | 16 | ||||
-rw-r--r-- | src/server/game/Entities/Object/Object.cpp | 27 | ||||
-rw-r--r-- | src/server/game/Entities/Object/Object.h | 4 | ||||
-rw-r--r-- | src/server/game/Entities/Object/ObjectDefines.h | 37 | ||||
-rw-r--r-- | src/server/game/Globals/ObjectMgr.cpp | 46 | ||||
-rw-r--r-- | src/server/worldserver/worldserver.conf.dist | 6 |
10 files changed, 117 insertions, 31 deletions
diff --git a/src/common/Utilities/Util.h b/src/common/Utilities/Util.h index f378d457648..78019885d99 100644 --- a/src/common/Utilities/Util.h +++ b/src/common/Utilities/Util.h @@ -503,7 +503,7 @@ bool CompareValues(ComparisionType type, T val1, T val2) } template<typename E> -typename std::underlying_type<E>::type AsUnderlyingType(E enumValue) +constexpr typename std::underlying_type<E>::type AsUnderlyingType(E enumValue) { static_assert(std::is_enum<E>::value, "AsUnderlyingType can only be used with enums"); return static_cast<typename std::underlying_type<E>::type>(enumValue); diff --git a/src/server/game/Entities/Creature/Creature.cpp b/src/server/game/Entities/Creature/Creature.cpp index 371b588e5e8..06a74ea1c79 100644 --- a/src/server/game/Entities/Creature/Creature.cpp +++ b/src/server/game/Entities/Creature/Creature.cpp @@ -2478,6 +2478,10 @@ bool Creature::LoadCreaturesAddon() if (cainfo->emote != 0) SetUInt32Value(UNIT_NPC_EMOTESTATE, cainfo->emote); + // Check if visibility distance different + if (cainfo->visibilityDistanceType != VisibilityDistanceType::Normal) + SetVisibilityDistanceOverride(cainfo->visibilityDistanceType); + // Load Path if (cainfo->path_id != 0) _waypointPathId = cainfo->path_id; diff --git a/src/server/game/Entities/Creature/CreatureData.h b/src/server/game/Entities/Creature/CreatureData.h index dae19fbf326..c08b2ae86a6 100644 --- a/src/server/game/Entities/Creature/CreatureData.h +++ b/src/server/game/Entities/Creature/CreatureData.h @@ -29,6 +29,7 @@ #include <cmath> struct ItemTemplate; +enum class VisibilityDistanceType : uint8; // EnumUtils: DESCRIBE THIS enum CreatureFlagsExtra : uint32 @@ -312,6 +313,7 @@ struct CreatureAddon uint32 bytes2; uint32 emote; std::vector<uint32> auras; + VisibilityDistanceType visibilityDistanceType; }; // Vendors diff --git a/src/server/game/Entities/GameObject/GameObject.cpp b/src/server/game/Entities/GameObject/GameObject.cpp index 8ae536497f4..bae468c329c 100644 --- a/src/server/game/Entities/GameObject/GameObject.cpp +++ b/src/server/game/Entities/GameObject/GameObject.cpp @@ -399,6 +399,10 @@ bool GameObject::Create(ObjectGuid::LowType guidlow, uint32 name_id, Map* map, u delete linkedGO; } + // Check if GameObject is Large + if (goinfo->IsLargeGameObject()) + SetVisibilityDistanceOverride(VisibilityDistanceType::Large); + return true; } diff --git a/src/server/game/Entities/GameObject/GameObjectData.h b/src/server/game/Entities/GameObject/GameObjectData.h index b27e004289b..ecb5ba8e684 100644 --- a/src/server/game/Entities/GameObject/GameObjectData.h +++ b/src/server/game/Entities/GameObject/GameObjectData.h @@ -571,6 +571,22 @@ struct GameObjectTemplate } } + bool IsLargeGameObject() const + { + switch (type) + { + case GAMEOBJECT_TYPE_BUTTON: return button.large != 0; + case GAMEOBJECT_TYPE_QUESTGIVER: return questgiver.large != 0; + case GAMEOBJECT_TYPE_GENERIC: return _generic.large != 0; + case GAMEOBJECT_TYPE_TRAP: return trap.large != 0; + case GAMEOBJECT_TYPE_SPELL_FOCUS: return spellFocus.large != 0; + case GAMEOBJECT_TYPE_GOOBER: return goober.large != 0; + case GAMEOBJECT_TYPE_SPELLCASTER: return spellcaster.large != 0; + case GAMEOBJECT_TYPE_CAPTURE_POINT: return capturePoint.large != 0; + default: return false; + } + } + void InitializeQueryData(); WorldPacket BuildQueryData(LocaleConstant loc) const; }; diff --git a/src/server/game/Entities/Object/Object.cpp b/src/server/game/Entities/Object/Object.cpp index 3909f76cd67..5087279adc0 100644 --- a/src/server/game/Entities/Object/Object.cpp +++ b/src/server/game/Entities/Object/Object.cpp @@ -47,6 +47,16 @@ #include "World.h" #include <G3D/Vector3.h> +constexpr float VisibilityDistances[AsUnderlyingType(VisibilityDistanceType::Max)] = +{ + DEFAULT_VISIBILITY_DISTANCE, + VISIBILITY_DISTANCE_TINY, + VISIBILITY_DISTANCE_SMALL, + VISIBILITY_DISTANCE_LARGE, + VISIBILITY_DISTANCE_GIGANTIC, + MAX_VISIBILITY_DISTANCE +}; + Object::Object() : m_PackGUID(sizeof(uint64)+1) { m_objectTypeId = TYPEID_OBJECT; @@ -1022,6 +1032,15 @@ void WorldObject::SetFarVisible(bool on) m_isFarVisible = on; } +void WorldObject::SetVisibilityDistanceOverride(VisibilityDistanceType type) +{ + ASSERT(type < VisibilityDistanceType::Max); + if (GetTypeId() == TYPEID_PLAYER) + return; + + m_visibilityDistanceOverride = VisibilityDistances[AsUnderlyingType(type)]; +} + void WorldObject::CleanupsBeforeDelete(bool /*finalCleanup*/) { if (IsInWorld()) @@ -1459,7 +1478,9 @@ float WorldObject::GetGridActivationRange() const float WorldObject::GetVisibilityRange() const { - if (IsFarVisible() && !ToPlayer()) + if (IsVisibilityOverridden() && !ToPlayer()) + return *m_visibilityDistanceOverride; + else if (IsFarVisible() && !ToPlayer()) return MAX_VISIBILITY_DISTANCE; else return GetMap()->GetVisibilityRange(); @@ -1471,7 +1492,9 @@ float WorldObject::GetSightRange(WorldObject const* target) const { if (ToPlayer()) { - if (target && target->IsFarVisible() && !target->ToPlayer()) + if (target && target->IsVisibilityOverridden() && !target->ToPlayer()) + return *target->m_visibilityDistanceOverride; + else if (target && target->IsFarVisible() && !target->ToPlayer()) return MAX_VISIBILITY_DISTANCE; else if (ToPlayer()->GetCinematicMgr()->IsOnCinematic()) return DEFAULT_VISIBILITY_INSTANCE; diff --git a/src/server/game/Entities/Object/Object.h b/src/server/game/Entities/Object/Object.h index db707fac897..7b13276a7f8 100644 --- a/src/server/game/Entities/Object/Object.h +++ b/src/server/game/Entities/Object/Object.h @@ -28,6 +28,7 @@ #include "MovementInfo.h" #include "ObjectDefines.h" #include "ObjectGuid.h" +#include "Optional.h" #include "Position.h" #include "SharedDefines.h" #include "SpellDefines.h" @@ -479,6 +480,8 @@ class TC_GAME_API WorldObject : public Object, public WorldLocation void setActive(bool isActiveObject); bool IsFarVisible() const { return m_isFarVisible; } void SetFarVisible(bool on); + bool IsVisibilityOverridden() const { return m_visibilityDistanceOverride.is_initialized(); } + void SetVisibilityDistanceOverride(VisibilityDistanceType type); void SetWorldObject(bool apply); bool IsPermanentWorldObject() const { return m_isWorldObject; } bool IsWorldObject() const; @@ -519,6 +522,7 @@ class TC_GAME_API WorldObject : public Object, public WorldLocation std::string m_name; bool m_isActive; bool m_isFarVisible; + Optional<float> m_visibilityDistanceOverride; bool const m_isWorldObject; ZoneScript* m_zoneScript; diff --git a/src/server/game/Entities/Object/ObjectDefines.h b/src/server/game/Entities/Object/ObjectDefines.h index ca6a55913e2..0a4faeb1281 100644 --- a/src/server/game/Entities/Object/ObjectDefines.h +++ b/src/server/game/Entities/Object/ObjectDefines.h @@ -21,16 +21,21 @@ #include "Define.h" -#define CONTACT_DISTANCE 0.5f -#define INTERACTION_DISTANCE 5.0f -#define ATTACK_DISTANCE 5.0f -#define INSPECT_DISTANCE 28.0f -#define TRADE_DISTANCE 11.11f -#define MAX_VISIBILITY_DISTANCE SIZE_OF_GRIDS // max distance for visible objects -#define SIGHT_RANGE_UNIT 50.0f -#define DEFAULT_VISIBILITY_DISTANCE 90.0f // default visible distance, 90 yards on continents -#define DEFAULT_VISIBILITY_INSTANCE 170.0f // default visible distance in instances, 170 yards -#define DEFAULT_VISIBILITY_BGARENAS 533.0f // default visible distance in BG/Arenas, roughly 533 yards +#define CONTACT_DISTANCE 0.5f +#define INTERACTION_DISTANCE 5.0f +#define ATTACK_DISTANCE 5.0f +#define INSPECT_DISTANCE 28.0f +#define TRADE_DISTANCE 11.11f +#define MAX_VISIBILITY_DISTANCE SIZE_OF_GRIDS // max distance for visible objects +#define SIGHT_RANGE_UNIT 50.0f +#define VISIBILITY_DISTANCE_GIGANTIC 400.0f +#define VISIBILITY_DISTANCE_LARGE 200.0f +#define VISIBILITY_DISTANCE_NORMAL 100.0f +#define VISIBILITY_DISTANCE_SMALL 50.0f +#define VISIBILITY_DISTANCE_TINY 25.0f +#define DEFAULT_VISIBILITY_DISTANCE VISIBILITY_DISTANCE_NORMAL // default visible distance, 100 yards on continents +#define DEFAULT_VISIBILITY_INSTANCE 170.0f // default visible distance in instances, 170 yards +#define DEFAULT_VISIBILITY_BGARENAS 533.0f // default visible distance in BG/Arenas, roughly 533 yards #define DEFAULT_PLAYER_BOUNDING_RADIUS 0.388999998569489f // player size, also currently used (correctly?) for any non Unit world objects #define DEFAULT_PLAYER_COMBAT_REACH 1.5f @@ -38,6 +43,18 @@ #define NOMINAL_MELEE_RANGE 5.0f #define MELEE_RANGE (NOMINAL_MELEE_RANGE - MIN_MELEE_REACH * 2) //center to center for players +enum class VisibilityDistanceType : uint8 +{ + Normal = 0, + Tiny = 1, + Small = 2, + Large = 3, + Gigantic = 4, + Infinite = 5, + + Max +}; + enum TempSummonType { TEMPSUMMON_TIMED_OR_DEAD_DESPAWN = 1, // despawns after a specified time OR when the creature disappears diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp index df4cdc346c2..b267c52aa32 100644 --- a/src/server/game/Globals/ObjectMgr.cpp +++ b/src/server/game/Globals/ObjectMgr.cpp @@ -487,8 +487,8 @@ void ObjectMgr::LoadCreatureTemplateAddons() { uint32 oldMSTime = getMSTime(); - // 0 1 2 3 4 5 6 - QueryResult result = WorldDatabase.Query("SELECT entry, path_id, mount, bytes1, bytes2, emote, auras FROM creature_template_addon"); + // 0 1 2 3 4 5 6 7 + QueryResult result = WorldDatabase.Query("SELECT entry, path_id, mount, bytes1, bytes2, emote, visibilityDistanceType, auras FROM creature_template_addon"); if (!result) { @@ -511,13 +511,14 @@ void ObjectMgr::LoadCreatureTemplateAddons() CreatureAddon& creatureAddon = _creatureTemplateAddonStore[entry]; - creatureAddon.path_id = fields[1].GetUInt32(); - creatureAddon.mount = fields[2].GetUInt32(); - creatureAddon.bytes1 = fields[3].GetUInt32(); - creatureAddon.bytes2 = fields[4].GetUInt32(); - creatureAddon.emote = fields[5].GetUInt32(); + creatureAddon.path_id = fields[1].GetUInt32(); + creatureAddon.mount = fields[2].GetUInt32(); + creatureAddon.bytes1 = fields[3].GetUInt32(); + creatureAddon.bytes2 = fields[4].GetUInt32(); + creatureAddon.emote = fields[5].GetUInt32(); + creatureAddon.visibilityDistanceType = VisibilityDistanceType(fields[6].GetUInt8()); - Tokenizer tokens(fields[6].GetString(), ' '); + Tokenizer tokens(fields[7].GetString(), ' '); uint8 i = 0; creatureAddon.auras.resize(tokens.size()); for (Tokenizer::const_iterator itr = tokens.begin(); itr != tokens.end(); ++itr) @@ -556,6 +557,13 @@ void ObjectMgr::LoadCreatureTemplateAddons() creatureAddon.emote = 0; } + if (creatureAddon.visibilityDistanceType >= VisibilityDistanceType::Max) + { + TC_LOG_ERROR("sql.sql", "Creature (Entry: %u) has invalid visibilityDistanceType (%u) defined in `creature_template_addon`.", + entry, AsUnderlyingType(creatureAddon.visibilityDistanceType)); + creatureAddon.visibilityDistanceType = VisibilityDistanceType::Normal; + } + ++count; } while (result->NextRow()); @@ -983,8 +991,8 @@ void ObjectMgr::LoadCreatureAddons() { uint32 oldMSTime = getMSTime(); - // 0 1 2 3 4 5 6 - QueryResult result = WorldDatabase.Query("SELECT guid, path_id, mount, bytes1, bytes2, emote, auras FROM creature_addon"); + // 0 1 2 3 4 5 6 7 + QueryResult result = WorldDatabase.Query("SELECT guid, path_id, mount, bytes1, bytes2, emote, visibilityDistanceType, auras FROM creature_addon"); if (!result) { @@ -1015,12 +1023,13 @@ void ObjectMgr::LoadCreatureAddons() TC_LOG_ERROR("sql.sql", "Creature (GUID %u) has movement type set to WAYPOINT_MOTION_TYPE but no path assigned", guid); } - creatureAddon.mount = fields[2].GetUInt32(); - creatureAddon.bytes1 = fields[3].GetUInt32(); - creatureAddon.bytes2 = fields[4].GetUInt32(); - creatureAddon.emote = fields[5].GetUInt32(); + creatureAddon.mount = fields[2].GetUInt32(); + creatureAddon.bytes1 = fields[3].GetUInt32(); + creatureAddon.bytes2 = fields[4].GetUInt32(); + creatureAddon.emote = fields[5].GetUInt32(); + creatureAddon.visibilityDistanceType = VisibilityDistanceType(fields[6].GetUInt8()); - Tokenizer tokens(fields[6].GetString(), ' '); + Tokenizer tokens(fields[7].GetString(), ' '); uint8 i = 0; creatureAddon.auras.resize(tokens.size()); for (Tokenizer::const_iterator itr = tokens.begin(); itr != tokens.end(); ++itr) @@ -1059,6 +1068,13 @@ void ObjectMgr::LoadCreatureAddons() creatureAddon.emote = 0; } + if (creatureAddon.visibilityDistanceType >= VisibilityDistanceType::Max) + { + TC_LOG_ERROR("sql.sql", "Creature (GUID: %u) has invalid visibilityDistanceType (%u) defined in `creature_addon`.", + guid, AsUnderlyingType(creatureAddon.visibilityDistanceType)); + creatureAddon.visibilityDistanceType = VisibilityDistanceType::Normal; + } + ++count; } while (result->NextRow()); diff --git a/src/server/worldserver/worldserver.conf.dist b/src/server/worldserver/worldserver.conf.dist index 99b888c9ff2..eb31fc4da9a 100644 --- a/src/server/worldserver/worldserver.conf.dist +++ b/src/server/worldserver/worldserver.conf.dist @@ -2117,15 +2117,15 @@ Visibility.GroupMode = 1 # Visibility.Distance.Instances # Visibility.Distance.BGArenas # Description: Visibility distance to see other players or gameobjects. -# Visibility on continents on retail ~90 yards. In BG/Arenas ~533. +# Visibility on continents on retail ~100 yards. In BG/Arenas ~533. # For instances default ~170. # Max limited by grid size: 533.33333 # Min limit is max aggro radius (45) * Rate.Creature.Aggro -# Default: 90 - (Visibility.Distance.Continents) +# Default: 100 - (Visibility.Distance.Continents) # 170 - (Visibility.Distance.Instances) # 533 - (Visibility.Distance.BGArenas) -Visibility.Distance.Continents = 90 +Visibility.Distance.Continents = 100 Visibility.Distance.Instances = 170 Visibility.Distance.BGArenas = 533 |