/*
*
*   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
*
*   In addition, as a special exception, the author gives permission to
*   link the code of this program with the Half-Life Game Engine ("HL
*   Engine") and Modified Game Libraries ("MODs") developed by Valve,
*   L.L.C ("Valve").  You must obey the GNU General Public License in all
*   respects for all of the code used other than the HL Engine and MODs
*   from Valve.  If you modify this file, you may extend this exception
*   to your version of the file, but you are not obligated to do so.  If
*   you do not wish to do so, delete this exception statement from your
*   version.
*
*/

#ifndef STUDIO_H
#define STUDIO_H
#ifdef _WIN32
#pragma once
#endif

#define MAXSTUDIOTRIANGLES     20000     // TODO: tune this
#define MAXSTUDIOVERTS         2048      // TODO: tune this
#define MAXSTUDIOSEQUENCES     2048      // total animation sequences
#define MAXSTUDIOSKINS         100       // total textures
#define MAXSTUDIOSRCBONES      512       // bones allowed at source movement
#define MAXSTUDIOBONES         128       // total bones actually used
#define MAXSTUDIOMODELS        32        // sub-models per model
#define MAXSTUDIOBODYPARTS     32
#define MAXSTUDIOGROUPS        16
#define MAXSTUDIOANIMATIONS    2048      // per sequence
#define MAXSTUDIOMESHES        256
#define MAXSTUDIOEVENTS        1024
#define MAXSTUDIOPIVOTS        256
#define MAXSTUDIOCONTROLLERS   8

typedef struct 
{
	int				id;
	int				version;

	char				name[64];
	int				length;

	vec3_t				eyeposition;		// ideal eye position
	vec3_t				min;			// ideal movement hull size
	vec3_t				max;			

	vec3_t				bbmin;			// clipping bounding box
	vec3_t				bbmax;		

	int				flags;

	int				numbones;		// bones
	int				boneindex;

	int				numbonecontrollers;	// bone controllers
	int				bonecontrollerindex;

	int				numhitboxes;		// complex bounding boxes
	int				hitboxindex;			
	
	int				numseq;			// animation sequences
	int				seqindex;

	int				numseqgroups;		// demand loaded sequences
	int				seqgroupindex;

	int				numtextures;		// raw textures
	int				textureindex;
	int				texturedataindex;

	int				numskinref;		// replaceable textures
	int				numskinfamilies;
	int				skinindex;

	int				numbodyparts;		
	int				bodypartindex;

	int				numattachments;		// queryable attachable points
	int				attachmentindex;

	int				soundtable;
	int				soundindex;
	int				soundgroups;
	int				soundgroupindex;

	int				numtransitions;		// animation node to animation node transition graph
	int				transitionindex;
} studiohdr_t;

// header for demand loaded sequence group data
typedef struct 
{
	int				id;
	int				version;

	char				name[64];
	int				length;
} studioseqhdr_t;

// bones
typedef struct 
{
	char				name[32];		// bone name for symbolic links
	int		 		parent;			// parent bone
	int				flags;			// ??
	int				bonecontroller[6];	// bone controller index, -1 == none
	float				value[6];		// default DoF values
	float				scale[6];   		// scale for delta DoF values
} mstudiobone_t;


// bone controllers
typedef struct 
{
	int				bone;		// -1 == 0
	int				type;		// X, Y, Z, XR, YR, ZR, M
	float				start;
	float				end;
	int				rest;		// byte index value at rest
	int				index;		// 0-3 user set controller, 4 mouth
} mstudiobonecontroller_t;

// intersection boxes
typedef struct
{
	int				bone;
	int				group;		// intersection group
	vec3_t				bbmin;		// bounding box
	vec3_t				bbmax;		
} mstudiobbox_t;

// demand loaded sequence groups
typedef struct
{
	char				label[32];	// textual name
	char				name[64];	// file name
	int32				unused1;    	// was "cache"  - index pointer
	int				unused2;   	// was "data" -  hack for group 0
} mstudioseqgroup_t;

// sequence descriptions
typedef struct
{
	char				label[32];	// sequence label

	float				fps;		// frames per second	
	int				flags;		// looping/non-looping flags

	int				activity;
	int				actweight;

	int				numevents;
	int				eventindex;

	int				numframes;	// number of frames per sequence

	int				numpivots;	// number of foot pivots
	int				pivotindex;

	int				motiontype;	
	int				motionbone;
	vec3_t				linearmovement;
	int				automoveposindex;
	int				automoveangleindex;

	vec3_t				bbmin;		// per sequence bounding box
	vec3_t				bbmax;		

	int				numblends;
	int				animindex;	// mstudioanim_t pointer relative to start of sequence group data
							// [blend][bone][X, Y, Z, XR, YR, ZR]

	int				blendtype[2];	// X, Y, Z, XR, YR, ZR
	float				blendstart[2];	// starting value
	float				blendend[2];	// ending value
	int				blendparent;

	int				seqgroup;	// sequence group for demand loading

	int				entrynode;	// transition node at entry
	int				exitnode;	// transition node at exit
	int				nodeflags;	// transition rules
	
	int				nextseq;	// auto advancing sequences
} mstudioseqdesc_t;

