///////////////////////////////////////////////////////////////////////////////
//	global include file for physics DLL
///////////////////////////////////////////////////////////////////////////////

#ifndef _G_GLOBAL_H
#define _G_GLOBAL_H

#include	"dk_shared.h"
#include	"p_user.h"

#include	"../dk_/dk_log.h"

#define	FRAMETIME		1.0F / (1000.0F / SV_FRAME_MILLISECONDS)

extern	cvar_t	*maxentities;
extern	cvar_t	*deathmatch;
extern	cvar_t	*dmflags;
extern	cvar_t	*skill;
extern	cvar_t	*fraglimit;
extern	cvar_t	*timelimit;
extern	cvar_t	*samelevel;
extern	cvar_t	*noexit;
extern	cvar_t	*g_select_empty;
extern	cvar_t	*g_unlimited_ammo;
extern	cvar_t	*dm_respawn;
extern	cvar_t	*dm_camping_time;
extern	cvar_t	*dm_camping_remind_time;
extern	cvar_t	*dm_camping_notify;
extern	cvar_t	*nomonsters;

extern	cvar_t	*sv_gravity;
extern	cvar_t	*sv_maxvelocity;

extern	cvar_t	*gun_x, *gun_y, *gun_z;
extern	cvar_t	*sv_rollspeed;
extern	cvar_t	*sv_rollangle;

extern	cvar_t	*run_pitch;
extern	cvar_t	*run_roll;
extern	cvar_t	*bob_up;
extern	cvar_t	*bob_pitch;
extern	cvar_t	*bob_roll;

extern	cvar_t	*sv_cheats;
extern	cvar_t	*maxclients;

extern	cvar_t	*hr_testvert;
extern	cvar_t	*hr_shownormals;

//	for slow motion physics
extern	cvar_t	*sv_frametime;
extern	float	p_frametime;

// memory tags to allow dynamic memory to be cleaned up
#define	TAG_GAME	765		// clear when unloading the dll
#define	TAG_LEVEL	766		// clear when loading a new level


extern	game_import_t	gi;
extern	game_export_t	globals;
extern	level_locals_t	level;
extern  game_locals_t   game;

extern	edict_t			*g_edicts;

extern serverState_t serverState;

///////////////////////////////////////////////////////////////////////////////
//	dk_dll.c
///////////////////////////////////////////////////////////////////////////////

extern	void	(*dll_ClientDisconnect)		(userEntity_t *self);
extern	void	(*dll_ClientBegin)			(userEntity_t *self, int loadgame);
extern	int		(*dll_ClientConnect)		(userEntity_t *self, void *userinfo, int loadgame);
extern	void	(*dll_ClientUserinfoChanged)(edict_t *ent, char *userinfo);
extern	void	(*dll_ClientThink)			(userEntity_t *ent, usercmd_t *ucmd, pmove_t *pm);
extern	void	(*dll_ClientBeginServerFrame)	(userEntity_t *ent);
extern	void	(*dll_think_stub)			(userEntity_t *ent);
extern	void	(*dll_Graphics3)			(void);
extern	void	(*dll_SetStats)				(userEntity_t *ent);

//	Nelno:	dll stuff
void	DLL_InitFunctions(void);		//	called once upon DLL load
void	DLL_LoadLevelFunctions (void);	//	called every each level load
void	DLL_ExitLevelFunctions (void);	//	called on each level exit
void	DLL_ExitFunctions (void);		//	called before unloading DLLs
void	DLL_LoadDLLs (char *dirName);	//	called to load DLLs
void	DLL_UnloadDLLs (void);			//	called to unload DLLs

///////////////////////////////////////////////////////////////////////////////
//	dk_ServerState.c
///////////////////////////////////////////////////////////////////////////////

void InitServerState(game_import_t *import);

///////////////////////////////////////////////////////////////////////////////
//	p_utils.c
///////////////////////////////////////////////////////////////////////////////

void		P_InitEdict (edict_t *e);
edict_t		*P_Spawn (void);
edict_t		*P_EntPtr (int entnum);
int			P_EntNum (edict_t *ent);
void		P_FreeEdict (edict_t *e);

void		P_TouchTriggers (edict_t *ent);

userEntity_t	*P_FirstEntity(void);
userEntity_t	*P_NextEntity(edict_t *ent);

///////////////////////////////////////////////////////////////////////////////
//	p_phys.c
///////////////////////////////////////////////////////////////////////////////

int		P_Push (edict_t *pusher, vec3_t move, vec3_t amove);
void	P_RunEntity (edict_t *ent);
void	P_CheckGround (edict_t *ent);
qboolean P_RunThink (edict_t *ent);

///////////////////////////////////////////////////////////////////////////////
//	p_save.c
///////////////////////////////////////////////////////////////////////////////

void	P_WriteGame (char *filename, char autosave);
void	P_ReadGame (char *filename);
void	P_WriteLevel (char *filename);
void	P_ReadLevel (char *filename);

///////////////////////////////////////////////////////////////////////////////
//	p_main.c
///////////////////////////////////////////////////////////////////////////////

void P_RunFrame (void);

///////////////////////////////////////////////////////////////////////////////
//	p_hierarchy.c
///////////////////////////////////////////////////////////////////////////////

void	hr_InitSurface (edict_t *parent, edict_t *child, char *f_surf, int f_vIndex, unsigned long flags);
void	hr_InitRelative (userEntity_t *parent, userEntity_t *child, unsigned long int flags);
void	hr_InitBmodel (userEntity_t *parent, userEntity_t *child, unsigned long int flags);
void	hr_InitSurface_Old (edict_t *parent, edict_t *child, char *f_surf, int f_vIndex, char *r_surf, int r_vIndex, unsigned long int flags);

void	hr_Move (edict_t *parent);
void	hrl_RemoveChildFromList (edict_t *parent, edict_t *child, int free_child);
void	hrl_DeleteList (edict_t *parent, int free_children);

void	hr_SetFlags (userEntity_t *parent, userEntity_t *child, unsigned long int flags);
unsigned long	hr_GetFlags (userEntity_t *parent, userEntity_t *child);

void	SV_SetStats(edict_t *ent);

#endif