2004-05-22 02:57:54 +02:00
|
|
|
// Entity.h
|
|
|
|
//
|
2004-07-20 21:30:35 +02:00
|
|
|
// Mark Thompson mot20@cam.ac.uk / mark@wildfiregames.com
|
2004-05-22 02:57:54 +02:00
|
|
|
//
|
|
|
|
// Entity class.
|
|
|
|
//
|
|
|
|
// Usage: Do not attempt to instantiate this class directly. (See EntityManager.h)
|
|
|
|
// Most of the members are trivially obvious; some highlights are:
|
|
|
|
//
|
2005-05-10 09:13:25 +02:00
|
|
|
// HEntity me: is a reference to this entity. See EntityHandles.h
|
2004-05-29 05:32:33 +02:00
|
|
|
//
|
|
|
|
// Destroying entities: An entity is destroyed when all references to it expire.
|
|
|
|
// It is somewhat unfunny if this happens while a method from this
|
|
|
|
// class is still executing. If you need to kill an entity,
|
2004-07-20 21:30:35 +02:00
|
|
|
// use CEntity::kill(). If kill() releases the final handle,
|
2004-05-29 05:32:33 +02:00
|
|
|
// the entity is placed in the reaper queue and is deleted immediately
|
|
|
|
// prior to its next update cycle.
|
|
|
|
//
|
2004-05-22 02:57:54 +02:00
|
|
|
// CUnit* m_actor: is the visible representation of this entity.
|
|
|
|
//
|
|
|
|
// snapToGround(): Called every frame, this will ensure the entity never takes flight.
|
|
|
|
// updateActorTransforms(): Must be called every time the position of this entity changes.
|
2004-05-26 22:57:25 +02:00
|
|
|
// Also remember to update the collision object if you alter the position directly.
|
2004-05-22 02:57:54 +02:00
|
|
|
//
|
2004-05-22 01:46:16 +02:00
|
|
|
|
|
|
|
#ifndef ENTITY_INCLUDED
|
|
|
|
#define ENTITY_INCLUDED
|
|
|
|
|
|
|
|
#include <deque>
|
2005-04-22 09:12:55 +02:00
|
|
|
#include "scripting/ScriptableComplex.h"
|
2005-01-18 01:46:18 +01:00
|
|
|
#include "Player.h"
|
2004-05-22 01:46:16 +02:00
|
|
|
|
2004-05-26 22:57:25 +02:00
|
|
|
#include "Vector2D.h"
|
2004-05-22 01:46:16 +02:00
|
|
|
#include "Vector3D.h"
|
|
|
|
#include "UnitManager.h"
|
|
|
|
#include "EntityOrders.h"
|
|
|
|
#include "EntityHandles.h"
|
|
|
|
#include "EntityMessage.h"
|
2004-10-07 21:23:35 +02:00
|
|
|
#include "EventHandlers.h"
|
2004-12-12 20:43:55 +01:00
|
|
|
#include "ScriptObject.h"
|
2005-04-15 06:23:33 +02:00
|
|
|
#include "ObjectEntry.h"
|
2004-11-11 08:09:32 +01:00
|
|
|
#include "EntitySupport.h"
|
2004-05-22 01:46:16 +02:00
|
|
|
|
2004-12-12 20:43:55 +01:00
|
|
|
class CBaseEntity;
|
|
|
|
class CBoundingObject;
|
|
|
|
class CUnit;
|
|
|
|
|
2004-11-11 08:09:32 +01:00
|
|
|
// TODO MT: Put this is /some/ sort of order...
|
|
|
|
|
2005-04-22 09:12:55 +02:00
|
|
|
class CEntity : public CJSComplex<CEntity>, public IEventTarget
|
2004-05-22 01:46:16 +02:00
|
|
|
{
|
2004-06-02 18:11:32 +02:00
|
|
|
friend class CEntityManager;
|
2005-01-23 22:58:06 +01:00
|
|
|
private:
|
|
|
|
// The player that owns this entity
|
|
|
|
CPlayer* m_player;
|
|
|
|
|
2004-05-22 01:46:16 +02:00
|
|
|
public:
|
2004-06-11 00:24:03 +02:00
|
|
|
// Intrinsic properties
|
2004-10-07 21:23:35 +02:00
|
|
|
CBaseEntity* m_base;
|
2004-11-11 08:09:32 +01:00
|
|
|
|
|
|
|
// The entity to switch to when this dies.
|
|
|
|
CStrW m_corpse;
|
2004-10-07 21:23:35 +02:00
|
|
|
|
2005-05-01 21:09:13 +02:00
|
|
|
// The class types this entity has
|
|
|
|
SClassSet m_classes;
|
|
|
|
|
2004-10-07 21:23:35 +02:00
|
|
|
float m_speed;
|
|
|
|
float m_turningRadius;
|
2005-05-01 21:09:13 +02:00
|
|
|
SEntityAction m_melee;
|
|
|
|
SEntityAction m_gather;
|
2004-10-07 21:23:35 +02:00
|
|
|
bool m_selected;
|
|
|
|
i32 m_grouped;
|
2004-07-20 21:30:35 +02:00
|
|
|
|
2004-11-11 08:09:32 +01:00
|
|
|
// If this unit has been removed from the gameworld but has still
|
|
|
|
// has references.
|
|
|
|
bool m_destroyed;
|
|
|
|
|
|
|
|
// If this unit is still active in the gameworld - i.e. not a corpse.
|
|
|
|
bool m_extant;
|
2004-07-20 21:30:35 +02:00
|
|
|
|
2005-09-05 23:45:26 +02:00
|
|
|
// HP properties
|
|
|
|
float m_healthCurr;
|
|
|
|
float m_healthMax;
|
2005-09-06 21:30:41 +02:00
|
|
|
float m_healthBarHeight;
|
2005-09-14 21:43:16 +02:00
|
|
|
|
|
|
|
// Minimap properties
|
|
|
|
CStrW m_minimapType;
|
|
|
|
int m_minimapR;
|
|
|
|
int m_minimapG;
|
|
|
|
int m_minimapB;
|
2005-09-05 23:45:26 +02:00
|
|
|
|
2005-09-18 05:47:15 +02:00
|
|
|
// Y anchor
|
|
|
|
CStrW m_anchorType;
|
|
|
|
|
2005-10-09 05:43:03 +02:00
|
|
|
// LOS
|
|
|
|
int m_los;
|
|
|
|
bool m_permanent;
|
|
|
|
|
2004-07-20 21:30:35 +02:00
|
|
|
//-- Interpolated property
|
|
|
|
CVector3D m_position;
|
|
|
|
CVector3D m_position_previous;
|
2004-10-07 21:23:35 +02:00
|
|
|
CVector3D m_graphics_position;
|
2004-07-23 12:56:52 +02:00
|
|
|
|
2004-05-26 22:57:25 +02:00
|
|
|
CBoundingObject* m_bounds;
|
2004-05-22 01:46:16 +02:00
|
|
|
float m_targetorientation;
|
2004-05-26 22:57:25 +02:00
|
|
|
CVector2D m_ahead;
|
2004-07-20 21:30:35 +02:00
|
|
|
|
|
|
|
//-- Interpolated property
|
|
|
|
float m_orientation;
|
|
|
|
float m_orientation_previous;
|
2004-10-07 21:23:35 +02:00
|
|
|
float m_graphics_orientation;
|
|
|
|
|
2005-10-07 04:44:54 +02:00
|
|
|
// If the actor's current transform data is valid (i.e. the entity hasn't
|
|
|
|
// moved since it was last calculated).
|
|
|
|
bool m_actor_transform_valid;
|
|
|
|
|
2004-10-07 21:23:35 +02:00
|
|
|
//-- Scripts
|
2004-10-23 16:39:28 +02:00
|
|
|
|
2005-04-22 09:12:55 +02:00
|
|
|
// Get script execution contexts - always run in the context of the entity that fired it.
|
|
|
|
JSObject* GetScriptExecContext( IEventTarget* target ) { return( ((CEntity*)target)->GetScript() ); }
|
|
|
|
|
2004-10-07 21:23:35 +02:00
|
|
|
CScriptObject m_EventHandlers[EVENT_LAST];
|
2004-07-20 21:30:35 +02:00
|
|
|
|
2004-05-22 01:46:16 +02:00
|
|
|
CUnit* m_actor;
|
2004-11-11 08:09:32 +01:00
|
|
|
|
|
|
|
// State transition in the FSM (animations should be reset)
|
|
|
|
bool m_transition;
|
|
|
|
int m_lastState;
|
2005-05-01 21:09:13 +02:00
|
|
|
|
|
|
|
// Position in the current state's cycle
|
2005-05-18 07:32:09 +02:00
|
|
|
static const size_t NOT_IN_CYCLE = (size_t)-1;
|
2005-05-01 21:09:13 +02:00
|
|
|
size_t m_fsm_cyclepos; // -cycle_length....cycle_length
|
|
|
|
CSkeletonAnim* m_fsm_animation; // the animation we're about to play this cycle,
|
|
|
|
size_t m_fsm_anipos; // the time at which we should start playing it.
|
|
|
|
size_t m_fsm_anipos2; // for when there are two animation-related events we need to take care of.
|
2004-05-22 01:46:16 +02:00
|
|
|
|
|
|
|
std::deque<CEntityOrder> m_orderQueue;
|
|
|
|
|
2004-05-22 02:57:54 +02:00
|
|
|
private:
|
2004-05-22 01:46:16 +02:00
|
|
|
CEntity( CBaseEntity* base, CVector3D position, float orientation );
|
2004-05-28 04:57:50 +02:00
|
|
|
|
2005-05-01 21:09:13 +02:00
|
|
|
uint processGotoHelper( CEntityOrder* current, size_t timestep_milli, HEntity& collide );
|
2005-04-15 06:23:33 +02:00
|
|
|
|
2005-05-01 21:09:13 +02:00
|
|
|
bool processContactAction( CEntityOrder* current, size_t timestep_millis, int transition, SEntityAction* action );
|
2005-05-21 03:40:32 +02:00
|
|
|
bool processContactActionNoPathing( CEntityOrder* current, size_t timestep_millis, const CStr& animation, CScriptEvent* contactEvent, SEntityAction* action );
|
2005-04-15 06:23:33 +02:00
|
|
|
|
2004-11-11 08:09:32 +01:00
|
|
|
bool processAttackMelee( CEntityOrder* current, size_t timestep_milli );
|
|
|
|
bool processAttackMeleeNoPathing( CEntityOrder* current, size_t timestep_milli );
|
2005-04-15 06:23:33 +02:00
|
|
|
bool processGather( CEntityOrder* current, size_t timestep_milli );
|
|
|
|
bool processGatherNoPathing( CEntityOrder* current, size_t timestep_milli );
|
|
|
|
|
2004-07-27 23:00:53 +02:00
|
|
|
bool processGotoNoPathing( CEntityOrder* current, size_t timestep_milli );
|
|
|
|
bool processGoto( CEntityOrder* current, size_t timestep_milli );
|
|
|
|
bool processPatrol( CEntityOrder* current, size_t timestep_milli );
|
2004-05-28 04:57:50 +02:00
|
|
|
|
2004-05-22 01:46:16 +02:00
|
|
|
public:
|
2004-05-29 05:32:33 +02:00
|
|
|
~CEntity();
|
2004-05-22 01:46:16 +02:00
|
|
|
|
|
|
|
// Handle-to-self.
|
|
|
|
HEntity me;
|
2004-07-20 21:30:35 +02:00
|
|
|
|
2004-10-23 16:39:28 +02:00
|
|
|
// Updates gameplay information for the specified timestep
|
2004-07-27 23:00:53 +02:00
|
|
|
void update( size_t timestep_millis );
|
2004-10-23 16:39:28 +02:00
|
|
|
// Updates graphical information for a point between the last and current simulation frame; 0 < relativeoffset < 1.
|
|
|
|
void interpolate( float relativeoffset );
|
|
|
|
|
2005-05-27 02:38:30 +02:00
|
|
|
// Updates auras
|
|
|
|
void UpdateAuras( size_t timestep_millis );
|
|
|
|
|
2005-01-23 23:32:10 +01:00
|
|
|
// Removes entity from the gameworld and deallocates it, but not necessarily immediately.
|
2004-07-20 21:30:35 +02:00
|
|
|
void kill();
|
|
|
|
|
2004-11-11 08:09:32 +01:00
|
|
|
// Process initialization
|
|
|
|
void Initialize();
|
|
|
|
|
|
|
|
// Process tick.
|
|
|
|
void Tick();
|
|
|
|
|
2005-01-23 22:58:06 +01:00
|
|
|
// Store the player associated with this entity
|
2005-01-24 00:04:00 +01:00
|
|
|
void SetPlayer(CPlayer *pPlayer);
|
2005-01-23 22:58:06 +01:00
|
|
|
|
2005-01-23 23:32:10 +01:00
|
|
|
// Retrieve the player associated with this entity
|
2005-01-24 07:14:13 +01:00
|
|
|
CPlayer* GetPlayer() { return m_player; }
|
2005-01-23 22:58:06 +01:00
|
|
|
|
2004-11-11 08:09:32 +01:00
|
|
|
// Process damage
|
|
|
|
void Damage( CDamageType& damage, CEntity* inflictor = NULL );
|
|
|
|
|
2005-09-18 05:47:15 +02:00
|
|
|
float getAnchorLevel( float x, float z );
|
|
|
|
|
2004-05-22 01:46:16 +02:00
|
|
|
void snapToGround();
|
2004-07-20 21:30:35 +02:00
|
|
|
void updateActorTransforms();
|
2004-10-23 16:39:28 +02:00
|
|
|
|
2005-05-01 21:09:13 +02:00
|
|
|
// Getter and setter for the class sets
|
|
|
|
jsval getClassSet();
|
|
|
|
void setClassSet( jsval value );
|
|
|
|
void rebuildClassSet();
|
|
|
|
|
2004-10-23 16:39:28 +02:00
|
|
|
// Things like selection circles and debug info - possibly move to gui if/when it becomes responsible for (and capable of) it.
|
2004-07-20 21:30:35 +02:00
|
|
|
void render();
|
|
|
|
void renderSelectionOutline( float alpha = 1.0f );
|
2005-09-06 21:30:41 +02:00
|
|
|
void renderHealthBar();
|
2004-07-20 21:30:35 +02:00
|
|
|
|
2004-10-23 16:39:28 +02:00
|
|
|
// After a collision, recalc the path to the next fixed waypoint.
|
2004-06-11 00:24:03 +02:00
|
|
|
void repath();
|
|
|
|
|
2004-10-23 16:39:28 +02:00
|
|
|
// Reset properties after the entity-template we use changes.
|
2004-06-11 00:24:03 +02:00
|
|
|
void loadBase();
|
2004-07-20 21:30:35 +02:00
|
|
|
|
|
|
|
void reorient(); // Orientation
|
2004-06-11 00:24:03 +02:00
|
|
|
void teleport(); // Fixes things if the position is changed by something externally.
|
2004-11-11 08:09:32 +01:00
|
|
|
void checkSelection(); // In case anyone tries to select/deselect this through JavaScript.
|
2004-07-20 21:30:35 +02:00
|
|
|
void checkGroup(); // Groups
|
2005-01-17 00:09:41 +01:00
|
|
|
void checkExtant(); // Existence
|
2004-07-20 21:30:35 +02:00
|
|
|
|
2004-10-23 16:39:28 +02:00
|
|
|
// Returns whether the entity is capable of performing the given orderType on the target.
|
2004-07-20 21:30:35 +02:00
|
|
|
bool acceptsOrder( int orderType, CEntity* orderTarget );
|
2004-06-11 00:24:03 +02:00
|
|
|
|
2004-07-20 21:30:35 +02:00
|
|
|
void clearOrders();
|
2004-05-22 01:46:16 +02:00
|
|
|
void pushOrder( CEntityOrder& order );
|
2004-10-07 21:23:35 +02:00
|
|
|
|
|
|
|
// Script constructor
|
|
|
|
|
2005-08-09 17:55:44 +02:00
|
|
|
static JSBool Construct( JSContext* cx, JSObject* obj, uint argc, jsval* argv, jsval* rval );
|
2004-10-07 21:23:35 +02:00
|
|
|
|
|
|
|
// Script-bound functions
|
|
|
|
|
|
|
|
jsval ToString( JSContext* cx, uintN argc, jsval* argv );
|
2005-05-18 07:32:09 +02:00
|
|
|
|
2004-10-07 21:23:35 +02:00
|
|
|
bool Order( JSContext* cx, uintN argc, jsval* argv, bool Queued );
|
|
|
|
inline bool OrderSingle( JSContext* cx, uintN argc, jsval* argv )
|
|
|
|
{
|
|
|
|
return( Order( cx, argc, argv, false ) );
|
|
|
|
}
|
|
|
|
inline bool OrderQueued( JSContext* cx, uintN argc, jsval* argv )
|
|
|
|
{
|
|
|
|
return( Order( cx, argc, argv, true ) );
|
|
|
|
}
|
2004-11-11 08:09:32 +01:00
|
|
|
bool Damage( JSContext* cx, uintN argc, jsval* argv );
|
|
|
|
bool Kill( JSContext* cx, uintN argc, jsval* argv );
|
2005-04-15 06:23:33 +02:00
|
|
|
jsval GetSpawnPoint( JSContext* cx, uintN argc, jsval* argv );
|
2005-08-09 17:55:44 +02:00
|
|
|
bool IsIdle( JSContext* UNUSED(cx), uintN UNUSED(argc), jsval* UNUSED(argv) )
|
2004-11-11 08:09:32 +01:00
|
|
|
{
|
|
|
|
return( m_orderQueue.empty() );
|
|
|
|
}
|
2005-05-01 21:09:13 +02:00
|
|
|
bool HasClass( JSContext* cx, uintN argc, jsval* argv )
|
|
|
|
{
|
2005-06-28 06:06:25 +02:00
|
|
|
debug_assert( argc >= 1 );
|
2005-05-01 21:09:13 +02:00
|
|
|
return( m_classes.IsMember( ToPrimitive<CStrW>( cx, argv[0] ) ) );
|
|
|
|
}
|
2004-10-07 21:23:35 +02:00
|
|
|
static void ScriptingInit();
|
2005-08-09 17:55:44 +02:00
|
|
|
|
|
|
|
private:
|
|
|
|
// squelch "unable to generate" warnings
|
|
|
|
CEntity(const CEntity& rhs);
|
|
|
|
const CEntity& operator=(const CEntity& rhs);
|
2004-05-22 01:46:16 +02:00
|
|
|
};
|
|
|
|
|
2004-07-22 18:18:12 +02:00
|
|
|
// General entity globals
|
|
|
|
|
|
|
|
|
2004-12-12 20:43:55 +01:00
|
|
|
// In its current incarnation, inefficient but pretty
|
2004-07-22 18:18:12 +02:00
|
|
|
#define SELECTION_TERRAIN_CONFORMANCE
|
|
|
|
|
|
|
|
extern int SELECTION_CIRCLE_POINTS;
|
|
|
|
extern int SELECTION_BOX_POINTS;
|
|
|
|
extern int SELECTION_SMOOTHNESS_UNIFIED;
|
|
|
|
|
2004-06-02 18:11:32 +02:00
|
|
|
#endif
|