/*---------------------------------------------------------------------------* Project: Horizon File: math_Matrix23.h Copyright (C)2009-2010 Nintendo Co., Ltd. All rights reserved. These coded instructions, statements, and computer programs contain proprietary information of Nintendo of America Inc. and/or Nintendo Company Ltd., and are protected by Federal copyright law. They may not be disclosed to third parties or copied or duplicated in any form, in whole or in part, without the prior written consent of Nintendo. $Revision: 24035 $ *---------------------------------------------------------------------------*/ #ifndef NN_MATH_MATRIX23_H_ #define NN_MATH_MATRIX23_H_ #include #include #pragma push #pragma Otime namespace nn { namespace math { struct MTX23; struct MTX22; /* ------------------------------------------------------------------------ MTX23用の関数 ------------------------------------------------------------------------ */ NN_MATH_INLINE MTX23* MTX23Copy(MTX23* pOut, const MTX23* p); NN_MATH_INLINE MTX23* MTX23Zero(MTX23* pOut); NN_MATH_INLINE MTX23* MTX23Identity(MTX23* pOut); NN_MATH_INLINE bool MTX23IsIdentity(const MTX23* p); NN_MATH_INLINE MTX23* MTX23Add(MTX23* pOut, const MTX23* p1, const MTX23* p2); NN_MATH_INLINE MTX23* MTX23Sub(MTX23* pOut, const MTX23* p1, const MTX23* p2); NN_MATH_INLINE MTX23* MTX23Mult(MTX23* pOut, const MTX23* p, f32 f); NN_MATH_INLINE MTX23* MTX23Mult(MTX23* pOut, const MTX23* p1, const MTX23* p2); NN_MATH_INLINE MTX23* MTX23Scale(MTX23* pOut, const MTX23* pM, const VEC2* pS); NN_MATH_INLINE MTX23* MTX23Translate(MTX23* pOut, const MTX23* pM, const VEC2* pT); NN_MATH_INLINE MTX23* MTX23RotFIdx(MTX23* pOut, f32 fIdx); NN_MATH_INLINE MTX23* MTX23RotCenterFIdx(MTX23* pOut, const VEC2* pCenter, f32 fIdx); NN_MATH_INLINE MTX23* MTX23MAdd(MTX23* pOut, f32 t, const MTX23* p1, const MTX23* p2); NN_MATH_INLINE MTX23* MTX22ToMTX23(MTX23* pOut, const MTX22* pM); struct MTX23_ { struct BaseData { f32 _00, _01, _02; f32 _10, _11, _12; }; union { #if defined(NN_MATH_USE_ANONYMOUS_STRUCT) struct { f32 _00, _01, _02; f32 _10, _11, _12; }; #endif BaseData f; f32 m[2][3]; f32 a[6]; VEC3_ v[2]; }; }; /*!--------------------------------------------------------------------------* @brief 2行3列の行列クラスです。 *---------------------------------------------------------------------------*/ struct MTX23 : public MTX23_ { public: static const int ROW_COUNT = 2; //!< 行数です。 static const int COLUMN_COUNT = 3; //!< 列数です。 //! @brief 単位行列です。 static const MTX23& Identity() { static const MTX23 identity( 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f); return identity; } typedef MTX23 self_type; //!< 自分の型です。 typedef f32 value_type; //!< 要素の型です。 public: //---------------------------------------- //! @name 作成 //@{ //! @brief コンストラクタです。 MTX23() {} //! @brief コンストラクタです。 MTX23(const f32* p) { (void)MTX23Copy(this, reinterpret_cast(p)); } //! @brief コンストラクタです。 MTX23(const MTX22& rhs) { MTX22ToMTX23(this, &rhs); } //! @brief コンストラクタです。 MTX23(f32 x00, f32 x01, f32 x02, f32 x10, f32 x11, f32 x12) { f._00 = x00; f._01 = x01; f._02 = x02; f._10 = x10; f._11 = x11; f._12 = x12; } //@} //---------------------------------------- //! @name 変換 //@{ //! @brief f32 型へのキャストです。 operator f32*() { return this->a; } //! @brief f32 型へのキャストです。 operator const f32*() const { return this->a; } //! @brief VEC2 型として行を取得します。 VEC3& GetRow(int index) { NN_MATH_MINMAXLT_ASSERT(index, 0, ROW_COUNT); return *reinterpret_cast(&this->v[index]); } //! @brief VEC2 型として行を取得します。 const VEC3& GetRow(int index) const { NN_MATH_MINMAXLT_ASSERT(index, 0, ROW_COUNT); return *reinterpret_cast(&this->v[index]); } //! @brief VEC3 型として列を取得します。 VEC2 GetColumn(int index) const { NN_MATH_MINMAXLT_ASSERT(index, 0, COLUMN_COUNT); VEC2 column; column.x = this->m[0][index]; column.y = this->m[1][index]; return column; } //! @brief VEC3 型で列を設定します。 void SetColumn(int index, const VEC2& column) { NN_MATH_MINMAXLT_ASSERT(index, 0, COLUMN_COUNT); this->m[0][index] = column.x; this->m[1][index] = column.y; } //@} //---------------------------------------- //! @name 設定 //@{ //! @brief 単位行列に設定します。 self_type& SetupIdentity() { return *MTX23Identity(this); } //@} //---------------------------------------- //! @name 演算 //@{ self_type& operator += (const self_type& rhs) { return *MTX23Add(this, this, &rhs); } self_type& operator -= (const self_type& rhs) { return *MTX23Sub(this, this, &rhs); } self_type& operator *= (f32 f) { return *MTX23Mult(this, this, f); } self_type& operator /= (f32 f) { return operator*=(1.f / f); } self_type operator + () const { return *this; } self_type operator - () const { return MTX23(-f._00, -f._01, -f._02, -f._10, -f._11, -f._12); } self_type operator + (const self_type& rhs) const { MTX23 tmp; return *MTX23Add(&tmp, this, &rhs); } self_type operator - (const self_type& rhs) const { MTX23 tmp; return *MTX23Sub(&tmp, this, &rhs); } self_type operator * (f32 f) const { MTX23 tmp; return *MTX23Mult(&tmp, this, f); } self_type operator / (f32 f) const { return *this * (1.f / f); } //@} //---------------------------------------- //! @name 設定 //@{ //! @brief スケール変換行列に設定します。 //! //! @param[in] matrix 元となる行列です。 //! @param[in] scale スケール値です。 //! self_type& SetupScale(const MTX23& matrix, const VEC2& scale) { return *MTX23Scale(this, &matrix, &scale); } //! @brief 平行移動行列に設定します。 //! //! @param[in] matrix 元となる行列です。 //! @param[in] translate 平行移動値です。 //! self_type& SetupTranslate(const MTX23& matrix, const VEC2& translate) { return *MTX23Translate(this, &matrix, &translate); } //! @brief XYZ 順の回転行列に設定します。 //! //! @param[in] rotate 回転値です。単位はラジアンです。 //! self_type& SetupRotate(f32 rotate) { return *MTX23RotFIdx(this, NN_MATH_RAD_TO_FIDX(rotate)); } //! @brief 指定した軸周りの回転行列に設定します。 //! //! @param[in] center 基準となる座標です。 //! @param[in] rotate 回転させる角度です。単位はラジアンです。 //! self_type& SetupRotate(const VEC2& center, f32 rotate) { return *MTX23RotCenterFIdx(this, ¢er, NN_MATH_RAD_TO_FIDX(rotate)); } //@} //---------------------------------------- //! @name 比較 //@{ //! @brief 同値であれば true を返します。 bool operator == (const self_type& rhs) const { return ::std::memcmp(this, &rhs, sizeof(MTX23)) == 0; } //! @brief 同値でなければ true を返します。 bool operator != (const self_type& rhs) const { return ::std::memcmp(this, &rhs, sizeof(MTX23)) != 0; } //! @brief 単位行列であれば true を返します。 bool IsIdentity() const { return MTX23IsIdentity(this); } //@} //! @brief 状態を出力します。 void Report(bool bNewline = true, const char* name = NULL) const; }; typedef struct MTX23 Matrix23; } // namespace math } // namespace nn namespace nn { namespace math { //-- const 引数を参照にしたオーバーロード inline MTX23* MTX23Copy(MTX23* pOut, const MTX23& m) { return MTX23Copy( pOut, &m ); } inline bool MTX23IsIdentity(const MTX23& m) { return MTX23IsIdentity( &m ); } inline MTX23* MTX23Add(MTX23* pOut, const MTX23& m1, const MTX23& m2) { return MTX23Add( pOut, &m1, &m2 ); } inline MTX23* MTX23Sub(MTX23* pOut, const MTX23& m1, const MTX23& m2) { return MTX23Sub( pOut, &m1, &m2 ); } inline MTX23* MTX23Mult(MTX23* pOut, const MTX23& m, f32 f) { return MTX23Mult( pOut, &m, f ); } inline MTX23* MTX23Mult(MTX23* pOut, const MTX23& m1, const MTX23& m2) { return MTX23Mult( pOut, &m1, &m2); } inline MTX23* MTX23Scale(MTX23* pOut, const MTX23& m, const VEC2& vS) { return MTX23Scale( pOut, &m, &vS); } inline MTX23* MTX23Translate(MTX23* pOut, const MTX23& m, const VEC2& vT) { return MTX23Translate( pOut, &m, &vT); } inline MTX23* MTX23RotCenterFIdx(MTX23* pOut, const VEC2& vCenter, f32 fIdx) { return MTX23RotCenterFIdx( pOut, &vCenter, fIdx ); } inline MTX23* MTX23MAdd(MTX23* pOut, f32 t, const MTX23& m1, const MTX23& m2) { return MTX23MAdd( pOut, t, &m1, &m2 ); } inline MTX23* MTX22ToMTX23(MTX23* pOut, const MTX22& m) { return MTX22ToMTX23( pOut, &m ); } } // namespace math } // namespace nn #if defined(NN_MATH_AS_INLINE) #include #endif #pragma pop #endif