#ifndef _RDCAMERA_H
#define _RDCAMERA_H

#include "types.h"
#include "Engine/rdCanvas.h"
#include "globals.h"

#ifdef __cplusplus
extern "C" {
#endif

#define rdCamera_New_ADDR (0x00443260)
#define rdCamera_NewEntry_ADDR (0x00443360)
#define rdCamera_Free_ADDR (0x00443440)
#define rdCamera_FreeEntry_ADDR (0x00443470)
#define rdCamera_SetCanvas_ADDR (0x00443490)
#define rdCamera_SetCurrent_ADDR (0x004434B0)
#define rdCamera_SetFOV_ADDR (0x004434D0)
#define rdCamera_SetProjectType_ADDR (0x00443520)
#define rdCamera_SetOrthoScale_ADDR (0x004435A0)
#define rdCamera_SetAspectRatio_ADDR (0x004435C0)
#define rdCamera_BuildFOV_ADDR (0x00443670)
#define rdCamera_SetFrustrum_ADDR (0x00443830)
#define rdCamera_Update_ADDR (0x00443900)
#define rdCamera_OrthoProject_ADDR (0x00443940)
#define rdCamera_OrthoProjectLst_ADDR (0x00443980)
#define rdCamera_OrthoProjectSquare_ADDR (0x00443A00)
#define rdCamera_OrthoProjectSquareLst_ADDR (0x00443A40)
#define rdCamera_PerspProject_ADDR (0x00443AB0)
#define rdCamera_PerspProjectLst_ADDR (0x00443B00)
#define rdCamera_PerspProjectSquare_ADDR (0x00443B80)
#define rdCamera_PerspProjectSquareLst_ADDR (0x00443BC0)
#define rdCamera_SetAmbientLight_ADDR (0x00443C30)
#define rdCamera_SetAttenuation_ADDR (0x00443C40)
#define rdCamera_AddLight_ADDR (0x00443C80)
#define rdCamera_ClearLights_ADDR (0x00443CF0)
#define rdCamera_AdvanceFrame_ADDR (0x00443D10)

rdCamera* rdCamera_New(flex_t fov, BOOL bFarClip, flex_t nearPlane, flex_t farPlane, flex_t aspectRatio);
int rdCamera_NewEntry(rdCamera *pCamera, flex_t fov, BOOL bClipFar, flex_t nearPlane, flex_t farPlane, flex_t aspectRatio);
void rdCamera_Free(rdCamera *pCamera);
void rdCamera_FreeEntry(rdCamera *pCamera);
MATH_FUNC int rdCamera_SetCanvas(rdCamera *pCamera, rdCanvas *pCanvas);
int rdCamera_SetCurrent(rdCamera *pCamera);
MATH_FUNC int rdCamera_SetFOV(rdCamera *pCamera, flex_t fov);
int rdCamera_SetProjectType(rdCamera *pCamera, int type);
MATH_FUNC int rdCamera_SetOrthoScale(rdCamera *pCamera, flex_t scale);
MATH_FUNC int rdCamera_SetAspectRatio(rdCamera *pCamera, flex_t ratio);
MATH_FUNC int rdCamera_BuildFOV(rdCamera *pCamera);
MATH_FUNC int rdCamera_SetFrustrum(rdCamera *pCamera, rdClipFrustum *pFrustrum, signed int height, signed int width, signed int height2, signed int width2);
MATH_FUNC void rdCamera_Update(rdMatrix34 *orient);
MATH_FUNC void rdCamera_OrthoProject(rdVector3* pDestVertex, const rdVector3* pSrcVertex);
MATH_FUNC void rdCamera_OrthoProjectLst(rdVector3 *pDestVerts, const rdVector3 *pSrcVerts, unsigned int numVerts);
MATH_FUNC void rdCamera_OrthoProjectSquare(rdVector3 *pDestVertex, const rdVector3 *pSrcVertex);
MATH_FUNC void rdCamera_OrthoProjectSquareLst(rdVector3 *pDestVerts, const rdVector3 *pSrcVerts, unsigned int numVerts);
MATH_FUNC FAST_FUNC void rdCamera_PerspProject(rdVector3 *pDestVertex, const rdVector3 *pSrcVertex);
MATH_FUNC FAST_FUNC void rdCamera_PerspProjectLst(rdVector3 *vertices_out, const rdVector3 *vertices_in, unsigned int num_vertices);
MATH_FUNC void rdCamera_PerspProjectSquare(rdVector3 *pDestVertex, const rdVector3 *pSrcVertex);
MATH_FUNC void rdCamera_PerspProjectSquareLst(rdVector3 *vertices_out, const rdVector3 *vertices_in, unsigned int num_vertices);
void rdCamera_SetAmbientLight(rdCamera *pCamera, flex_t amt);
MATH_FUNC void rdCamera_SetAttenuation(rdCamera *pCamera, flex_t min, flex_t max);
MATH_FUNC int rdCamera_AddLight(rdCamera *pCamera, rdLight *pLight, rdVector3 *pPos);
int rdCamera_ClearLights(rdCamera *pCamera);
void rdCamera_AdvanceFrame();
flex_t rdCamera_GetMipmapScalar(); // MOTS added
void rdCamera_SetMipmapScalar(flex_t val); // MOTS added

#ifdef TARGET_TWL
MATH_FUNC FAST_FUNC void rdCamera_PerspProjectClip(rdVector3 *vertices_out, const rdVector3 *vertices_in); // Added
MATH_FUNC FAST_FUNC void rdCamera_PerspProjectLstClip(rdVector3 *vertices_out, const rdVector3 *vertices_in, unsigned int num_vertices); // Added
#endif

#ifdef __cplusplus
}
#endif

#endif // _RDCAMERA_H
