// Copyright (C) 2002-2009 Nikolaus Gebhardt // This file is part of the "Irrlicht Engine". // For conditions of distribution and use, see copyright notice in irrlicht.h #ifndef __I_SKINNED_MESH_H_INCLUDED__ #define __I_SKINNED_MESH_H_INCLUDED__ #include "irrArray.h" #include "IBoneSceneNode.h" #include "IAnimatedMesh.h" #include "SSkinMeshBuffer.h" namespace irr { namespace scene { enum E_INTERPOLATION_MODE { // constant interpolation EIM_CONSTANT = 0, // linear interpolation EIM_LINEAR, //! count of all available interpolation modes EIM_COUNT }; //! Interface for using some special functions of Skinned meshes class ISkinnedMesh : public IAnimatedMesh { public: //! Gets joint count. //! \return Returns amount of joints in the skeletal animated mesh. virtual u32 getJointCount() const = 0; //! Gets the name of a joint. //! \param number: Zero based index of joint. The last joint //! has the number getJointCount()-1; //! \return Returns name of joint and null if an error happened. virtual const c8* getJointName(u32 number) const = 0; //! Gets a joint number from its name //! \param name: Name of the joint. //! \return Returns the number of the joint or -1 if not found. virtual s32 getJointNumber(const c8* name) const = 0; //! uses animation from another mesh //! the animation is linked (not copied) based on joint names (so make sure they are unique) //! \return Returns true if all joints in this mesh were //! matched up (empty names will not be matched, and it's case //! sensitive). Unmatched joints will not be animated. virtual bool useAnimationFrom(const ISkinnedMesh *mesh) = 0; //!Update Normals when Animating //!False= Don't animate, faster //!True= Update normals virtual void updateNormalsWhenAnimating(bool on) = 0; //!Sets Interpolation Mode virtual void setInterpolationMode(E_INTERPOLATION_MODE mode) = 0; //! Animates this mesh's joints based on frame input virtual void animateMesh(f32 frame, f32 blend)=0; //! Preforms a software skin on this mesh based of joint positions virtual void skinMesh() = 0; //! converts the vertex type of all meshbuffers to tangents. eg for bumpmapping virtual void convertMeshToTangents() = 0; //! (This feature is not implementated in irrlicht yet) virtual bool setHardwareSkinning(bool on) = 0; //! A vertex weight struct SWeight { //! Index of the mesh buffer u16 buffer_id; //I doubt 32bits is needed //! Index of the vertex u32 vertex_id; //Store global ID here //! Weight Strength/Percentage (0-1) f32 strength; private: //! Internal members used by CSkinnedMesh friend class CSkinnedMesh; bool *Moved; core::vector3df StaticPos; core::vector3df StaticNormal; }; //! Animation keyframe which describes a new position struct SPositionKey { f32 frame; core::vector3df position; }; //! Animation keyframe which describes a new scale struct SScaleKey { f32 frame; core::vector3df scale; }; //! Animation keyframe which describes a new rotation struct SRotationKey { f32 frame; core::quaternion rotation; }; //! Joints struct SJoint { SJoint() : UseAnimationFrom(0), LocalAnimatedMatrix_Animated(false), GlobalSkinningSpace(false), positionHint(-1),scaleHint(-1),rotationHint(-1) { } //! The name of this joint core::stringc Name; //! Local matrix of this joint core::matrix4 LocalMatrix; //! List of child joints core::array Children; //! List of attached meshes core::array AttachedMeshes; //! Animation keys causing translation change core::array PositionKeys; //! Animation keys causing scale change core::array ScaleKeys; //! Animation keys causing rotation change core::array RotationKeys; //! Skin weights core::array Weights; //! Unnecessary for loaders, will be overwritten on finalize core::matrix4 GlobalMatrix; core::matrix4 GlobalAnimatedMatrix; core::matrix4 LocalAnimatedMatrix; core::vector3df Animatedposition; core::vector3df Animatedscale; core::quaternion Animatedrotation; core::matrix4 GlobalInversedMatrix; //the x format pre-calculates this private: //! Internal members used by CSkinnedMesh friend class CSkinnedMesh; SJoint *UseAnimationFrom; bool LocalAnimatedMatrix_Animated; bool GlobalSkinningSpace; s32 positionHint; s32 scaleHint; s32 rotationHint; }; //Interface for the mesh loaders (finalize should lock these functions, and they should have some prefix like loader_ //these functions will use the needed arrays, set values, etc to help the loaders //! exposed for loaders: to add mesh buffers virtual core::array &getMeshBuffers() = 0; //! exposed for loaders: joints list virtual core::array &getAllJoints() = 0; //! exposed for loaders: joints list virtual const core::array &getAllJoints() const = 0; //! loaders should call this after populating the mesh virtual void finalize() = 0; virtual SSkinMeshBuffer *createBuffer() = 0; virtual SJoint *createJoint(SJoint *parent=0) = 0; virtual SWeight *createWeight(SJoint *joint) = 0; virtual SPositionKey *createPositionKey(SJoint *joint) = 0; virtual SScaleKey *createScaleKey(SJoint *joint) = 0; virtual SRotationKey *createRotationKey(SJoint *joint) = 0; virtual bool isStatic()=0; }; } // end namespace scene } // end namespace irr #endif