#pragma once

#include "../lm/vector3.h"
#include "../lm/vector4.h"


namespace lgr
{


//! rgb形式の色を表す
template<typename T>
class color3 : public lm::vector3<T>
{
public:
	color3(void)                                         : lm::vector3<T>( T(0) , T(0) , T(0) ) {}
	color3( const T& i_r , const T& i_g , const T& i_b ) : lm::vector3<T>( i_r  , i_g  , i_b  ) {}
	color3( const color3<T>& _v )                        : lm::vector3<T>( _v.x , _v.y , _v.z ) {}
	color3( const T* _v )                                : lm::vector3<T>( _v ) {}

	// 要素型が異なる色クラスへの変換.
	template<typename U>
	operator color3<U>(void) const
	{
		return color3<U>( static_cast<U>(x) , static_cast<U>(y) , static_cast<U>(z) );
	}

	// 無彩色を設定
	void set_neutral(const T& rgb)
	{
		set(rgb, rgb, rgb);
	}

	// r , g , b へのアクセサ
	T& r(void){ return x; }
	T& g(void){ return y; }
	T& b(void){ return z; }
	const T& r(void) const { return x; }
	const T& g(void) const { return y; }
	const T& b(void) const { return z; }
};

template<typename T>
inline color3<T> operator/(const color3<T>& c, T s)
{
	return color3<T>(c.r() / s, c.g() / s, c.b() / s);
}

typedef color3<int>           color3i;
typedef color3<unsigned char> color3b;
typedef color3<float>         color3f;
typedef color3<double>        color3d;



// rgba形式の色を表す
template<typename T>
class color4 : public lm::vector4<T>
{
public:
	color4( void )                                               : lm::vector4<T>( T(0) , T(0) , T(0) , T(0) ) {}
	color4( const T& _r, const T& _g, const T& _b, const T& _a ) : lm::vector4<T>( _r   , _g   , _b   , _a   ) {}
	color4( const vector4<T>& _v )                               : lm::vector4<T>( _v.x , _v.y , _v.z , _v.w ) {}
	color4( const T* _v )                                        : lm::vector4<T>( _v ) {}

	// 要素型が異なる色クラスへの変換.
	template<typename U>
	operator color4<U>(void) const
	{
		return color4<U>( static_cast<U>(x) , static_cast<U>(y) , static_cast<U>(z) , static_cast<U>(w) );
	}

	// 無彩色を設定
	void set_neutral(const T& rgb, const T& a)
	{
		set(rgb, rgb, rgb, a);
	}

	// r , g , b へのアクセサ
	T& r(void){ return x; }
	T& g(void){ return y; }
	T& b(void){ return z; }
	T& a(void){ return w; }
	const T& r(void) const { return x; }
	const T& g(void) const { return y; }
	const T& b(void) const { return z; }
	const T& a(void) const { return w; }
};

typedef color4<int>           color4i ;
typedef color4<unsigned char> color4b ;
typedef color4<float>         color4f ;
typedef color4<double>        color4d ;


}
