
#ifndef __LOADLND_H__
#define __LOADLND_H__

//#include "types.nh"


enum
{
	FLAME_VENT,
	STEAM_VENT,
	AIR_VENT,
	SMOKE_VENT,
	SNOWBALL_VENT,
	BOULDER_VENT,
	ICICLE_VENT,
	FLOATY_VENT,
	BUBBLE_VENT,
	CANNONBALL_VENT,
	WATER_VENT,		// new
	NUMVENTS,
};



/*
#define SET_ON_FIRE (1<<9)
#define ON_FIRE		(1<<10)
*/




enum
{
	STUN,				//0
	DEATH,				//1
	FROGGY,				//2
	SUCTION,			//3
	HERCULES,			//4
	SPEEDUP,			//5
	ROTORBLADES,		//6
	BOWLINGBALL,		//7
	POWERBALL,			//8
	BALLBEARING,		//9
	BEACHBALL,			//10
	SNOWBALL,			//11
	CRYSTALBALL,		//12
	BOOMERANGBALL,		//13
	VANISHBALL,			//14
	NUMPICKUPS			//15
};

enum
{
	STONE,
	GRASS,
	ICE,
	MUD,
	SAND,
	WATERY,
	LAVA,
	STICKY,
	SLIDY,
	GOO,
	SNOW,
	ICYSNOW,
	FORCE_FIELD,
	STICKY2,		// new
	UNDERWATER,
	NUM_TERRAIN_TYPES
};

