///////////////////////////////////////////////////////////////////////////////
//  CCamera.cpp

#include "CCamera.h"

namespace math3d {

CCamera::CCamera(void)
{
}

CCamera::~CCamera()
{
}

void CCamera::SetPos(float fX, float fY, float fZ)
{
	m_Pos.Set(fX, fY, fZ);
}

void CCamera::SetPos(const S3D& Pos)
{
	m_Pos = Pos;
}

// 回転
void CCamera::ResetRotate()
{
	m_Quaternion = SQuaternion();
}

void CCamera::AddAngle(float fAngle)
{
	m_Quaternion = SMatrix::CreateRotH(fAngle).GetQuaternion() * m_Quaternion;
}

void CCamera::AddAngleP(float fAngleP)
{
	m_Quaternion = m_Quaternion * SMatrix::CreateRotP(fAngleP).GetQuaternion();
}

void CCamera::SetRotate(const SQuaternion& Q)
{
	m_Quaternion = Q;
}

const SQuaternion& CCamera::GetQuaternion() const
{
	return m_Quaternion;
}

void CCamera::AddForward(float fMove)
{
	const S3D Pos = S3D(0.0f, 0.0f, fMove) * GetRotInvMatrix();

	m_Pos += Pos;
}

void CCamera::AddY(float fY)
{
	m_Pos.fY += fY;
}

// 取得
float CCamera::GetX() const
{
	return m_Pos.fX;
}

float CCamera::GetY() const
{
	return m_Pos.fY;
}

float CCamera::GetZ() const
{
	return m_Pos.fZ;
}

const S3D& CCamera::GetPos() const
{
	return m_Pos;
}

// ワールド座標系からビュー座標系に変換する行列を求める
SMatrix CCamera::GetMatrix(void) const
{
	return
		SMatrix::CreateMove(-m_Pos) *
		GetRotMatrix();
}

// ビュー座標系からワールド座標系に変換する行列を求める
SMatrix CCamera::GetInvMatrix(void) const
{
	return
		GetRotInvMatrix() *
		SMatrix::CreateMove(m_Pos);
}

SMatrix CCamera::GetRotMatrix(void) const
{
	return m_Quaternion.GetInverse().GetMatrix();
}

SMatrix CCamera::GetRotInvMatrix(void) const
{
	return m_Quaternion.GetMatrix();
}

S3D CCamera::GetViewVec(void) const
{
	return S3D(0.0f, 0.0f, 1.0f) * GetRotInvMatrix();
}

S3D CCamera::GetViewUpVec(void) const
{
	return S3D(0.0f, 1.0f, 0.0f) * GetRotInvMatrix();
}

S3D CCamera::GetViewRightVec(void) const
{
	return S3D(1.0f, 0.0f, 0.0f) * GetRotInvMatrix();
}

}

