aboutsummaryrefslogtreecommitdiff
path: root/src/game/Object.h
diff options
context:
space:
mode:
authorNeo2003 <none@none>2008-10-02 16:23:55 -0500
committerNeo2003 <none@none>2008-10-02 16:23:55 -0500
commit9b1c0e006f20091f28f3f468cfcab1feb51286bd (patch)
treeb5d1ba94a656e6679f8737f9ea6bed1239b73b14 /src/game/Object.h
[svn] * Proper SVN structureinit
--HG-- branch : trunk
Diffstat (limited to 'src/game/Object.h')
-rw-r--r--src/game/Object.h460
1 files changed, 460 insertions, 0 deletions
diff --git a/src/game/Object.h b/src/game/Object.h
new file mode 100644
index 00000000000..c870e9452c9
--- /dev/null
+++ b/src/game/Object.h
@@ -0,0 +1,460 @@
+/*
+ * Copyright (C) 2005-2008 MaNGOS <http://www.mangosproject.org/>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#ifndef _OBJECT_H
+#define _OBJECT_H
+
+#include "Common.h"
+#include "ByteBuffer.h"
+#include "UpdateFields.h"
+#include "UpdateData.h"
+#include "GameSystem/GridReference.h"
+#include "ObjectDefines.h"
+
+#include <set>
+#include <string>
+
+#define CONTACT_DISTANCE 0.5f
+#define INTERACTION_DISTANCE 5
+#define ATTACK_DISTANCE 5
+#define DETECT_DISTANCE 20 // max distance to successful detect stealthed unit
+#define MAX_VISIBILITY_DISTANCE (5*SIZE_OF_GRID_CELL/2.0f) // max distance for visible object show, limited by active zone for player based at cell size (active zone = 5x5 cells)
+#define DEFAULT_VISIBILITY_DISTANCE (SIZE_OF_GRID_CELL) // default visible distance
+
+#define DEFAULT_WORLD_OBJECT_SIZE 0.388999998569489f // player size, also currently used (correctly?) for any non Unit world objects
+
+enum TypeMask
+{
+ TYPEMASK_OBJECT = 0x0001,
+ TYPEMASK_ITEM = 0x0002,
+ TYPEMASK_CONTAINER = 0x0006, // TYPEMASK_ITEM | 0x0004
+ TYPEMASK_UNIT = 0x0008,
+ TYPEMASK_PLAYER = 0x0010,
+ TYPEMASK_GAMEOBJECT = 0x0020,
+ TYPEMASK_DYNAMICOBJECT = 0x0040,
+ TYPEMASK_CORPSE = 0x0080,
+ TYPEMASK_AIGROUP = 0x0100,
+ TYPEMASK_AREATRIGGER = 0x0200
+};
+
+enum TypeID
+{
+ TYPEID_OBJECT = 0,
+ TYPEID_ITEM = 1,
+ TYPEID_CONTAINER = 2,
+ TYPEID_UNIT = 3,
+ TYPEID_PLAYER = 4,
+ TYPEID_GAMEOBJECT = 5,
+ TYPEID_DYNAMICOBJECT = 6,
+ TYPEID_CORPSE = 7,
+ TYPEID_AIGROUP = 8,
+ TYPEID_AREATRIGGER = 9
+};
+
+uint32 GuidHigh2TypeId(uint32 guid_hi);
+
+enum TempSummonType
+{
+ TEMPSUMMON_TIMED_OR_DEAD_DESPAWN = 1, // despawns after a specified time OR when the creature disappears
+ TEMPSUMMON_TIMED_OR_CORPSE_DESPAWN = 2, // despawns after a specified time OR when the creature dies
+ TEMPSUMMON_TIMED_DESPAWN = 3, // despawns after a specified time
+ TEMPSUMMON_TIMED_DESPAWN_OUT_OF_COMBAT = 4, // despawns after a specified time after the creature is out of combat
+ TEMPSUMMON_CORPSE_DESPAWN = 5, // despawns instantly after death
+ TEMPSUMMON_CORPSE_TIMED_DESPAWN = 6, // despawns after a specified time after death
+ TEMPSUMMON_DEAD_DESPAWN = 7, // despawns when the creature disappears
+ TEMPSUMMON_MANUAL_DESPAWN = 8 // despawns when UnSummon() is called
+};
+
+class WorldPacket;
+class UpdateData;
+class ByteBuffer;
+class WorldSession;
+class Creature;
+class Player;
+class Map;
+class UpdateMask;
+class InstanceData;
+
+typedef HM_NAMESPACE::hash_map<Player*, UpdateData> UpdateDataMapType;
+
+struct WorldLocation
+{
+ uint32 mapid;
+ float x;
+ float y;
+ float z;
+ float o;
+ explicit WorldLocation(uint32 mapid = 0, float x = 0, float y = 0, float z = 0, float o = 0)
+ : mapid(mapid), x(x), y(y), z(z), o(o) {}
+ WorldLocation(WorldLocation const &loc)
+ : mapid(loc.mapid), x(loc.x), y(loc.y), z(loc.z), o(loc.o) {}
+};
+
+class MANGOS_DLL_SPEC Object
+{
+ public:
+ virtual ~Object ( );
+
+ const bool& IsInWorld() const { return m_inWorld; }
+ virtual void AddToWorld()
+ {
+ if(m_inWorld)
+ return;
+
+ m_inWorld = true;
+
+ // synchronize values mirror with values array (changes will send in updatecreate opcode any way
+ ClearUpdateMask(true);
+ }
+ virtual void RemoveFromWorld()
+ {
+ // if we remove from world then sending changes not required
+ if(m_uint32Values)
+ ClearUpdateMask(true);
+ m_inWorld = false;
+ }
+
+ const uint64& GetGUID() const { return GetUInt64Value(0); }
+ uint32 GetGUIDLow() const { return GUID_LOPART(GetUInt64Value(0)); }
+ uint32 GetGUIDMid() const { return GUID_ENPART(GetUInt64Value(0)); }
+ uint32 GetGUIDHigh() const { return GUID_HIPART(GetUInt64Value(0)); }
+ const ByteBuffer& GetPackGUID() const { return m_PackGUID; }
+ uint32 GetEntry() const { return GetUInt32Value(OBJECT_FIELD_ENTRY); }
+
+ uint8 GetTypeId() const { return m_objectTypeId; }
+ bool isType(uint16 mask) const { return (mask & m_objectType); }
+
+ virtual void BuildCreateUpdateBlockForPlayer( UpdateData *data, Player *target ) const;
+ void SendUpdateToPlayer(Player* player);
+
+ void BuildValuesUpdateBlockForPlayer( UpdateData *data, Player *target ) const;
+ void BuildOutOfRangeUpdateBlock( UpdateData *data ) const;
+ void BuildMovementUpdateBlock( UpdateData * data, uint32 flags = 0 ) const;
+ void BuildUpdate(UpdateDataMapType &);
+
+ virtual void DestroyForPlayer( Player *target ) const;
+
+ const int32& GetInt32Value( uint16 index ) const
+ {
+ ASSERT( index < m_valuesCount || PrintIndexError( index , false) );
+ return m_int32Values[ index ];
+ }
+
+ const uint32& GetUInt32Value( uint16 index ) const
+ {
+ ASSERT( index < m_valuesCount || PrintIndexError( index , false) );
+ return m_uint32Values[ index ];
+ }
+
+ const uint64& GetUInt64Value( uint16 index ) const
+ {
+ ASSERT( index + 1 < m_valuesCount || PrintIndexError( index , false) );
+ return *((uint64*)&(m_uint32Values[ index ]));
+ }
+
+ const float& GetFloatValue( uint16 index ) const
+ {
+ ASSERT( index < m_valuesCount || PrintIndexError( index , false ) );
+ return m_floatValues[ index ];
+ }
+
+ uint8 GetByteValue( uint16 index, uint8 offset) const
+ {
+ ASSERT( index < m_valuesCount || PrintIndexError( index , false) );
+ ASSERT( offset < 4 );
+ return *(((uint8*)&m_uint32Values[ index ])+offset);
+ }
+
+ uint8 GetUInt16Value( uint16 index, uint8 offset) const
+ {
+ ASSERT( index < m_valuesCount || PrintIndexError( index , false) );
+ ASSERT( offset < 2 );
+ return *(((uint16*)&m_uint32Values[ index ])+offset);
+ }
+
+ void SetInt32Value( uint16 index, int32 value );
+ void SetUInt32Value( uint16 index, uint32 value );
+ void SetUInt64Value( uint16 index, const uint64 &value );
+ void SetFloatValue( uint16 index, float value );
+ void SetByteValue( uint16 index, uint8 offset, uint8 value );
+ void SetUInt16Value( uint16 index, uint8 offset, uint16 value );
+ void SetInt16Value( uint16 index, uint8 offset, int16 value ) { SetUInt16Value(index,offset,(uint16)value); }
+ void SetStatFloatValue( uint16 index, float value);
+ void SetStatInt32Value( uint16 index, int32 value);
+
+ void ApplyModUInt32Value(uint16 index, int32 val, bool apply);
+ void ApplyModInt32Value(uint16 index, int32 val, bool apply);
+ void ApplyModUInt64Value(uint16 index, int32 val, bool apply);
+ void ApplyModPositiveFloatValue( uint16 index, float val, bool apply);
+ void ApplyModSignedFloatValue( uint16 index, float val, bool apply);
+
+ void ApplyPercentModFloatValue(uint16 index, float val, bool apply)
+ {
+ val = val != -100.0f ? val : -99.9f ;
+ SetFloatValue(index, GetFloatValue(index) * (apply?(100.0f+val)/100.0f : 100.0f / (100.0f+val)) );
+ }
+
+ void SetFlag( uint16 index, uint32 newFlag );
+ void RemoveFlag( uint16 index, uint32 oldFlag );
+
+ void ToggleFlag( uint16 index, uint32 flag)
+ {
+ if(HasFlag(index, flag))
+ RemoveFlag(index, flag);
+ else
+ SetFlag(index, flag);
+ }
+
+ bool HasFlag( uint16 index, uint32 flag ) const
+ {
+ ASSERT( index < m_valuesCount || PrintIndexError( index , false ) );
+ return (m_uint32Values[ index ] & flag) != 0;
+ }
+
+ void ApplyModFlag( uint16 index, uint32 flag, bool apply)
+ {
+ if(apply) SetFlag(index,flag); else RemoveFlag(index,flag);
+ }
+
+ void SetFlag64( uint16 index, uint64 newFlag )
+ {
+ uint64 oldval = GetUInt64Value(index);
+ uint64 newval = oldval | newFlag;
+ SetUInt64Value(index,newval);
+ }
+
+ void RemoveFlag64( uint16 index, uint64 oldFlag )
+ {
+ uint64 oldval = GetUInt64Value(index);
+ uint64 newval = oldval & ~oldFlag;
+ SetUInt64Value(index,newval);
+ }
+
+ void ToggleFlag64( uint16 index, uint64 flag)
+ {
+ if(HasFlag64(index, flag))
+ RemoveFlag64(index, flag);
+ else
+ SetFlag64(index, flag);
+ }
+
+ bool HasFlag64( uint16 index, uint64 flag ) const
+ {
+ ASSERT( index < m_valuesCount || PrintIndexError( index , false ) );
+ return (GetUInt64Value( index ) & flag) != 0;
+ }
+
+ void ApplyModFlag64( uint16 index, uint64 flag, bool apply)
+ {
+ if(apply) SetFlag64(index,flag); else RemoveFlag64(index,flag);
+ }
+
+ void ClearUpdateMask(bool remove);
+ void SendUpdateObjectToAllExcept(Player* exceptPlayer);
+
+ bool LoadValues(const char* data);
+
+ uint16 GetValuesCount() const { return m_valuesCount; }
+
+ void InitValues() { _InitValues(); }
+
+ virtual bool hasQuest(uint32 /* quest_id */) const { return false; }
+ virtual bool hasInvolvedQuest(uint32 /* quest_id */) const { return false; }
+ protected:
+
+ Object ( );
+
+ void _InitValues();
+ void _Create (uint32 guidlow, uint32 entry, HighGuid guidhigh);
+
+ virtual void _SetUpdateBits(UpdateMask *updateMask, Player *target) const;
+
+ virtual void _SetCreateBits(UpdateMask *updateMask, Player *target) const;
+ void _BuildMovementUpdate(ByteBuffer * data, uint8 flags, uint32 flags2 ) const;
+ void _BuildValuesUpdate(uint8 updatetype, ByteBuffer *data, UpdateMask *updateMask, Player *target ) const;
+
+ uint16 m_objectType;
+
+ uint8 m_objectTypeId;
+ uint8 m_updateFlag;
+
+ union
+ {
+ int32 *m_int32Values;
+ uint32 *m_uint32Values;
+ float *m_floatValues;
+ };
+
+ uint32 *m_uint32Values_mirror;
+
+ uint16 m_valuesCount;
+
+ bool m_objectUpdated;
+
+ private:
+ bool m_inWorld;
+
+ ByteBuffer m_PackGUID;
+
+ // for output helpfull error messages from asserts
+ bool PrintIndexError(uint32 index, bool set) const;
+ Object(const Object&); // prevent generation copy constructor
+ Object& operator=(Object const&); // prevent generation assigment operator
+};
+
+class MANGOS_DLL_SPEC WorldObject : public Object
+{
+ public:
+ virtual ~WorldObject ( ) {}
+
+ virtual void Update ( uint32 /*time_diff*/ ) { }
+
+ void _Create( uint32 guidlow, HighGuid guidhigh, uint32 mapid );
+
+ void Relocate(float x, float y, float z, float orientation)
+ {
+ m_positionX = x;
+ m_positionY = y;
+ m_positionZ = z;
+ m_orientation = orientation;
+ }
+
+ void Relocate(float x, float y, float z)
+ {
+ m_positionX = x;
+ m_positionY = y;
+ m_positionZ = z;
+ }
+
+ void Relocate(WorldLocation const & loc)
+ {
+ SetMapId(loc.mapid);
+ Relocate(loc.x, loc.y, loc.z, loc.o);
+ }
+
+ void SetOrientation(float orientation) { m_orientation = orientation; }
+
+ float GetPositionX( ) const { return m_positionX; }
+ float GetPositionY( ) const { return m_positionY; }
+ float GetPositionZ( ) const { return m_positionZ; }
+ void GetPosition( float &x, float &y, float &z ) const
+ { x = m_positionX; y = m_positionY; z = m_positionZ; }
+ void GetPosition( WorldLocation &loc ) const
+ { loc.mapid = GetMapId(); GetPosition(loc.x, loc.y, loc.z); loc.o = GetOrientation(); }
+ float GetOrientation( ) const { return m_orientation; }
+ void GetNearPoint2D( float &x, float &y, float distance, float absAngle) const;
+ void GetNearPoint( WorldObject const* searcher, float &x, float &y, float &z, float searcher_size, float distance2d,float absAngle) const;
+ void GetClosePoint(float &x, float &y, float &z, float size, float distance2d = 0, float angle = 0) const
+ {
+ // angle calculated from current orientation
+ GetNearPoint(NULL,x,y,z,size,distance2d,GetOrientation() + angle);
+ }
+ void GetContactPoint( const WorldObject* obj, float &x, float &y, float &z, float distance2d = CONTACT_DISTANCE) const
+ {
+ // angle to face `obj` to `this` using distance includes size of `obj`
+ GetNearPoint(obj,x,y,z,obj->GetObjectSize(),distance2d,GetAngle( obj ));
+ }
+
+ float GetObjectSize() const
+ {
+ return ( m_valuesCount > UNIT_FIELD_BOUNDINGRADIUS ) ? m_floatValues[UNIT_FIELD_BOUNDINGRADIUS] : DEFAULT_WORLD_OBJECT_SIZE;
+ }
+ bool IsPositionValid() const;
+ void UpdateGroundPositionZ(float x, float y, float &z) const;
+
+ void GetRandomPoint( float x, float y, float z, float distance, float &rand_x, float &rand_y, float &rand_z ) const;
+
+ void SetMapId(uint32 newMap) { m_mapId = newMap; }
+
+ uint32 GetMapId() const { return m_mapId; }
+
+ uint32 GetZoneId() const;
+ uint32 GetAreaId() const;
+
+ InstanceData* GetInstanceData();
+
+ const char* GetName() const { return m_name.c_str(); }
+ void SetName(std::string newname) { m_name=newname; }
+
+ float GetDistance( const WorldObject* obj ) const;
+ float GetDistance(const float x, const float y, const float z) const;
+ float GetDistance2d(const WorldObject* obj) const;
+ float GetDistance2d(const float x, const float y) const;
+ float GetDistanceZ(const WorldObject* obj) const;
+ bool IsInMap(const WorldObject* obj) const { return GetMapId()==obj->GetMapId() && GetInstanceId()==obj->GetInstanceId(); }
+ bool IsWithinDistInMap(const WorldObject* obj, const float dist2compare) const;
+ bool IsWithinLOS(const float x, const float y, const float z ) const;
+ bool IsWithinLOSInMap(const WorldObject* obj) const;
+
+ float GetAngle( const WorldObject* obj ) const;
+ float GetAngle( const float x, const float y ) const;
+ bool HasInArc( const float arcangle, const WorldObject* obj ) const;
+
+ virtual void SendMessageToSet(WorldPacket *data, bool self);
+ virtual void SendMessageToSetInRange(WorldPacket *data, float dist, bool self);
+ void BuildHeartBeatMsg( WorldPacket *data ) const;
+ void BuildTeleportAckMsg( WorldPacket *data, float x, float y, float z, float ang) const;
+ bool IsBeingTeleported() { return mSemaphoreTeleport; }
+ void SetSemaphoreTeleport(bool semphsetting) { mSemaphoreTeleport = semphsetting; }
+
+ void MonsterSay(const char* text, uint32 language, uint64 TargetGuid);
+ void MonsterYell(const char* text, uint32 language, uint64 TargetGuid);
+ void MonsterTextEmote(const char* text, uint64 TargetGuid, bool IsBossEmote = false);
+ void MonsterWhisper(const char* text, uint64 receiver, bool IsBossWhisper = false);
+ void MonsterSay(int32 textId, uint32 language, uint64 TargetGuid);
+ void MonsterYell(int32 textId, uint32 language, uint64 TargetGuid);
+ void MonsterTextEmote(int32 textId, uint64 TargetGuid, bool IsBossEmote = false);
+ void MonsterWhisper(int32 textId, uint64 receiver, bool IsBossWhisper = false);
+ void BuildMonsterChat(WorldPacket *data, uint8 msgtype, char const* text, uint32 language, char const* name, uint64 TargetGuid) const;
+
+ void SendObjectDeSpawnAnim(uint64 guid);
+
+ virtual void SaveRespawnTime() {}
+
+ uint32 GetInstanceId() const { return m_InstanceId; }
+ void SetInstanceId(uint32 val) { m_InstanceId = val; }
+
+ void AddObjectToRemoveList();
+
+ // main visibility check function in normal case (ignore grey zone distance check)
+ bool isVisibleFor(Player const* u) const { return isVisibleForInState(u,false); }
+
+ // low level function for visibility change code, must be define in all main world object subclasses
+ virtual bool isVisibleForInState(Player const* u, bool inVisibleList) const = 0;
+
+ Map * GetMap() const;
+ Map const* GetBaseMap() const;
+ Creature* SummonCreature(uint32 id, float x, float y, float z, float ang,TempSummonType spwtype,uint32 despwtime);
+
+ protected:
+ explicit WorldObject();
+ std::string m_name;
+
+ private:
+ uint32 m_mapId;
+
+ float m_positionX;
+ float m_positionY;
+ float m_positionZ;
+ float m_orientation;
+
+ bool mSemaphoreTeleport;
+
+ uint32 m_InstanceId;
+};
+#endif