enum
{
	TOKEN_NULL,								// 0
	TOKEN_HAND_START,						
	TOKEN_BALL_START,						
	TOKEN_CAMERA_START,						
	TOKEN_PUZZLE,							// 4
	TOKEN_PUZZLE_AND,						
	TOKEN_PUZZLE_OR,						
	TOKEN_PUZZLE_NUMTIMES,					
	TOKEN_PUZZLE_ANY,						// 8
	TOKEN_CONDITION_AT_POINT,				
	TOKEN_CONDITION_AT_SPIN,				
	TOKEN_CONDITION_AT_ORBIT,				
	TOKEN_CONDITION_JUST_AT_POINT,			// c
	TOKEN_CONDITION_JUST_AT_SPIN,			
	TOKEN_CONDITION_JUST_AT_ORBIT,			
	TOKEN_CONDITION_HAND_ON,				
	TOKEN_CONDITION_HAND_JUST_ON,			// 10
	TOKEN_CONDITION_BALL_ON,				
	TOKEN_CONDITION_BALL_JUST_ON,			
	TOKEN_CONDITION_NME_ON,					
	TOKEN_CONDITION_NME_JUST_ON,			// 14
	TOKEN_CONDITION_HAND_TOUCHING,			
	TOKEN_CONDITION_HAND_JUST_TOUCHED,		
	TOKEN_CONDITION_BALL_TOUCHING,			
	TOKEN_CONDITION_BALL_JUST_TOUCHED,		// 18
	TOKEN_CONDITION_NME_TOUCHING,			
	TOKEN_CONDITION_NME_JUST_TOUCHED,		
	TOKEN_CONDITION_VAR_EQUAL,				
	TOKEN_CONDITION_VAR_NOT_EQUAL,			// 1c
	TOKEN_CONDITION_VAR_GREATER_THAN,			
	TOKEN_CONDITION_VAR_LESS_THAN,			
	TOKEN_CONDITION_CONFINED,				
	TOKEN_CONDITION_JUST_CONFINED,			// 20
	TOKEN_CONDITION_NME_DEAD,					
	TOKEN_CONDITION_HAND_CROSSES_LINE,		
	TOKEN_CONDITION_HAND_IN_BOX,			
	TOKEN_CONDITION_HAND_IN_RANGE,			// 24
	TOKEN_CONDITION_BALL_IN_BOX,			
	TOKEN_CONDITION_BALL_IN_RANGE,			
	TOKEN_CONDITION_CAM_IN_BOX,				
	TOKEN_CONDITION_CAM_IN_RANGE,			// 28
	TOKEN_CONDITION_HAND_IN_CYLINDER,
	TOKEN_CONDITION_DESTROYED,
	TOKEN_CONDITION_COLLECTED,
	TOKEN_CONDITION_PICKUP_ON,				// 2c
	TOKEN_CONDITION_JUST_AT_ROT,
	TOKEN_CONDITION_DUMMY0,
	TOKEN_CONDITION_DUMMY1,
	TOKEN_CONDITION_DUMMY2,
	TOKEN_CONDITION_DUMMY3,
	TOKEN_CONDITION_DUMMY4,
	TOKEN_ACTION_START_MOVE,			  				
	TOKEN_ACTION_START_SPIN,			  	
	TOKEN_ACTION_START_ORBIT,			  	
	TOKEN_ACTION_SET_NEXT_POINT,		  	// 30
	TOKEN_ACTION_SET_NEXT_SPIN,			  	
	TOKEN_ACTION_SET_SPIN_WAIT,
	TOKEN_ACTION_SET_SPIN_AXIS,			  	
	TOKEN_ACTION_SET_STATE,				  	// 34
	TOKEN_ACTION_SET_CONVEYOR,
	TOKEN_ACTION_SET_EXISTANCE,			  	
	TOKEN_ACTION_SET_GRAVITY,			
	TOKEN_ACTION_SET_VAR,				  	// 38
	TOKEN_ACTION_ADDTO_VAR,				  
	TOKEN_ACTION_SUBFROM_VAR,
	TOKEN_ACTION_DROP_PICKUP,			  	
	TOKEN_ACTION_ADD_NME,					// 3c
	TOKEN_ACTION_MOVE_PLAT,
	TOKEN_ACTION_LOOK_AT_PLAT,			  	
	TOKEN_ACTION_LOOK_AT_POINT,			  	
	TOKEN_ACTION_SET_CAMERA_POS,		  	// 40
	TOKEN_ACTION_SET_CAM_DIST,		  	
	TOKEN_ACTION_SET_CAM_HEIGHT,		  	
	TOKEN_ACTION_NME_GOTO_ACTION,		  	
	TOKEN_ACTION_SET_WIND,				  	// 44
	TOKEN_ACTION_DROP_GARIBS,			  	
	TOKEN_ACTION_CAM_HEIGHT,			  	
	TOKEN_ACTION_CAM_DISTANCE,			  	
	TOKEN_ACTION_CAM_PARALLEL,			  	// 48
	TOKEN_ACTION_CAM_FIXEDPOS,			  	
	TOKEN_ACTION_CAM_FIXEDROT,			  	
	TOKEN_ACTION_CAM_CORNER,			  	
	TOKEN_ACTION_CAM_IGNORE_SLOPES,		  	// 4c
	TOKEN_ACTION_CAM_CIRCLE,
	TOKEN_ACTION_SET_WATERLEVEL,		  
	TOKEN_ACTION_EARTHQUAKE,			  
	TOKEN_ACTION_SET_LEVEL_GRAVITY,			// 50
	TOKEN_ACTION_START_CAMEO,
	TOKEN_ACTION_SET_PLAT_DIR,
	TOKEN_ACTION_UNFREEZE_BALL,
	TOKEN_ACTION_START_SOUND,				// 54
	TOKEN_ACTION_SET_BACKDROP,
	TOKEN_ACTION_SET_FOG,
	TOKEN_ACTION_ADD_TO_SCORE,
	TOKEN_ACTION_SET_TERRAIN,
	TOKEN_ACTION_DESTROY,
	TOKEN_ACTION_TELEPORT_TO,
	TOKEN_ACTION_DUMMY1,
	TOKEN_ACTION_DUMMY2,
	TOKEN_ACTION_DUMMY3,
	TOKEN_ACTION_DUMMY4,
	TOKEN_SPINTOMOVE,						// 58
	TOKEN_MOVETOSPIN,						
	TOKEN_SPINTOSPIN,						
	TOKEN_PUSH,								
	TOKEN_HEADSTART,						// 5c
	TOKEN_DUMMY,							
	TOKEN_LOOKATPOINT,						
	TOKEN_GOFORWARDS,						
	TOKEN_LOOKATHAND,						// 60
	TOKEN_LOOKATBALL,						
	TOKEN_PLATFORM,							
	TOKEN_RESTART,							
	TOKEN_NOCOLLISION,						// 64
	TOKEN_DESTRUCTIBLE,						
	TOKEN_REVERSING,						
	TOKEN_CRUMBLE,							
	TOKEN_CONVEYOR,							// 68
	TOKEN_CATAPULT,							
	TOKEN_TERRAIN,							
	TOKEN_POINT,							
	TOKEN_SPEED,							// 6c
	TOKEN_ACCEL,							
	TOKEN_BOUNCE,							
	TOKEN_TAG,								
	TOKEN_PENDULUM,							// 70
	TOKEN_PARENTTAG,						
	TOKEN_CONFINE,							
	TOKEN_MOVETARGET,						
	TOKEN_MOVEBYSPEED,						// 74
	TOKEN_ORBIT,							
	TOKEN_ORBITPAUSE,						
	TOKEN_ORBITFLIP,						
	TOKEN_SYMMETRY,							// 78
	TOKEN_SCALE,							
	TOKEN_STRETCH,							
	TOKEN_TAKESPIN,							
	TOKEN_SPINPAUSE,						// 7c
	TOKEN_SPINFLIP,							
	TOKEN_MAXROT,							
	TOKEN_SPIN,								
	TOKEN_SEESAW,							// 80
	TOKEN_TOPPLE,							
	TOKEN_SPIKE,							
	TOKEN_ENEMY,							
	TOKEN_END_ENEMY,						// 84
	TOKEN_GARIBGROUP,						
	TOKEN_GARIB,							
	TOKEN_PICKUP,							
	TOKEN_SCENERY,							// 88
	TOKEN_TELEPORT,							
	TOKEN_FAN,								
	TOKEN_MAGNET,							
	TOKEN_WIND,								// 8c
	TOKEN_ROPEBRIDGE,						
	TOKEN_ELECTRIC,							
	TOKEN_ORBITBRIDGE,						
	TOKEN_SINEBRIDGE,						// 90
	TOKEN_BACKGROUND,						
	TOKEN_LANDSCAPE,						
	TOKEN_LANDROT,
	TOKEN_LANDSCALE,						// 94
	TOKEN_CONDITION,						
	TOKEN_ACTION,							
	TOKEN_LIGHT,							
	TOKEN_AMBIENT_LIGHT,					// 98
	TOKEN_BACKDROP,							
	TOKEN_NORMAL_INSTRUCTION,				
	TOKEN_CONDITIONAL_INSTRUCTION,			
	TOKEN_ATTACK_INSTRUCTION,				// 9c
	TOKEN_GRAVITY,							
	TOKEN_CURRENT,							
	TOKEN_TILTY,
	TOKEN_WATER,							// a0
	TOKEN_CONFINE_ENEMY,
	TOKEN_VENT,
	TOKEN_VENT_PATTERN,
	TOKEN_FLOATS,							// a4
	TOKEN_FOG,
	TOKEN_POS,
	TOKEN_STARTPOINT,
	TOKEN_EXITDOOR,							// a8
	TOKEN_LEVEL_GRAVITY,
	TOKEN_CAMEO,
	TOKEN_CAMEO_INSTRUCTION,
	TOKEN_CAMEO_INSTRUCTION_ANIMATION,		// ac
	TOKEN_CAMEO_INSTRUCTION_TARGET_CAMERA,
	TOKEN_CAMEO_INSTRUCTION_MOVE_ACTOR,
	TOKEN_CAMEO_INSTRUCTION_ROTATE_ACTOR,
	TOKEN_CAMEO_INSTRUCTION_TIE_ACTOR_TO_SPHERE,	// b0
	TOKEN_CAMEO_INSTRUCTION_DISABLE_ACTOR,
	TOKEN_CAMEO_INSTRUCTION_LIGHTNING,
	TOKEN_MODGE,
	TOKEN_SPARKLY,							// b4
	TOKEN_BUZZER,
	TOKEN_BUZZER_PATTERN,
	TOKEN_COLL_OFFSET,
	TOKEN_RECALC,							// b8
	TOKEN_NOCAMCOLLIDE,					
	TOKEN_DISABLE_REDIRECTION,
	TOKEN_TIP,
	TOKEN_CAMEO_OBJ,						// bc
	TOKEN_AMBIENT_SOUND,
	TOKEN_SOUND,
	TOKEN_CAMEO_CAM,
	TOKEN_ANIMATE_PLATFORM,					// c0
	TOKEN_MOVE_SOUND,
	TOKEN_STOP_SOUND,
	TOKEN_SPIN_SOUND,
	TOKEN_ORBIT_SOUND,						// c4
	TOKEN_SPIN_STOP_SOUND,
	TOKEN_ORBIT_STOP_SOUND,
	TOKEN_CRUMBLE_SOUND,
	TOKEN_DESTROY_SOUND,					// c8
	TOKEN_TIP_NUMBER,

};											
											
