////////////////////////////////////////////////////////////////
// Body list routines
//
// just a list of models that is used for the bodies of dead 
// players
////////////////////////////////////////////////////////////////

// user interface file between katana and dlls
#include "world.h"
#include "skat.h"
#include "nodelist.h"
#include "triggers.h"
#include "client.h"
#include "ai_move.h"
#include "ai_frames.h"

#define		MAX_BODIES		8

static		userEntity_t	*bodylist_head;

/////////////////////////
//  bodylist_init
//
//	creates a circular list of entities which are linked
//	by their owner field
/////////////////////////

void	bodylist_init (userEntity_t *self)
{
	userEntity_t	*body, *first_body, *last_body;
	int				i;

	for (i = 0; i < MAX_BODIES; i++)
	{
		body = gstate->SpawnEntity ();

		// keep a pointer to the first body in the list
		if (i == 0)
			first_body = body;

		body->modelName = NULL;
		body->movetype = MOVETYPE_NONE;
		body->solid = SOLID_NOT;
		
		// this will link the last body to the first in a circle
		body->owner = first_body;

		// create the playerHook for this body
		// all Hunk_Alloc'd memory will be released by Quake when a level ends
		// so we need not worry about freeing it later
		body->userHook = com->malloc_hook (sizeof (playerHook_t), MEM_HUNK); 
		memset (body->userHook, 0x00, sizeof (playerHook_t));
			
		// link last body to this body
		if (i != 0)
			last_body->owner = body;

		last_body = body;
	}

	bodylist_head = first_body;
}

/////////////////////////
//	bodylist_add
/////////////////////////

void	bodylist_add (userEntity_t *self)
{
	userEntity_t	*owner;
	playerHook_t	*hook;

	// copy the body's attributes to the body list, except for owner and hook
	owner = bodylist_head->owner;
	hook = (playerHook_t *) bodylist_head->userHook;

	// copy userhook
	*((userEntity_t *)bodylist_head->userHook) = *((userEntity_t *)self->userHook);
	// copy entity fields
	*bodylist_head = *self;

//state->SetModel (bodylist_head, bodylist_head->modelName);
	// make sure we relink the body for clipping
	gstate->SetOrigin2 (bodylist_head, bodylist_head->s.origin);

	bodylist_head->owner = owner;
	bodylist_head->userHook = (void *) hook;

	// set up this entity as a bot so that the engine doesn't do client only stuff with it
	bodylist_head->flags = (bodylist_head->flags - (bodylist_head->flags & FL_CLIENT)) | FL_BOT;
	
	// remove respawning flag so bodies don't start trying to respawn as clients
	hook->dflags = hook->dflags - (hook->dflags & DFL_RESPAWN);
	bodylist_head->prethink = ai_frame_update;
	bodylist_head->postthink = NULL;
	bodylist_head->button0 = 0;
	bodylist_head->button1 = 0;
	bodylist_head->button2 = 0;

	/// FIXME: now in friction hook!!!
	// set up vars for water velocity
/*	
	hook->rotation_scale = 0.5;
	hook->mass_scale = 0.4;
	hook->last_water = CONTENTS_EMPTY;
	hook->hit_water_pos = Vector (bodylist_head->s.origin);
	hook->change_time = 0;
*/
	// move to the next body in the list
	bodylist_head = bodylist_head->owner;

	bodylist_head->movetype = MOVETYPE_FLOAT;
}
