/*---------------------------------------------------------------------------* Project: NintendoWare File: gfx_Skeleton.h Copyright (C)2009-2011 Nintendo/HAL Laboratory, Inc. All rights reserved. These coded instructions, statements, and computer programs contain proprietary information of Nintendo and/or its licensed developers and are protected by national and international copyright laws. 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. The content herein is highly confidential and should be handled accordingly. $Revision: 31311 $ *---------------------------------------------------------------------------*/ #ifndef NW_GFX_SKELETON_H_ #define NW_GFX_SKELETON_H_ #include #include #include namespace nw { namespace math { struct MTX34; struct Transform3; } namespace gfx { class SkeletalModel; class CalculatedTransform; //--------------------------------------------------------------------------- //! @brief SkeletalModel 内の階層構造を表すインターフェースです。 //! //! ISkeleton は廃止され Skeleton に変更されました。 //--------------------------------------------------------------------------- class Skeleton : public SceneObject { private: NW_DISALLOW_COPY_AND_ASSIGN(Skeleton); public: NW_UT_RUNTIME_TYPEINFO; //! @brief マトリクス計算時に呼ばれるコールバック用シグナルの定義です。 //! //! @sa PreCalculateMatrixSignal //! @sa PostCalculateMatrixSignal typedef ut::Signal2 CalculateMatrixSignal; //! @brief マトリクス計算時に呼ばれるコールバック用スロットの定義です。 typedef CalculateMatrixSignal::SlotType CalculateMatrixSlot; //! 動きを付けられるポーズを表すクラスです。 class TransformPose { private: NW_DISALLOW_COPY_AND_ASSIGN(TransformPose); public: //! 計算済みトランスフォームを表す定義です。 typedef CalculatedTransform Transform; //! トランスフォームの配列を表す定義です。 typedef ut::MoveArray TransformArray; //! トランスフォームの配列の範囲を表す定義です。 typedef std::pair TransformRange; //! トランスフォームの配列の範囲を表す定義です。 typedef std::pair ConstTransformRange; //! コンストラクタです。 TransformPose() {} //! コンストラクタです。 explicit TransformPose(TransformArray& transforms) : m_Transforms(transforms) {} //! ボーンの数を取得します。 int GetBonesCount() const { return m_Transforms.Size(); } //! トランスフォームを取得します。 bool GetTransform(int index, Transform** transform) { if (index < 0 || this->GetBonesCount() <= index) { return false; } *transform = &this->m_Transforms[index]; return true; } //! トランスフォームを取得します。 bool GetTransform(int index, const Transform** transform) const { if (index < 0 || this->GetBonesCount() <= index) { return false; } *transform = &this->m_Transforms[index]; return true; } //! トランスフォームを取得します。 Transform* GetTransform(int index) { return &this->m_Transforms[index]; } //! トランスフォームを取得します。 const Transform* GetTransform(int index) const { return &this->m_Transforms[index]; } //! トランスフォームの先頭を指すイテレータを取得します。 TransformArray::iterator GetBeginTransform() { return m_Transforms.Begin(); } //! トランスフォームの終端を指すイテレータを取得します。 TransformArray::iterator GetEndTransform() { return m_Transforms.End(); } //! トランスフォームの先頭と終端を指すイテレータを取得します。 TransformRange GetAllTransforms() { return TransformRange(m_Transforms.Begin(), m_Transforms.End()); } //! トランスフォームの先頭と終端を指すイテレータを取得します。 ConstTransformRange GetAllTransforms() const { return ConstTransformRange(m_Transforms.Begin(), m_Transforms.End()); } private: TransformArray m_Transforms; }; //! スケルトンのマトリクスを表すクラスです。 class MatrixPose { private: NW_DISALLOW_COPY_AND_ASSIGN(MatrixPose); public: //! マトリクスの配列を表す定義です。 typedef ut::MoveArray MatrixArray; //! マトリクスの配列の範囲を表す定義です。 typedef std::pair MatrixRange; //! マトリクスの配列の範囲を表す定義です。 typedef std::pair ConstMatrixRange; //! コンストラクタです。 MatrixPose() {} //! コンストラクタです。 explicit MatrixPose(MatrixArray& matrices) : m_Matrices(matrices) {} //! ボーンの数を取得します。 int GetBonesCount() const { return m_Matrices.Size(); } //! マトリクスを取得します。 bool GetMatrix(int index, math::MTX34** matrix) { if (index < 0 || this->GetBonesCount() <= index) { return false; } *matrix = &this->m_Matrices[index]; return true; } //! マトリクスを取得します。 bool GetMatrix(int index, const math::MTX34** matrix) const { if (index < 0 || this->GetBonesCount() <= index) { return false; } *matrix = &this->m_Matrices[index]; return true; } //! マトリクスを取得します。 math::MTX34* GetMatrix(int index) { return &this->m_Matrices[index]; } //! マトリクスを取得します。 const math::MTX34* GetMatrix(int index) const { return &this->m_Matrices[index]; } //! マトリクスの先頭を指すイテレータを取得します。 MatrixArray::iterator GetBeginMatrix() { return m_Matrices.Begin(); } //! マトリクスの終端を指すイテレータを取得します。 MatrixArray::iterator GetEndMatrix() { return m_Matrices.End(); } //! マトリクスの先頭と終端を指すイテレータを取得します。 MatrixRange GetAllMatrices() { return MatrixRange(m_Matrices.Begin(), m_Matrices.End()); } //! マトリクスの先頭と終端を指すイテレータを取得します。 ConstMatrixRange GetAllMatrices() const { return ConstMatrixRange(m_Matrices.Begin(), m_Matrices.End()); } private: MatrixArray m_Matrices; }; //! スケルトンの最初のポーズを表すクラスです。 class OriginalPose { private: NW_DISALLOW_COPY_AND_ASSIGN(OriginalPose); public: //! nw::math::Transform3 を表す定義です。 typedef math::Transform3 Transform; //! コンストラクタです。 explicit OriginalPose(ResSkeleton resource) : m_Resource(resource) {} //! ボーンの数を取得します。 int GetBonesCount() const { return m_Resource.GetBonesCount(); } //! トランスフォームを取得します。 bool GetTransform(int index, Transform** transform) { if (index < 0 || this->GetBonesCount() <= index) { return false; } ResBone bone = m_Resource.GetBones(index); if (!bone.IsValid()) { return false; } *transform = &bone.GetTransform(); return true; } //! トランスフォームを取得します。 bool GetTransform(int index, const Transform** transform) const { if (index < 0 || this->GetBonesCount() <= index) { return false; } ResBone bone = m_Resource.GetBones(index); if (!bone.IsValid()) { return false; } *transform = &bone.GetTransform(); return true; } //! トランスフォームを取得します。 Transform* GetTransform(int index) { return &m_Resource.GetBones(index).GetTransform(); } //! トランスフォームを取得します。 const Transform* GetTransform(int index) const { return &m_Resource.GetBones(index).GetTransform(); } private: ResSkeleton m_Resource; }; //---------------------------------------- //! @name リソース //@{ //! スケルトンのリソースを取得します。 ResSkeleton GetResSkeleton() { return ResStaticCast(this->GetResSceneObject()); } //! スケルトンのリソースを取得します。 const ResSkeleton GetResSkeleton() const { return ResStaticCast(this->GetResSceneObject()); } //@} //---------------------------------------- //! @name 更新 //@{ //! @brief スケルトンが更新済みかどうかを取得します。 bool IsUpdated() { return this->m_IsUpdated; } //! @brief スケルトンが更新済みかどうかを設定します。 void SetUpdated(bool isUpdated) { this->m_IsUpdated = isUpdated; } //@} //---------------------------------------- //! @name 所有者 //@{ //! 所有者となるスケルタルモデルを取得します。 const SkeletalModel* GetOwnerSkeletalModel() const { return m_OwnerSkeletalModel; } //! 所有者となるスケルタルモデルを取得します。 SkeletalModel* GetOwnerSkeletalModel() { return m_OwnerSkeletalModel; } //! 所有者となるスケルタルモデルを設定します。 void SetOwnerSkeletalModel(SkeletalModel* ownerSkeletalModel) { m_OwnerSkeletalModel = ownerSkeletalModel; } //@} //---------------------------------------- //! @name ポーズ //@{ //! @brief ローカルトランスフォームのポーズを取得します。 //! //! @return ローカルトランスフォームのポーズです。 //! virtual TransformPose& LocalTransformPose() = 0; //! @brief ローカルトランスフォームのポーズを取得します。 //! //! @return ローカルトランスフォームのポーズです。 //! virtual const TransformPose& LocalTransformPose() const = 0; //! @brief ワールドトランスフォームのポーズを取得します。 //! //! @return ワールドトランスフォームのポーズです。 //! virtual TransformPose& WorldTransformPose() = 0; //! @brief ワールドトランスフォームのポーズを取得します。 //! //! @return ワールドトランスフォームのポーズです。 //! virtual const TransformPose& WorldTransformPose() const = 0; //! @brief ワールドマトリクスのポーズを取得します。 //! //! @return ワールドマトリクスのポーズです。 //! virtual MatrixPose& WorldMatrixPose() = 0; //! @brief ワールドマトリクスのポーズを取得します。 //! //! @return ワールドマトリクスのポーズです。 //! virtual const MatrixPose& WorldMatrixPose() const = 0; //! @brief スキニングマトリクスのポーズを取得します。 //! //! @return スキニングマトリクスのポーズです。 //! virtual MatrixPose& SkiningMatrixPose() = 0; //! @brief スキニングマトリクスのポーズを取得します。 //! //! @return スキニングマトリクスのポーズです。 //! virtual const MatrixPose& SkiningMatrixPose() const = 0; //! @brief オリジナルポーズを取得します。 //! //! @return オリジナルポーズです。 //! virtual OriginalPose& LocalOriginalPose() = 0; //! @brief オリジナルポーズを取得します。 //! //! @return オリジナルポーズです。 //! virtual const OriginalPose& LocalOriginalPose() const = 0; //@} //---------------------------------------- //! @name コールバック //@{ //! @brief ボーンのマトリクス計算前のシグナルを取得します。 //! //! @sa CalculateMatrixSignal CalculateMatrixSignal& PreCalculateMatrixSignal() { return *m_PreCalculateMatrixSignal; } //! @brief ボーンのマトリクス計算前のシグナルを取得します。 //! //! @sa CalculateMatrixSignal const CalculateMatrixSignal& PreCalculateMatrixSignal() const { return *m_PreCalculateMatrixSignal; } //! @brief ボーンのマトリクス計算後のシグナルを取得します。 //! //! @sa CalculateMatrixSignal CalculateMatrixSignal& PostCalculateMatrixSignal() { return *m_PostCalculateMatrixSignal; } //! @brief ボーンのマトリクス計算後のシグナルを取得します。 //! //! @sa CalculateMatrixSignal const CalculateMatrixSignal& PostCalculateMatrixSignal() const { return *m_PostCalculateMatrixSignal; } //@} protected: //---------------------------------------- //! @name コンストラクタ/デストラクタ //@{ //! コンストラクタです。 Skeleton( os::IAllocator* allocator, ResSkeleton resource, int maxCallbacks, bool isFixedSizeMemory) : SceneObject(allocator, resource), m_PreCalculateMatrixSignal(NULL), m_PostCalculateMatrixSignal(NULL), m_IsUpdated(false) { this->SetOwnerSkeletalModel(NULL); CreateCallbacks(allocator, maxCallbacks, isFixedSizeMemory); } //! デストラクタです。 virtual ~Skeleton() { SafeDestroy(this->m_PreCalculateMatrixSignal); SafeDestroy(this->m_PostCalculateMatrixSignal); } //@} //! @brief コンストラクタの実行に必要なメモリサイズを取得します。 //! //! @details :private static void GetMemorySizeForConstruct( os::MemorySizeCalculator* pSize, int maxCallbacks) { // Skeleton::CreateCallbacks if (maxCallbacks == 0) { CalculateMatrixSignal::GetMemorySizeForInvalidateSignalInternal(pSize); CalculateMatrixSignal::GetMemorySizeForInvalidateSignalInternal(pSize); } else { CalculateMatrixSignal::GetMemorySizeForFixedSizedSignalInternal(pSize, maxCallbacks); CalculateMatrixSignal::GetMemorySizeForFixedSizedSignalInternal(pSize, maxCallbacks); } } private: //! コールバック関数を生成します。 void CreateCallbacks(os::IAllocator* allocator, int maxCallbacks, bool isFixedSizeMemory); SkeletalModel* m_OwnerSkeletalModel; CalculateMatrixSignal* m_PreCalculateMatrixSignal; CalculateMatrixSignal* m_PostCalculateMatrixSignal; bool m_IsUpdated; }; } // namespace gfx } // namespace nw #endif // NW_GFX_SKELETON_H_