#define	TOKEN_END 32000

enum
{
	CAMEO_INSTRUCTION_ANIMATION,
	CAMEO_INSTRUCTION_TARGET_CAMERA,
	CAMEO_INSTRUCTION_MOVE_ACTOR,
	CAMEO_INSTRUCTION_ROTATE_ACTOR,
	CAMEO_INSTRUCTION_TIE_ACTOR_TO_SPHERE,
	CAMEO_INSTRUCTION_DISABLE_ACTOR,
	CAMEO_INSTRUCTION_LIGHTNING,
	NUM_CAMEO_INSTRUCTION_TYPES,
};

enum
{
	NME_MOVETO,			//0
	NME_MOVETO2D,		//1
	NME_FACETO,			//2
	NME_RANDOMMOVE,		//3
	NME_WAIT,			//4
	NME_FIRE1,			//5
	NME_FIRE2,			//6
	NME_SPECIAL,		//7
	NME_FACEPLAYER,		//8
	NME_FOLLOWPLAYER,	//9
	NME_HOLDPLAYER,		//10
	NME_DROPPLAYER,		//11
	NME_FLEEPLAYER,		//12
	NME_CIRCLE,			//13
	NME_DONTATTACK,		//14
	NME_ATTACK,			//15
	NME_ENDATTACK,		//16
	NME_CHARGE,			//17
	NME_BRANCH,			//18
	NME_RETURN,			//19
	NME_LOOP,			//20
	NME_LOADCOUNTER,	//21
	NME_MOVE_VECTOR,	//22
	NME_JUMP,			//23
	NME_DIE,			//24
};

