diff options
| author | pete318 <pete318@hotmail.com> | 2015-07-25 16:34:19 +0000 |
|---|---|---|
| committer | r00ty <pete318@hotmail.com> | 2015-09-22 21:33:57 +0200 |
| commit | dcb7082277447c21b11c4a1d59f105fa342c172e (patch) | |
| tree | cdfbcfb3f9019499f4c2ffe1540f88b13122e414 /src/server/game/Entities/Object | |
| parent | 0427870585f873b724b068541a933cdd68fa35a0 (diff) | |
Map local guids 6.x -> 3.3.35:
Implemented:
https://github.com/TrinityCore/TrinityCore/commit/ca83e14f8b141fab0a13e08f48fca6c1ace0c4c7
https://github.com/TrinityCore/TrinityCore/commit/ee1c1b97be4492ecabe8b15ea6323fc37e4eaa8c
https://github.com/TrinityCore/TrinityCore/commit/18e4ab6911468b829b0fc768e532a770263c3717
https://github.com/TrinityCore/TrinityCore/commit/bf37446b3c2ed73b4d3aa9e227d3eff5c53b378b
https://github.com/TrinityCore/TrinityCore/commit/cb854a2b7bb7bd96cf9c4d1daf3789f797bf4db8
* This adds separate (per map) guid sequences depending on object type
* Ported map object container from cmangos/mangos-wotlk@a2d396e
* Added type container visitor for TypeUnorderedMapContainer
* Implemented helper function to erase unique pairs from multimap containers
* Moved object storage of all objects except players and transports to map level
* Added containers linking database spawn id with creature/gameobject in world
* Renamed DBTableGuid to spawnId
* Added a separate spawn id sequence generator for creatures and gameobjects - this will be used in db tables
* Moved building SMSG_UPDATE_OBJECT - updatefields changes broadcast to map update
* Added new function to return but not increment guid
* Adjusted .debug loadcells to show low guid in map before/after load
* Added debug messages for creature spawn/destroy, for map guid debugging
* Store all Gameobjects and Creatures added to OutdoorPvP, so the callback script can be removed when OutdoorPvP instance is destroyed.
Diffstat (limited to 'src/server/game/Entities/Object')
| -rw-r--r-- | src/server/game/Entities/Object/Object.cpp | 131 | ||||
| -rw-r--r-- | src/server/game/Entities/Object/Object.h | 11 | ||||
| -rw-r--r-- | src/server/game/Entities/Object/ObjectGuid.cpp | 55 | ||||
| -rw-r--r-- | src/server/game/Entities/Object/ObjectGuid.h | 177 |
4 files changed, 200 insertions, 174 deletions
diff --git a/src/server/game/Entities/Object/Object.cpp b/src/server/game/Entities/Object/Object.cpp index 6087e03b1bb..f5af3556332 100644 --- a/src/server/game/Entities/Object/Object.cpp +++ b/src/server/game/Entities/Object/Object.cpp @@ -81,14 +81,12 @@ Object::~Object() if (isType(TYPEMASK_ITEM)) TC_LOG_FATAL("misc", "Item slot %u", ((Item*)this)->GetSlot()); ABORT(); - RemoveFromWorld(); } if (m_objectUpdated) { TC_LOG_FATAL("misc", "Object::~Object %s deleted but still in update list!!", GetGUID().ToString().c_str()); ABORT(); - sObjectAccessor->RemoveUpdateObject(this); } delete [] m_uint32Values; @@ -133,7 +131,8 @@ void Object::AddToWorld() m_inWorld = true; // synchronize values mirror with values array (changes will send in updatecreate opcode any way - ClearUpdateMask(true); + ASSERT(!m_objectUpdated); + ClearUpdateMask(false); } void Object::RemoveFromWorld() @@ -418,7 +417,7 @@ void Object::BuildMovementUpdate(ByteBuffer* data, uint16 flags) const case TYPEID_GAMEOBJECT: case TYPEID_DYNAMICOBJECT: case TYPEID_CORPSE: - *data << uint32(GetGUIDLow()); // GetGUIDLow() + *data << uint32(GetGUID().GetCounter()); // GetGUID().GetCounter() break; //! Unit, Player and default here are sending wrong values. /// @todo Research the proper formula @@ -509,6 +508,15 @@ void Object::BuildValuesUpdate(uint8 updateType, ByteBuffer* data, Player* targe data->append(fieldBuffer); } +void Object::AddToObjectUpdateIfNeeded() +{ + if (m_inWorld && !m_objectUpdated) + { + AddToObjectUpdate(); + m_objectUpdated = true; + } +} + void Object::ClearUpdateMask(bool remove) { _changesMask.Clear(); @@ -516,7 +524,8 @@ void Object::ClearUpdateMask(bool remove) if (m_objectUpdated) { if (remove) - sObjectAccessor->RemoveUpdateObject(this); + RemoveFromObjectUpdate(); + m_objectUpdated = false; } } @@ -614,11 +623,7 @@ void Object::SetInt32Value(uint16 index, int32 value) m_int32Values[index] = value; _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -631,11 +636,7 @@ void Object::SetUInt32Value(uint16 index, uint32 value) m_uint32Values[index] = value; _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -657,11 +658,7 @@ void Object::SetUInt64Value(uint16 index, uint64 value) _changesMask.SetBit(index); _changesMask.SetBit(index + 1); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -674,11 +671,7 @@ bool Object::AddGuidValue(uint16 index, ObjectGuid value) _changesMask.SetBit(index); _changesMask.SetBit(index + 1); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); return true; } @@ -696,11 +689,7 @@ bool Object::RemoveGuidValue(uint16 index, ObjectGuid value) _changesMask.SetBit(index); _changesMask.SetBit(index + 1); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); return true; } @@ -717,11 +706,7 @@ void Object::SetFloatValue(uint16 index, float value) m_floatValues[index] = value; _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -741,11 +726,8 @@ void Object::SetByteValue(uint16 index, uint8 offset, uint8 value) m_uint32Values[index] |= uint32(uint32(value) << (offset * 8)); _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); + } } @@ -765,11 +747,7 @@ void Object::SetUInt16Value(uint16 index, uint8 offset, uint16 value) m_uint32Values[index] |= uint32(uint32(value) << (offset * 16)); _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -782,11 +760,7 @@ void Object::SetGuidValue(uint16 index, ObjectGuid value) _changesMask.SetBit(index); _changesMask.SetBit(index + 1); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -856,11 +830,7 @@ void Object::SetFlag(uint16 index, uint32 newFlag) m_uint32Values[index] = newval; _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -877,11 +847,7 @@ void Object::RemoveFlag(uint16 index, uint32 oldFlag) m_uint32Values[index] = newval; _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -921,11 +887,7 @@ void Object::SetByteFlag(uint16 index, uint8 offset, uint8 newFlag) m_uint32Values[index] |= uint32(uint32(newFlag) << (offset * 8)); _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -944,11 +906,7 @@ void Object::RemoveByteFlag(uint16 index, uint8 offset, uint8 oldFlag) m_uint32Values[index] &= ~uint32(uint32(oldFlag) << (offset * 8)); _changesMask.SetBit(index); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } } @@ -1158,7 +1116,7 @@ bool WorldObject::_IsWithinDist(WorldObject const* obj, float dist2compare, bool float sizefactor = GetObjectSize() + obj->GetObjectSize(); float maxdist = dist2compare + sizefactor; - if (GetTransport() && obj->GetTransport() && obj->GetTransport()->GetGUIDLow() == GetTransport()->GetGUIDLow()) + if (GetTransport() && obj->GetTransport() && obj->GetTransport()->GetGUID().GetCounter() == GetTransport()->GetGUID().GetCounter()) { float dtx = m_movementInfo.transport.pos.m_positionX - obj->m_movementInfo.transport.pos.m_positionX; float dty = m_movementInfo.transport.pos.m_positionY - obj->m_movementInfo.transport.pos.m_positionY; @@ -1747,11 +1705,7 @@ bool WorldObject::CanDetectStealthOf(WorldObject const* obj, bool checkAlert) co void Object::ForceValuesUpdateAtIndex(uint32 i) { _changesMask.SetBit(i); - if (m_inWorld && !m_objectUpdated) - { - sObjectAccessor->AddUpdateObject(this); - m_objectUpdated = true; - } + AddToObjectUpdateIfNeeded(); } void Unit::BuildHeartBeatMsg(WorldPacket* data) const @@ -1829,7 +1783,7 @@ void WorldObject::AddObjectToRemoveList() Map* map = FindMap(); if (!map) { - TC_LOG_ERROR("misc", "Object (TypeId: %u Entry: %u GUID: %u) at attempt add to move list not have valid map (Id: %u).", GetTypeId(), GetEntry(), GetGUIDLow(), GetMapId()); + TC_LOG_ERROR("misc", "Object (TypeId: %u Entry: %u GUID: %u) at attempt add to move list not have valid map (Id: %u).", GetTypeId(), GetEntry(), GetGUID().GetCounter(), GetMapId()); return; } @@ -1909,8 +1863,8 @@ TempSummon* Map::SummonCreature(uint32 entry, Position const& pos, SummonPropert summon = new Minion(properties, summoner, false); break; } - - if (!summon->Create(sObjectMgr->GenerateLowGuid(HIGHGUID_UNIT), this, phase, entry, pos.GetPositionX(), pos.GetPositionY(), pos.GetPositionZ(), pos.GetOrientation(), nullptr, vehId)) + + if (!summon->Create(GenerateLowGuid<HighGuid::Unit>(), this, phase, entry, pos.GetPositionX(), pos.GetPositionY(), pos.GetPositionZ(), pos.GetOrientation(), nullptr, vehId)) { delete summon; return NULL; @@ -1964,6 +1918,11 @@ void WorldObject::SetZoneScript() } } +void WorldObject::ClearZoneScript() +{ + m_zoneScript = NULL; +} + TempSummon* WorldObject::SummonCreature(uint32 entry, const Position &pos, TempSummonType spwtype, uint32 duration, uint32 /*vehId*/) const { if (Map* map = FindMap()) @@ -2004,7 +1963,7 @@ GameObject* WorldObject::SummonGameObject(uint32 entry, float x, float y, float Map* map = GetMap(); GameObject* go = new GameObject(); - if (!go->Create(sObjectMgr->GenerateLowGuid(HIGHGUID_GAMEOBJECT), entry, map, GetPhaseMask(), x, y, z, ang, rotation0, rotation1, rotation2, rotation3, 100, GO_STATE_READY)) + if (!go->Create(map->GenerateLowGuid<HighGuid::GameObject>(), entry, map, GetPhaseMask(), x, y, z, ang, rotation0, rotation1, rotation2, rotation3, 100, GO_STATE_READY)) { delete go; return NULL; @@ -2288,7 +2247,7 @@ void WorldObject::MovePosition(Position &pos, float dist, float angle) if (!Trinity::IsValidMapCoord(destx, desty, pos.m_positionZ)) { TC_LOG_FATAL("misc", "WorldObject::MovePosition: Object (TypeId: %u Entry: %u GUID: %u) has invalid coordinates X: %f and Y: %f were passed!", - GetTypeId(), GetEntry(), GetGUIDLow(), destx, desty); + GetTypeId(), GetEntry(), GetGUID().GetCounter(), destx, desty); return; } @@ -2563,6 +2522,16 @@ void WorldObject::BuildUpdate(UpdateDataMapType& data_map) ClearUpdateMask(false); } +void WorldObject::AddToObjectUpdate() +{ + GetMap()->AddUpdateObject(this); +} + +void WorldObject::RemoveFromObjectUpdate() +{ + GetMap()->RemoveUpdateObject(this); +} + ObjectGuid WorldObject::GetTransGUID() const { if (GetTransport()) diff --git a/src/server/game/Entities/Object/Object.h b/src/server/game/Entities/Object/Object.h index e673e346a5f..43d1ecdeabd 100644 --- a/src/server/game/Entities/Object/Object.h +++ b/src/server/game/Entities/Object/Object.h @@ -101,9 +101,6 @@ class Object virtual void RemoveFromWorld(); ObjectGuid GetGUID() const { return GetGuidValue(OBJECT_FIELD_GUID); } - uint32 GetGUIDLow() const { return GetGuidValue(OBJECT_FIELD_GUID).GetCounter(); } - uint32 GetGUIDMid() const { return GetGuidValue(OBJECT_FIELD_GUID).GetEntry(); } - uint32 GetGUIDHigh() const { return GetGuidValue(OBJECT_FIELD_GUID).GetHigh(); } PackedGuid const& GetPackGUID() const { return m_PackGUID; } uint32 GetEntry() const { return GetUInt32Value(OBJECT_FIELD_ENTRY); } void SetEntry(uint32 entry) { SetUInt32Value(OBJECT_FIELD_ENTRY, entry); } @@ -234,6 +231,10 @@ class Object uint16 _fieldNotifyFlags; + virtual void AddToObjectUpdate() = 0; + virtual void RemoveFromObjectUpdate() = 0; + void AddToObjectUpdateIfNeeded(); + bool m_objectUpdated; private: @@ -535,6 +536,7 @@ class WorldObject : public Object, public WorldLocation Map const* GetBaseMap() const; void SetZoneScript(); + void ClearZoneScript(); ZoneScript* GetZoneScript() const { return m_zoneScript; } TempSummon* SummonCreature(uint32 id, Position const &pos, TempSummonType spwtype = TEMPSUMMON_MANUAL_DESPAWN, uint32 despwtime = 0, uint32 vehId = 0) const; @@ -555,6 +557,9 @@ class WorldObject : public Object, public WorldLocation virtual void UpdateObjectVisibility(bool forced = true); void BuildUpdate(UpdateDataMapType&) override; + void AddToObjectUpdate() override; + void RemoveFromObjectUpdate() override; + //relocation and visibility system functions void AddToNotify(uint16 f) { m_notifyflags |= f;} bool isNeedNotify(uint16 f) const { return (m_notifyflags & f) != 0; } diff --git a/src/server/game/Entities/Object/ObjectGuid.cpp b/src/server/game/Entities/Object/ObjectGuid.cpp index b86a253a84d..552705d8df8 100644 --- a/src/server/game/Entities/Object/ObjectGuid.cpp +++ b/src/server/game/Entities/Object/ObjectGuid.cpp @@ -28,18 +28,18 @@ char const* ObjectGuid::GetTypeName(HighGuid high) { switch (high) { - case HIGHGUID_ITEM: return "Item"; - case HIGHGUID_PLAYER: return "Player"; - case HIGHGUID_GAMEOBJECT: return "Gameobject"; - case HIGHGUID_TRANSPORT: return "Transport"; - case HIGHGUID_UNIT: return "Creature"; - case HIGHGUID_PET: return "Pet"; - case HIGHGUID_VEHICLE: return "Vehicle"; - case HIGHGUID_DYNAMICOBJECT: return "DynObject"; - case HIGHGUID_CORPSE: return "Corpse"; - case HIGHGUID_MO_TRANSPORT: return "MoTransport"; - case HIGHGUID_INSTANCE: return "InstanceID"; - case HIGHGUID_GROUP: return "Group"; + case HighGuid::Item: return "Item"; + case HighGuid::Player: return "Player"; + case HighGuid::GameObject: return "Gameobject"; + case HighGuid::Transport: return "Transport"; + case HighGuid::Unit: return "Creature"; + case HighGuid::Pet: return "Pet"; + case HighGuid::Vehicle: return "Vehicle"; + case HighGuid::DynamicObject: return "DynObject"; + case HighGuid::Corpse: return "Corpse"; + case HighGuid::Mo_Transport: return "MoTransport"; + case HighGuid::Instance: return "InstanceID"; + case HighGuid::Group: return "Group"; default: return "<unknown>"; } @@ -57,15 +57,14 @@ std::string ObjectGuid::ToString() const return str.str(); } -template<HighGuid high> -uint32 ObjectGuidGenerator<high>::Generate() +ObjectGuid ObjectGuid::Global(HighGuid type, LowType counter) { - if (_nextGuid >= ObjectGuid::GetMaxCounter(high) - 1) - { - TC_LOG_ERROR("", "%s guid overflow!! Can't continue, shutting down server. ", ObjectGuid::GetTypeName(high)); - World::StopNow(ERROR_EXIT_CODE); - } - return _nextGuid++; + return ObjectGuid(type, counter); +} + +ObjectGuid ObjectGuid::MapSpecific(HighGuid type, uint32 entry, LowType counter) +{ + return ObjectGuid(type, entry, counter); } ByteBuffer& operator<<(ByteBuffer& buf, ObjectGuid const& guid) @@ -92,14 +91,8 @@ ByteBuffer& operator>>(ByteBuffer& buf, PackedGuidReader const& guid) return buf; } -template uint32 ObjectGuidGenerator<HIGHGUID_ITEM>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_PLAYER>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_GAMEOBJECT>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_TRANSPORT>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_UNIT>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_PET>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_VEHICLE>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_DYNAMICOBJECT>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_CORPSE>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_INSTANCE>::Generate(); -template uint32 ObjectGuidGenerator<HIGHGUID_GROUP>::Generate(); +void ObjectGuidGeneratorBase::HandleCounterOverflow(HighGuid high) +{ + TC_LOG_ERROR("misc", "%s guid overflow!! Can't continue, shutting down server. ", ObjectGuid::GetTypeName(high)); + World::StopNow(ERROR_EXIT_CODE); +}
\ No newline at end of file diff --git a/src/server/game/Entities/Object/ObjectGuid.h b/src/server/game/Entities/Object/ObjectGuid.h index b541328c467..705cc3eac3e 100644 --- a/src/server/game/Entities/Object/ObjectGuid.h +++ b/src/server/game/Entities/Object/ObjectGuid.h @@ -22,6 +22,7 @@ #include "Common.h" #include "ByteBuffer.h" +#include <type_traits> #include <functional> #include <unordered_set> @@ -52,23 +53,57 @@ enum TypeMask TYPEMASK_SEER = TYPEMASK_PLAYER | TYPEMASK_UNIT | TYPEMASK_DYNAMICOBJECT }; -enum HighGuid +enum class HighGuid { - HIGHGUID_ITEM = 0x4000, // blizz 4000 - HIGHGUID_CONTAINER = 0x4000, // blizz 4000 - HIGHGUID_PLAYER = 0x0000, // blizz 0000 - HIGHGUID_GAMEOBJECT = 0xF110, // blizz F110 - HIGHGUID_TRANSPORT = 0xF120, // blizz F120 (for GAMEOBJECT_TYPE_TRANSPORT) - HIGHGUID_UNIT = 0xF130, // blizz F130 - HIGHGUID_PET = 0xF140, // blizz F140 - HIGHGUID_VEHICLE = 0xF150, // blizz F550 - HIGHGUID_DYNAMICOBJECT = 0xF100, // blizz F100 - HIGHGUID_CORPSE = 0xF101, // blizz F100 - HIGHGUID_MO_TRANSPORT = 0x1FC0, // blizz 1FC0 (for GAMEOBJECT_TYPE_MO_TRANSPORT) - HIGHGUID_INSTANCE = 0x1F40, // blizz 1F40 - HIGHGUID_GROUP = 0x1F50 + Item = 0x4000, // blizz 4000 + Container = 0x4000, // blizz 4000 + Player = 0x0000, // blizz 0000 + GameObject = 0xF110, // blizz F110 + Transport = 0xF120, // blizz F120 (for GAMEOBJECT_TYPE_TRANSPORT) + Unit = 0xF130, // blizz F130 + Pet = 0xF140, // blizz F140 + Vehicle = 0xF150, // blizz F550 + DynamicObject = 0xF100, // blizz F100 + Corpse = 0xF101, // blizz F100 + Mo_Transport = 0x1FC0, // blizz 1FC0 (for GAMEOBJECT_TYPE_MO_TRANSPORT) + Instance = 0x1F40, // blizz 1F40 + Group = 0x1F50, }; +template<HighGuid high> +struct ObjectGuidTraits +{ + static bool const Global = false; + static bool const MapSpecific = false; +}; + +#define GUID_TRAIT_GLOBAL(highguid) \ + template<> struct ObjectGuidTraits<highguid> \ + { \ + static bool const Global = true; \ + static bool const MapSpecific = false; \ + }; + +#define GUID_TRAIT_MAP_SPECIFIC(highguid) \ + template<> struct ObjectGuidTraits<highguid> \ + { \ + static bool const Global = false; \ + static bool const MapSpecific = true; \ + }; + +GUID_TRAIT_GLOBAL(HighGuid::Player) +GUID_TRAIT_GLOBAL(HighGuid::Item) +GUID_TRAIT_GLOBAL(HighGuid::Mo_Transport) +GUID_TRAIT_GLOBAL(HighGuid::Group) +GUID_TRAIT_GLOBAL(HighGuid::Instance) +GUID_TRAIT_MAP_SPECIFIC(HighGuid::Transport) +GUID_TRAIT_MAP_SPECIFIC(HighGuid::Unit) +GUID_TRAIT_MAP_SPECIFIC(HighGuid::Vehicle) +GUID_TRAIT_MAP_SPECIFIC(HighGuid::Pet) +GUID_TRAIT_MAP_SPECIFIC(HighGuid::GameObject) +GUID_TRAIT_MAP_SPECIFIC(HighGuid::DynamicObject) +GUID_TRAIT_MAP_SPECIFIC(HighGuid::Corpse) + class ObjectGuid; class PackedGuid; @@ -85,6 +120,12 @@ class ObjectGuid typedef uint32 LowType; + template<HighGuid type> + static typename std::enable_if<ObjectGuidTraits<type>::Global, ObjectGuid>::type Create(LowType counter) { return Global(type, counter); } + + template<HighGuid type> + static typename std::enable_if<ObjectGuidTraits<type>::MapSpecific, ObjectGuid>::type Create(uint32 entry, LowType counter) { return MapSpecific(type, entry, counter); } + ObjectGuid() : _guid(0) { } explicit ObjectGuid(uint64 guid) : _guid(guid) { } ObjectGuid(HighGuid hi, uint32 entry, LowType counter) : _guid(counter ? uint64(counter) | (uint64(entry) << 24) | (uint64(hi) << 48) : 0) { } @@ -123,41 +164,41 @@ class ObjectGuid uint32 GetMaxCounter() const { return GetMaxCounter(GetHigh()); } bool IsEmpty() const { return _guid == 0; } - bool IsCreature() const { return GetHigh() == HIGHGUID_UNIT; } - bool IsPet() const { return GetHigh() == HIGHGUID_PET; } - bool IsVehicle() const { return GetHigh() == HIGHGUID_VEHICLE; } + bool IsCreature() const { return GetHigh() == HighGuid::Unit; } + bool IsPet() const { return GetHigh() == HighGuid::Pet; } + bool IsVehicle() const { return GetHigh() == HighGuid::Vehicle; } bool IsCreatureOrPet() const { return IsCreature() || IsPet(); } bool IsCreatureOrVehicle() const { return IsCreature() || IsVehicle(); } bool IsAnyTypeCreature() const { return IsCreature() || IsPet() || IsVehicle(); } - bool IsPlayer() const { return !IsEmpty() && GetHigh() == HIGHGUID_PLAYER; } + bool IsPlayer() const { return !IsEmpty() && GetHigh() == HighGuid::Player; } bool IsUnit() const { return IsAnyTypeCreature() || IsPlayer(); } - bool IsItem() const { return GetHigh() == HIGHGUID_ITEM; } - bool IsGameObject() const { return GetHigh() == HIGHGUID_GAMEOBJECT; } - bool IsDynamicObject() const { return GetHigh() == HIGHGUID_DYNAMICOBJECT; } - bool IsCorpse() const { return GetHigh() == HIGHGUID_CORPSE; } - bool IsTransport() const { return GetHigh() == HIGHGUID_TRANSPORT; } - bool IsMOTransport() const { return GetHigh() == HIGHGUID_MO_TRANSPORT; } + bool IsItem() const { return GetHigh() == HighGuid::Item; } + bool IsGameObject() const { return GetHigh() == HighGuid::GameObject; } + bool IsDynamicObject() const { return GetHigh() == HighGuid::DynamicObject; } + bool IsCorpse() const { return GetHigh() == HighGuid::Corpse; } + bool IsTransport() const { return GetHigh() == HighGuid::Transport; } + bool IsMOTransport() const { return GetHigh() == HighGuid::Mo_Transport; } bool IsAnyTypeGameObject() const { return IsGameObject() || IsTransport() || IsMOTransport(); } - bool IsInstance() const { return GetHigh() == HIGHGUID_INSTANCE; } - bool IsGroup() const { return GetHigh() == HIGHGUID_GROUP; } + bool IsInstance() const { return GetHigh() == HighGuid::Instance; } + bool IsGroup() const { return GetHigh() == HighGuid::Group; } static TypeID GetTypeId(HighGuid high) { switch (high) { - case HIGHGUID_ITEM: return TYPEID_ITEM; - //case HIGHGUID_CONTAINER: return TYPEID_CONTAINER; HIGHGUID_CONTAINER==HIGHGUID_ITEM currently - case HIGHGUID_UNIT: return TYPEID_UNIT; - case HIGHGUID_PET: return TYPEID_UNIT; - case HIGHGUID_PLAYER: return TYPEID_PLAYER; - case HIGHGUID_GAMEOBJECT: return TYPEID_GAMEOBJECT; - case HIGHGUID_DYNAMICOBJECT: return TYPEID_DYNAMICOBJECT; - case HIGHGUID_CORPSE: return TYPEID_CORPSE; - case HIGHGUID_MO_TRANSPORT: return TYPEID_GAMEOBJECT; - case HIGHGUID_VEHICLE: return TYPEID_UNIT; + case HighGuid::Item: return TYPEID_ITEM; + //case HighGuid::Container: return TYPEID_CONTAINER; HighGuid::Container==HighGuid::Item currently + case HighGuid::Unit: return TYPEID_UNIT; + case HighGuid::Pet: return TYPEID_UNIT; + case HighGuid::Player: return TYPEID_PLAYER; + case HighGuid::GameObject: return TYPEID_GAMEOBJECT; + case HighGuid::DynamicObject: return TYPEID_DYNAMICOBJECT; + case HighGuid::Corpse: return TYPEID_CORPSE; + case HighGuid::Mo_Transport: return TYPEID_GAMEOBJECT; + case HighGuid::Vehicle: return TYPEID_UNIT; // unknown - case HIGHGUID_INSTANCE: - case HIGHGUID_GROUP: + case HighGuid::Instance: + case HighGuid::Group: default: return TYPEID_OBJECT; } } @@ -178,19 +219,19 @@ class ObjectGuid { switch (high) { - case HIGHGUID_ITEM: - case HIGHGUID_PLAYER: - case HIGHGUID_DYNAMICOBJECT: - case HIGHGUID_CORPSE: - case HIGHGUID_MO_TRANSPORT: - case HIGHGUID_INSTANCE: - case HIGHGUID_GROUP: + case HighGuid::Item: + case HighGuid::Player: + case HighGuid::DynamicObject: + case HighGuid::Corpse: + case HighGuid::Mo_Transport: + case HighGuid::Instance: + case HighGuid::Group: return false; - case HIGHGUID_GAMEOBJECT: - case HIGHGUID_TRANSPORT: - case HIGHGUID_UNIT: - case HIGHGUID_PET: - case HIGHGUID_VEHICLE: + case HighGuid::GameObject: + case HighGuid::Transport: + case HighGuid::Unit: + case HighGuid::Pet: + case HighGuid::Vehicle: default: return true; } @@ -198,6 +239,9 @@ class ObjectGuid bool HasEntry() const { return HasEntry(GetHigh()); } + static ObjectGuid Global(HighGuid type, LowType counter); + static ObjectGuid MapSpecific(HighGuid type, uint32 entry, LowType counter); + explicit ObjectGuid(uint32 const&) = delete; // no implementation, used to catch wrong type assignment ObjectGuid(HighGuid, uint32, uint64 counter) = delete; // no implementation, used to catch wrong type assignment ObjectGuid(HighGuid, uint64 counter) = delete; // no implementation, used to catch wrong type assignment @@ -233,18 +277,33 @@ class PackedGuid ByteBuffer _packedGuid; }; -template<HighGuid high> -class ObjectGuidGenerator + +class ObjectGuidGeneratorBase { - public: - explicit ObjectGuidGenerator(uint32 start = 1) : _nextGuid(start) { } +public: + ObjectGuidGeneratorBase(ObjectGuid::LowType start = 1) : _nextGuid(start) { } - void Set(uint32 val) { _nextGuid = val; } - uint32 Generate(); - uint32 GetNextAfterMaxUsed() const { return _nextGuid; } + virtual void Set(uint32 val) { _nextGuid = val; } + virtual ObjectGuid::LowType Generate() = 0; + ObjectGuid::LowType GetNextAfterMaxUsed() const { return _nextGuid; } - private: - uint32 _nextGuid; +protected: + static void HandleCounterOverflow(HighGuid high); + uint64 _nextGuid; +}; + +template<HighGuid high> +class ObjectGuidGenerator : public ObjectGuidGeneratorBase +{ +public: + explicit ObjectGuidGenerator(ObjectGuid::LowType start = 1) : ObjectGuidGeneratorBase(start) { } + + ObjectGuid::LowType Generate() override + { + if (_nextGuid >= ObjectGuid::GetMaxCounter(high) - 1) + HandleCounterOverflow(high); + return _nextGuid++; + } }; ByteBuffer& operator<<(ByteBuffer& buf, ObjectGuid const& guid); |
