#pragma once

#include <C2/gl/Projection.h>
#include <C2/gl/Manipulator.h>

#include <C2/lm/range3.h>

#include "SeqTrans.h"



namespace gl
{


enum class ViewPoint
{
	Front,
	Back,
	Left,
	Right,
	Top,
	Bottom,
	Perse,
};


class Camera
{
public:
	enum ProjectionMode
	{
		PROJ_PERS,
		PROJ_ORTHO,
	};

public:
	Camera(void)
	{
		m_Projection.m_Fovy = 45;
		m_ProjMode = PROJ_PERS;
		m_CameraReverse = false;
		m_EnableSeqence = true;
	}

	void Reset(void);

	void ResetViewFront(void);
	void ResetViewBack(void);
	void ResetViewLeft(void);
	void ResetViewRight(void);
	void ResetViewTop(void);
	void ResetViewBottom(void);
	void ResetViewPerse(void);
	void ResetViewPoint(ViewPoint vp);

	void ResetViewKeepAngle(const lm::range3f& r);

	void LookOrigin(void);

	lib_gl::Viewport& GetViewport(void)
	{
		return m_Projection.m_Viewport;
	}
	const lib_gl::Viewport& GetViewport(void) const
	{
		return m_Projection.m_Viewport;
	}

	void SetGLProjection(void);
	void SetGLModelview(void);
	void SetViewportAndMatrix(void);

	bool LoadSeq(const char* path);

	void SetFrame(int frame);

private:
	void ResetViewOrthoMain(const lm::vec3f& eye_angle, const lm::vec3f& up);
	void ResetViewMain(const lm::range3f& r, const lm::vec3f& ang, const lm::vec3f& up);
	void SetClipRangeAuto(float base_length);

	void CoordAdjustFromBlend(lm::vec3f& v) const;

public:
	lib_gl::PersProjection    m_Projection;
	lib_gl::CameraManipulator m_Manip;

	ProjectionMode m_ProjMode;

	bool m_CameraReverse;

	geom::SeqTrans m_SeqTrans;
	bool m_EnableSeqence;
	lm::vec3f m_SeqPos;
	lm::vec3f m_SeqUp;
	lm::vec3f m_SeqLook;
};


}