//enemy action conditions
enum
{
	IF_BALL_IN_RANGE,
	IF_BALL_IN_RANGE_2D,
	IF_HAND_IN_RANGE,
	IF_HAND_IN_RANGE_2D,
	IF_CLOSEST_IN_RANGE,
	IF_CLOSEST_IN_RANGE_2D,
	IF_CANSEE_BALL,
	IF_CANSEE_HAND,
	IF_CANSEE_CLOSEST,
	EVERY_NUM_FRAMES,
	BETWEEN_SPIN_VALS,
	IF_HAND_HOLDING_BALL,
	IF_HAND_NOT_HOLDING_BALL,
	IF_IM_HOLDING_BALL,
	IF_IM_NOT_HOLDING_BALL,
	IF_IM_HOLDING_HAND,
	IF_IM_NOT_HOLDING_HAND,
	IF_TOUCHING_BALL,
	IF_TOUCHING_HAND,
	IF_OUT_OF_BOUNDS,
	ALWAYS,
	NEVER,
	SOMETIMES
};



// note - fred changed this back to a filename
void ParseLandscapeFile(char *filename);
void ReleaseLandscapeFile();

int ParseTokenCameo(short token,UBYTE **data);



/*
typedef struct tagSCENERYPOS
{
	VECTOR pos;
}SCENERYPOS;

extern SCENERYPOS *sceneries;
extern ULONG numberofsceneries;
*/

// ========= platform-reading ===========

#define PLATFORM_MAX_POINTS 20

typedef struct PLATFORM_DEFTAG *PLATFORM_DEFHANDLE;

typedef struct PLATFORM_POINTTAG
{
	VECTOR	pos;
	int		wait;
}PLATFORM_POINTSTR;


// bitmasks for the platform's "flags" short
#define PLATFLAG_NOCOLLISION		1
#define PLATFLAG_IS_RESTART			2

#define PLATFLAG_DESTRUCTIBLE		4
#define PLATFLAG_DESTRUCT_BALL		8
#define PLATFLAG_DESTRUCT_NODUST	16

#define PLATFLAG_CRUMBLE			32

#define PLATFLAG_NOCAMCOLLISION		64

#define PLATFLAG_EXITDOOR			128
#define PLATFLAG_TELEPORT			256
#define PLATFLAG_HOOP				512