// events
#include "studio_event.h"
/*
typedef struct 
{
	int 				frame;
	int				event;
	int				type;
	char				options[64];
} mstudioevent_t;
*/

// pivots
typedef struct 
{
	vec3_t				org;		// pivot point
	int				start;
	int				end;
} mstudiopivot_t;

// attachment
typedef struct 
{
	char				name[32];
	int				type;
	int				bone;
	vec3_t				org;		// attachment point
	vec3_t				vectors[3];
} mstudioattachment_t;

typedef struct
{
	unsigned short	offset[6];
} mstudioanim_t;

// animation frames
typedef union 
{
	struct {
		byte	valid;
		byte	total;
	} num;
	short		value;
} mstudioanimvalue_t;



// body part index
typedef struct
{
	char				name[64];
	int				nummodels;
	int				base;
	int				modelindex;	// index into models array
} mstudiobodyparts_t;



// skin info
typedef struct
{
	char				name[64];
	int				flags;
	int				width;
	int				height;
	int				index;
} mstudiotexture_t;


// skin families
// short	index[skinfamilies][skinref]

// studio models
typedef struct
{
	char				name[64];

	int				type;

	float				boundingradius;

	int				nummesh;
	int				meshindex;

	int				numverts;	// number of unique vertices
	int				vertinfoindex;	// vertex bone info
	int				vertindex;	// vertex vec3_t
	int				numnorms;	// number of unique surface normals
	int				norminfoindex;	// normal bone info
	int				normindex;	// normal vec3_t

	int				numgroups;	// deformation groups
	int				groupindex;
} mstudiomodel_t;


// vec3_t	boundingbox[model][bone][2];		// complex intersection info


// meshes
typedef struct 
{
	int				numtris;
	int				triindex;
	int				skinref;
	int				numnorms;	// per mesh normals
	int				normindex;	// normal vec3_t
} mstudiomesh_t;

// triangles
#if 0
typedef struct 
{
	short				vertindex;	// index into vertex array
	short				normindex;	// index into normal array
	short				s,t;		// s,t position on skin
} mstudiotrivert_t;
#endif

#define STUDIO_DYNAMIC_LIGHT		0x0100		// dynamically get lighting from floor or ceil (flying monsters)
#define STUDIO_TRACE_HITBOX		0x0200		// always use hitbox trace instead of bbox

// lighting options
#define STUDIO_NF_FLATSHADE		0x0001
#define STUDIO_NF_CHROME		0x0002
#define STUDIO_NF_FULLBRIGHT		0x0004
#define STUDIO_NF_NOMIPS		0x0008
#define STUDIO_NF_ALPHA			0x0010
#define STUDIO_NF_ADDITIVE		0x0020
#define STUDIO_NF_MASKED		0x0040

// motion flags
#define STUDIO_X		0x0001
#define STUDIO_Y		0x0002
#define STUDIO_Z		0x0004
#define STUDIO_XR		0x0008
#define STUDIO_YR		0x0010
#define STUDIO_ZR		0x0020
#define STUDIO_LX		0x0040
#define STUDIO_LY		0x0080
#define STUDIO_LZ		0x0100
#define STUDIO_AX		0x0200
#define STUDIO_AY		0x0400
#define STUDIO_AZ		0x0800
#define STUDIO_AXR		0x1000
#define STUDIO_AYR		0x2000
#define STUDIO_AZR		0x4000
#define STUDIO_TYPES		0x7FFF
#define STUDIO_RLOOP		0x8000	// controller that wraps shortest distance

// sequence flags
#define STUDIO_LOOPING		0x0001

// bone flags
#define STUDIO_HAS_NORMALS	0x0001
#define STUDIO_HAS_VERTICES 	0x0002
#define STUDIO_HAS_BBOX		0x0004
#define STUDIO_HAS_CHROME	0x0008	// if any of the textures have chrome on them

#define RAD_TO_STUDIO		(32768.0/M_PI)
#define STUDIO_TO_RAD		(M_PI/32768.0)


#define STUDIO_NUM_HULLS	128
#define STUDIO_NUM_PLANES	(STUDIO_NUM_HULLS * 6)
#define STUDIO_CACHE_SIZE	16

#endif // STUDIO_H