/*****************************************************************************/

#ifndef _MATH_H_
#define _MATH_H_


#include "Types.h"


/*****************************************************************************/

#define PI 3.14159265358979323846

#define ONE 4096
#define MAX_ANGLES 4096
#define ANGLE_MASK (MAX_ANGLES-1)


/*****************************************************************************/

extern float
	SinTable[MAX_ANGLES];


/*****************************************************************************/

extern
	void Math_Setup();


/*****************************************************************************/

#define Point3 Vector3


class Vector3
{
	public:

		float
			x,
			y,
			z;


		Vector3 operator +( Vector3 &v );
		Vector3 operator -( Vector3 &v );
		float operator *( Vector3 &v );
		Vector3& operator -=( Vector3 &v );
		int operator ==( Vector3 &v );

		void Normalize();
		void Negate();
};


float DotProduct( Vector3 *a, Vector3 *b );
float DotProduct( Vector3 &a, Vector3 &b );

Vector3 CrossProduct( Vector3 *a, Vector3 *b );
Vector3 CrossProduct( Vector3 &a, Vector3 &b );


/*****************************************************************************/

class Matrix3
{
	public:

		float
			m[3][3],
			t[3];

		void SetIdentity();

		void SetScale( float scale );
		void SetScale( float *scale );

		void SetTrans( Vector3 *trans );
		void SetTrans( float *trans );
		void SetTrans( float x, float y, float z );

		void GetTrans( Vector3 *trans );
		void GetTrans( float *trans );

		void ScaleBy( float scale );

		void RotateByX( s32 angle );
		void RotateByY( s32 angle );
		void RotateByZ( s32 angle );

		void SetRotateX( s32 angle );
		void SetRotateY( s32 angle );
		void SetRotateZ( s32 angle );

		void MulByMatrix( Matrix3 *matrix );

		void Multiply( Vector3 *vector );

		void Transform( Vector3 *vector );
		void Transform( Matrix3 *matrix );

		void CopyToMem( float *mem );
		void CopyFromMem( float *mem );
};


/*****************************************************************************/


typedef struct
{
	Vector3
		Normal;
	float
		Dist;
} Plane;


#endif