typedef struct PLATFORM_HEADERTAG
{
	PLATFORM_DEFHANDLE next;
	//char	name[8];		// Note - max len of the filename will be 7 characters till I redo scripted
	//char	sFragName[8];
	ULONG	platID;
	char	n_points;		// even if n_points = 0, points[0] is the position
	char	pad;

	short	flags;
//	char	nocollision;	// eg - restart points
//	char	restart;		// it's a restart gate

	short	tag;			// the all-important "tag" used for all the puzzle stuff
	short	parentTag;		// parent platform

	int		start_point;
	int		maxspeed;
	int		accel;

	short	terrain;

	short	move_sfx;	// high byte = bank
	short	move_pitch;
	short	move_vol;
	short	stop_sfx;	// high byte = bank
	short	stop_pitch;
	short	stop_vol;
	short	dest_sfx;	// high byte = bank
	short	dest_pitch;
	short	dest_vol;

	struct
	{
		int		nBits;
		ULONG	fragID;
	}destruct;

	struct
	{
		short yes;
		short limit;
		short time;
		short grav;
	}crumble;

	struct
	{
		short yes;
		short axis;
		short angle;
		short friction;
		short headstart;
		short pad;
	}pendulum;

	struct
	{
		short yes;
		short axis;
		short inertia;
		short levelout;
		short maxrot;
		short initrot;
		short maxspeed;
		short mass;
	}seesaw;				// she saw a seesaw on the sea shore

	struct
	{
		short yes;
		short axis;
		short initrot;
		short rotspeed;
	}spin;

	struct
	{
		short yes,mass;
		short pX,pY,pZ;
		short aX,aY,aZ;
	}confine;

	struct
	{
		short yes, axis;
		short angle, pad;
	}topple;

	struct
	{
		short yes, times;
		short wait, angle;
	}spinpause;

	struct
	{
		short yes, pad;
		short wait, angle;
	}spinflip;

	struct
	{
		short yes, pad;
	}magnet;
}PLATFORM_HEADERSTR;

typedef struct PLATFORM_DEFTAG
{
	PLATFORM_HEADERSTR	head;
	PLATFORM_POINTSTR	points[PLATFORM_MAX_POINTS];	// note - the structure should only be mallocced for as many points are used
}PLATFORM_DEFSTR;


// Wind stuff

typedef struct LIGHTNING_DEFTAG *LIGHTNING_DEFHANDLE;

typedef struct LIGHTNING_DEFTAG
{
	LIGHTNING_DEFHANDLE next, prev;
	short tag, flags;
	short pTag[2];
	RGBCD colour;
	VECTOR p1;
	VECTOR p2;
	short jagginess;
	short thickness;
	int active;
	// for internal use only
	SVECTOR calcPos[2];
}LIGHTNING_DEFSTR;

// ========= enemy model loading ===========

typedef struct tagLOADEDMODEL{
	NEWMODEL *psa;
	objectSegDataType *seg;
	unsigned long crc;
}LOADEDMODEL;

LOADEDMODEL * EnsureModelLoaded(unsigned long crc, char *name,USHORT scale);

// used by the cameo player to move platforms around...

typedef struct tagDYNCOLLBOX *DYNCOLLBOXHANDLE;	// rqd coz we can't include the platform header here (!)

void loadlndFindPlatform(SHORT tag, PLATFORM_DEFSTR **plat_ret,DYNCOLLBOXHANDLE *box_ret);
ENEMYPOS *loadlndFindEnemy(SHORT tag);

extern int loadlnd_allow_platforms;
//extern int loadlnd_load_scape;

#define ADD2POINTER(a,b) ( (void *) ( (int)(a) + (b))  )


// return values
#define INWATER          0
#define ABOVEWATER       1
#define BELOWWATER       2
#define NOWHERENEARWATER 3

// at the moment, special-cased for AT1/HUB8. tbd - do properly
// "in" is a model (non-4096'd) vector,
// radius & *waterheight are also "small numbers"

// waterheight is returned if the return value isn't "NOWHERENEARWATER"

int loadlndGetWaterInfo(VECTOR *in, int radius, int *waterheight);
#define loadlndGetWaterInfo(in, radius, waterheight) waterGetWaterInfo(in,radius,waterheight)


void UpdateGamestate();


#endif








