From 7859a00967501e8bd1b02cd0457669beb062f881 Mon Sep 17 00:00:00 2001 From: Benau <Benau@users.noreply.github.com> Date: Thu, 11 Jan 2018 13:38:08 +0800 Subject: [PATCH] Remove unused mesh code --- lib/irrlicht/include/IAnimatedMesh.h | 2 - lib/irrlicht/include/ISkinnedMesh.h | 6 +- .../Irrlicht/CAnimatedMeshSceneNode.cpp | 4 +- .../source/Irrlicht/CAnimatedMeshSceneNode.h | 2 +- lib/irrlicht/source/Irrlicht/CSkinnedMesh.cpp | 465 +++--------------- lib/irrlicht/source/Irrlicht/CSkinnedMesh.h | 18 +- src/graphics/mesh_tools.cpp | 417 +--------------- src/graphics/mesh_tools.hpp | 19 +- src/graphics/sp/sp_mesh.hpp | 5 +- src/graphics/sp/sp_mesh_node.cpp | 2 +- src/graphics/sp/sp_mesh_node.hpp | 3 +- src/tracks/model_definition_loader.cpp | 10 - src/tracks/track.cpp | 6 +- src/tracks/track_object_presentation.cpp | 28 +- 14 files changed, 86 insertions(+), 901 deletions(-) diff --git a/lib/irrlicht/include/IAnimatedMesh.h b/lib/irrlicht/include/IAnimatedMesh.h index 7091f3e22..3e08528df 100644 --- a/lib/irrlicht/include/IAnimatedMesh.h +++ b/lib/irrlicht/include/IAnimatedMesh.h @@ -8,8 +8,6 @@ #include "aabbox3d.h" #include "IMesh.h" -typedef void (*SkinningCallback)(const irr::core::matrix4& m, int joint, int offset); - namespace irr { namespace scene diff --git a/lib/irrlicht/include/ISkinnedMesh.h b/lib/irrlicht/include/ISkinnedMesh.h index 7a36aa307..59e21dcc4 100644 --- a/lib/irrlicht/include/ISkinnedMesh.h +++ b/lib/irrlicht/include/ISkinnedMesh.h @@ -69,11 +69,7 @@ namespace scene virtual void animateMesh(f32 frame, f32 blend)=0; //! Preforms a software skin on this mesh based of joint positions - virtual void skinMesh(f32 strength=1.f, SkinningCallback sc = NULL, int offset = -1) = 0; - - //! converts the vertex type of all meshbuffers to tangents. - /** E.g. used for bump mapping. */ - virtual void convertMeshToTangents(bool(*predicate)(IMeshBuffer*)) = 0; + virtual void skinMesh(f32 strength=1.f) = 0; //! Allows to enable hardware skinning. /* This feature is not implementated in Irrlicht yet */ diff --git a/lib/irrlicht/source/Irrlicht/CAnimatedMeshSceneNode.cpp b/lib/irrlicht/source/Irrlicht/CAnimatedMeshSceneNode.cpp index 157261e70..2d617ca66 100644 --- a/lib/irrlicht/source/Irrlicht/CAnimatedMeshSceneNode.cpp +++ b/lib/irrlicht/source/Irrlicht/CAnimatedMeshSceneNode.cpp @@ -176,7 +176,7 @@ void CAnimatedMeshSceneNode::OnRegisterSceneNode() } } -IMesh * CAnimatedMeshSceneNode::getMeshForCurrentFrame(SkinningCallback sc, int offset) +IMesh * CAnimatedMeshSceneNode::getMeshForCurrentFrame() { if(Mesh->getMeshType() != EAMT_SKINNED) { @@ -201,7 +201,7 @@ IMesh * CAnimatedMeshSceneNode::getMeshForCurrentFrame(SkinningCallback sc, int skinnedMesh->animateMesh(getFrameNr(), 1.0f); // Update the skinned mesh for the current joint transforms. - skinnedMesh->skinMesh(AnimationStrength, sc, offset); + skinnedMesh->skinMesh(AnimationStrength); if (JointMode == EJUOR_READ)//read from mesh { diff --git a/lib/irrlicht/source/Irrlicht/CAnimatedMeshSceneNode.h b/lib/irrlicht/source/Irrlicht/CAnimatedMeshSceneNode.h index 4d09652d6..f17086d01 100644 --- a/lib/irrlicht/source/Irrlicht/CAnimatedMeshSceneNode.h +++ b/lib/irrlicht/source/Irrlicht/CAnimatedMeshSceneNode.h @@ -173,7 +173,7 @@ namespace scene protected: //! Get a static mesh for the current frame of this animated mesh - virtual IMesh* getMeshForCurrentFrame(SkinningCallback sc = NULL, int offset = -1); + virtual IMesh* getMeshForCurrentFrame(); void buildFrameNr(u32 timeMs); virtual void checkJoints(); diff --git a/lib/irrlicht/source/Irrlicht/CSkinnedMesh.cpp b/lib/irrlicht/source/Irrlicht/CSkinnedMesh.cpp index 4493599a8..cc2bec034 100644 --- a/lib/irrlicht/source/Irrlicht/CSkinnedMesh.cpp +++ b/lib/irrlicht/source/Irrlicht/CSkinnedMesh.cpp @@ -11,55 +11,6 @@ #include "os.h" #include "irrMap.h" -inline irr::s16 float_16(irr::f32 in) -{ - irr::s32 i; - memcpy(&i, &in, 4); - irr::s32 s = (i >> 16) & 0x00008000; - irr::s32 e = ((i >> 23) & 0x000000ff) - (127 - 15); - irr::s32 m = i & 0x007fffff; - if (e <= 0) - { - if (e < -10) - { - return irr::s16(s); - } - m = (m | 0x00800000) >> (1 - e); - if (m & 0x00001000) - m += 0x00002000; - return irr::s16(s | (m >> 13)); - } - else if (e == 0xff - (127 - 15)) - { - if (m == 0) - { - return irr::s16(s | 0x7c00); - } - else - { - m >>= 13; - return irr::s16(s | 0x7c00 | m | (m == 0)); - } - } - else - { - if (m & 0x00001000) - { - m += 0x00002000; - if (m & 0x00800000) - { - m = 0; // overflow in significand, - e += 1; // adjust exponent - } - } - if (e > 30) - { - return irr::s16(s | 0x7c00); - } - return irr::s16(s | (e << 10) | (m >> 13)); - } -} - namespace irr { namespace scene @@ -72,8 +23,7 @@ CSkinnedMesh::CSkinnedMesh() LastAnimatedFrame(-1), SkinnedLastFrame(false), InterpolationMode(EIM_LINEAR), HasAnimation(false), PreparedForSkinning(false), - AnimateNormals(true), HardwareSkinning(false), m_total_joints(0), - m_current_joint(0) + AnimateNormals(true), HardwareSkinning(false) { #ifdef _DEBUG setDebugName("CSkinnedMesh"); @@ -511,7 +461,7 @@ void CSkinnedMesh::getFrameData(f32 frame, SJoint *joint, //-------------------------------------------------------------------------- //! Preforms a software skin on this mesh based of joint positions -void CSkinnedMesh::skinMesh(f32 strength, SkinningCallback sc, int offset) +void CSkinnedMesh::skinMesh(f32 strength) { if (!HasAnimation || SkinnedLastFrame) return; @@ -522,109 +472,94 @@ void CSkinnedMesh::skinMesh(f32 strength, SkinningCallback sc, int offset) //----------------- SkinnedLastFrame=true; - m_current_joint = 0; - if (HardwareSkinning) - { - for (u32 i = 0; i < RootJoints.size(); i++) - skinJoint(RootJoints[i], 0, strength, sc, offset); - } - else - { - //Software skin.... - u32 i; - //rigid animation - for (i=0; i<AllJoints.size(); ++i) + //Software skin.... + u32 i; + + //rigid animation + for (i=0; i<AllJoints.size(); ++i) + { + for (u32 j=0; j<AllJoints[i]->AttachedMeshes.size(); ++j) { - for (u32 j=0; j<AllJoints[i]->AttachedMeshes.size(); ++j) - { - SSkinMeshBuffer* Buffer=(*SkinningBuffers)[ AllJoints[i]->AttachedMeshes[j] ]; - Buffer->Transformation=AllJoints[i]->GlobalAnimatedMatrix; - } + SSkinMeshBuffer* Buffer=(*SkinningBuffers)[ AllJoints[i]->AttachedMeshes[j] ]; + Buffer->Transformation=AllJoints[i]->GlobalAnimatedMatrix; } - - //clear skinning helper array - for (i=0; i<Vertices_Moved.size(); ++i) - for (u32 j=0; j<Vertices_Moved[i].size(); ++j) - Vertices_Moved[i][j]=false; - - //skin starting with the root joints - for (i=0; i<RootJoints.size(); ++i) - skinJoint(RootJoints[i], 0, strength); - - for (i=0; i<SkinningBuffers->size(); ++i) - (*SkinningBuffers)[i]->setDirty(EBT_VERTEX); } + + //clear skinning helper array + for (i=0; i<Vertices_Moved.size(); ++i) + for (u32 j=0; j<Vertices_Moved[i].size(); ++j) + Vertices_Moved[i][j]=false; + + //skin starting with the root joints + for (i=0; i<RootJoints.size(); ++i) + skinJoint(RootJoints[i], 0, strength); + + for (i=0; i<SkinningBuffers->size(); ++i) + (*SkinningBuffers)[i]->setDirty(EBT_VERTEX); + updateBoundingBox(); } -void CSkinnedMesh::skinJoint(SJoint *joint, SJoint *parentJoint, f32 strength, - SkinningCallback sc, int offset) +void CSkinnedMesh::skinJoint(SJoint *joint, SJoint *parentJoint, f32 strength) { if (joint->Weights.size()) { //Find this joints pull on vertices... core::matrix4 jointVertexPull(core::matrix4::EM4CONST_NOTHING); jointVertexPull.setbyproduct(joint->GlobalAnimatedMatrix, joint->GlobalInversedMatrix); - if (HardwareSkinning) - { - if (sc != NULL) sc(jointVertexPull, m_current_joint, offset); - m_current_joint++; - } - else - { - core::vector3df thisVertexMove, thisNormalMove; - core::array<scene::SSkinMeshBuffer*> &buffersUsed=*SkinningBuffers; + core::vector3df thisVertexMove, thisNormalMove; - //Skin Vertices Positions and Normals... - for (u32 i=0; i<joint->Weights.size(); ++i) + core::array<scene::SSkinMeshBuffer*> &buffersUsed=*SkinningBuffers; + + //Skin Vertices Positions and Normals... + for (u32 i=0; i<joint->Weights.size(); ++i) + { + SWeight& weight = joint->Weights[i]; + + // Pull this vertex... + jointVertexPull.transformVect(thisVertexMove, weight.StaticPos); + + if (AnimateNormals) + jointVertexPull.rotateVect(thisNormalMove, weight.StaticNormal); + + // Apply animation strength + if(strength != 1.f) { - SWeight& weight = joint->Weights[i]; + thisVertexMove = core::lerp(weight.StaticPos, thisVertexMove, strength); + if(AnimateNormals) + thisNormalMove = core::lerp(weight.StaticNormal, thisNormalMove, strength); + } - // Pull this vertex... - jointVertexPull.transformVect(thisVertexMove, weight.StaticPos); + if (! (*(weight.Moved)) ) + { + *(weight.Moved) = true; + + buffersUsed[weight.buffer_id]->getVertex(weight.vertex_id)->Pos = thisVertexMove * weight.strength; if (AnimateNormals) - jointVertexPull.rotateVect(thisNormalMove, weight.StaticNormal); + buffersUsed[weight.buffer_id]->getVertex(weight.vertex_id)->Normal = thisNormalMove * weight.strength; - // Apply animation strength - if(strength != 1.f) - { - thisVertexMove = core::lerp(weight.StaticPos, thisVertexMove, strength); - if(AnimateNormals) - thisNormalMove = core::lerp(weight.StaticNormal, thisNormalMove, strength); - } - - if (! (*(weight.Moved)) ) - { - *(weight.Moved) = true; - - buffersUsed[weight.buffer_id]->getVertex(weight.vertex_id)->Pos = thisVertexMove * weight.strength; - - if (AnimateNormals) - buffersUsed[weight.buffer_id]->getVertex(weight.vertex_id)->Normal = thisNormalMove * weight.strength; - - //*(weight._Pos) = thisVertexMove * weight.strength; - } - else - { - buffersUsed[weight.buffer_id]->getVertex(weight.vertex_id)->Pos += thisVertexMove * weight.strength; - - if (AnimateNormals) - buffersUsed[weight.buffer_id]->getVertex(weight.vertex_id)->Normal += thisNormalMove * weight.strength; - - //*(weight._Pos) += thisVertexMove * weight.strength; - } - - buffersUsed[weight.buffer_id]->boundingBoxNeedsRecalculated(); + //*(weight._Pos) = thisVertexMove * weight.strength; } + else + { + buffersUsed[weight.buffer_id]->getVertex(weight.vertex_id)->Pos += thisVertexMove * weight.strength; + + if (AnimateNormals) + buffersUsed[weight.buffer_id]->getVertex(weight.vertex_id)->Normal += thisNormalMove * weight.strength; + + //*(weight._Pos) += thisVertexMove * weight.strength; + } + + buffersUsed[weight.buffer_id]->boundingBoxNeedsRecalculated(); } } //Skin all children for (u32 j=0; j<joint->Children.size(); ++j) - skinJoint(joint->Children[j], joint, strength, sc, offset); + skinJoint(joint->Children[j], joint, strength); } @@ -1462,278 +1397,6 @@ void CSkinnedMesh::addJoints(core::array<IBoneSceneNode*> &jointChildSceneNodes, SkinnedLastFrame=false; } -bool CSkinnedMesh::sortJointInfluenceFunc(const JointInfluence& a, - const JointInfluence& b) -{ - return a.weight > b.weight; -} - -void CSkinnedMesh::convertForSkinning() -{ -/* if (HardwareSkinning) return; - - setHardwareSkinning(true); - WeightInfluence wi; - for (u32 b = 0; b < LocalBuffers.size(); b++) - { - if (LocalBuffers[b]) - LocalBuffers[b]->convertForSkinning(); - - wi.push_back(core::array<core::array<JointInfluence> > ()); - for (u32 i = 0; i < LocalBuffers[b]->getVertexCount(); i++) - wi[b].push_back(core::array<JointInfluence>()); - } - - size_t idx = 0; - for (u32 i = 0; i < RootJoints.size(); i++) - computeWeightInfluence(RootJoints[i], idx, wi); - - for (u32 b = 0; b < LocalBuffers.size(); b++) - { - if (LocalBuffers[b]) - { - const u32 total = wi[b].size(); - _IRR_DEBUG_BREAK_IF(LocalBuffers[b]->getVertexCount() != total); - for (u32 i = 0; i < total; i++) - { - core::array<JointInfluence> this_influence; - core::array<JointInfluence> reported_weight = wi[b][i]; - reported_weight.sort(sortJointInfluenceFunc); - for (u32 j = 0; j < 4; j++) - { - JointInfluence influence; - influence.joint_idx = -32768; - influence.weight = j == 0 ? 1.0f : 0.0f; - this_influence.push_back(influence); - } - float total_weight = 0.0f; - const unsigned max_weight = - reported_weight.size() > 4 ? 4 : reported_weight.size(); - for (u32 j = 0; j < max_weight; j++) - { - total_weight += reported_weight[j].weight; - this_influence[j].joint_idx = reported_weight[j].joint_idx; - this_influence[j].weight = reported_weight[j].weight; - } - if (total_weight != 0.0f) - { - for (u32 j = 0; j < max_weight; j++) - { - this_influence[j].weight = - this_influence[j].weight / total_weight; - } - } - for (int j = 0; j < 4; j++) - { - LocalBuffers[b]->Vertices_SkinnedMesh[i].m_joint_idx[j] = (s16)this_influence[j].joint_idx; - LocalBuffers[b]->Vertices_SkinnedMesh[i].m_weight[j] = float_16 - (this_influence[j].weight); - } - } - } - } - SkinnedLastFrame = false; - skinMesh(); - m_total_joints = m_current_joint;*/ -} - -void CSkinnedMesh::computeWeightInfluence(SJoint *joint, size_t &index, WeightInfluence& wi) -{ - if (!joint->Weights.empty()) - { - for (u32 i = 0; i < joint->Weights.size(); i++) - { - SWeight& weight = joint->Weights[i]; - JointInfluence tmp; - tmp.joint_idx = (int)index; - tmp.weight = weight.strength; - wi[weight.buffer_id][weight.vertex_id].push_back(tmp); - } - index++; - } - - for (u32 j = 0; j < joint->Children.size(); j++) - computeWeightInfluence(joint->Children[j], index, wi); -} - -void CSkinnedMesh::convertMeshToTangents(bool(*predicate)(IMeshBuffer*)) -{ -/* bool recalculate_animation = false; - toStaticPose(); - for (u32 b = 0; b < LocalBuffers.size(); b++) - { - bool recalculate_joints = false; - core::map<u32, u32> vert_loc_map; - SSkinMeshBuffer* ssmb = LocalBuffers[b]; - if (ssmb) - { - if (!predicate(ssmb)) continue; - ssmb->Vertices_Tangents.set_used(ssmb->Vertices_Standard.size()); - for (unsigned i = 0; i < ssmb->Vertices_Tangents.size(); i++) - { - ssmb->Vertices_Tangents[i] = video::S3DVertexTangents(ssmb->Vertices_Standard[i].Pos, - ssmb->Vertices_Standard[i].Normal,ssmb->Vertices_Standard[i].Color, - ssmb->Vertices_Standard[i].TCoords); - if (!ssmb->m_tangents_map.empty()) - { - ssmb->Vertices_Tangents[i].Tangent = ssmb->m_tangents_map.find(i)->getValue().first; - ssmb->Vertices_Tangents[i].Binormal = ssmb->m_tangents_map.find(i)->getValue().second.first; - ssmb->Vertices_Tangents[i].m_bitangent_sign = ssmb->m_tangents_map.find(i)->getValue().second.second; - } - } - - - - recalculate_joints = true; - recalculate_animation = true; - core::map<video::S3DVertexTangents, u32> vert_map; - core::array<u16> tmp_indices; - for (u32 i = 0; i < ssmb->Indices.size(); i++) - { - u32 vert_location = 0; - const u32 cur_ver_loc = ssmb->Indices[i]; - const video::S3DVertex& v_old = ssmb->Vertices_Standard[cur_ver_loc]; - video::S3DVertexTangents v(v_old.Pos, v_old.Normal, v_old.Color, v_old.TCoords); - core::map<video::S3DVertexTangents, u32>::Node *n = vert_map.find(v); - if (n) - { - vert_location = n->getValue(); - } - else - { - vert_location = ssmb->Vertices_Tangents.size(); - ssmb->Vertices_Tangents.push_back(v); - vert_map.insert(v, vert_location); - } - vert_loc_map[cur_ver_loc] = vert_location; - tmp_indices.push_back(vert_location); - } - const s32 index_count = tmp_indices.size(); - u16* idx = tmp_indices.pointer(); - video::S3DVertexTangents* v = ssmb->Vertices_Tangents.pointer(); - core::vector3df local_normal; - if (!ssmb->m_tangents_map.empty()) - { - for (unsigned i = 0; i < ssmb->Vertices_Tangents.size(); i++) - { - auto a = ssmb->m_tangents_map.find(v[i].Pos); - if (a) - { - v[i].Tangent = a->getValue().first; - v[i].Binormal = a->getValue().second.first; - v[i].m_bitangent_sign = a->getValue().second.second; - } - else - { - printf("ddd\n"); - } - } - } - else - { - for (s32 i = 0; i < index_count; i += 3) - { - calculateTangents( - local_normal, - v[idx[i+0]].Tangent, - v[idx[i+0]].Binormal, - v[idx[i+0]].Pos, - v[idx[i+1]].Pos, - v[idx[i+2]].Pos, - v[idx[i+0]].TCoords, - v[idx[i+1]].TCoords, - v[idx[i+2]].TCoords); - - calculateTangents( - local_normal, - v[idx[i+1]].Tangent, - v[idx[i+1]].Binormal, - v[idx[i+1]].Pos, - v[idx[i+2]].Pos, - v[idx[i+0]].Pos, - v[idx[i+1]].TCoords, - v[idx[i+2]].TCoords, - v[idx[i+0]].TCoords); - - calculateTangents( - local_normal, - v[idx[i+2]].Tangent, - v[idx[i+2]].Binormal, - v[idx[i+2]].Pos, - v[idx[i+0]].Pos, - v[idx[i+1]].Pos, - v[idx[i+2]].TCoords, - v[idx[i+0]].TCoords, - v[idx[i+1]].TCoords); - } - - ssmb->Vertices_Standard.clear(); - ssmb->VertexType = video::EVT_TANGENTS; - } - if (recalculate_joints) - { - Vertices_Moved[b].set_used(ssmb->getVertexCount()); - for (u32 i = 0; i < AllJoints.size(); i++) - { - SJoint *joint = AllJoints[i]; - for (u32 j = 0; j <joint->Weights.size(); j++) - { - if (joint->Weights[j].buffer_id == b) - { - core::map<u32, u32>::Node *n = - vert_loc_map.find(joint->Weights[j].vertex_id); - if (n) - { - joint->Weights[j].vertex_id = n->getValue(); - } - } - } - } - } - } - if (recalculate_animation) - { - PreparedForSkinning = false; - checkForAnimation(); - }*/ -} - -void CSkinnedMesh::calculateTangents( - core::vector3df& normal, - core::vector3df& tangent, - core::vector3df& binormal, - core::vector3df& vt1, core::vector3df& vt2, core::vector3df& vt3, // vertices - core::vector2df& tc1, core::vector2df& tc2, core::vector2df& tc3) // texture coords -{ - core::vector3df v1 = vt1 - vt2; - core::vector3df v2 = vt3 - vt1; - normal = v2.crossProduct(v1); - normal.normalize(); - - // binormal - - f32 deltaX1 = tc1.X - tc2.X; - f32 deltaX2 = tc3.X - tc1.X; - binormal = (v1 * deltaX2) - (v2 * deltaX1); - binormal.normalize(); - - // tangent - - f32 deltaY1 = tc1.Y - tc2.Y; - f32 deltaY2 = tc3.Y - tc1.Y; - tangent = (v1 * deltaY2) - (v2 * deltaY1); - tangent.normalize(); - - // adjust - - core::vector3df txb = tangent.crossProduct(binormal); - if (txb.dotProduct(normal) < 0.0f) - { - tangent *= -1.0f; - binormal *= -1.0f; - } -} - } // end namespace scene } // end namespace irr diff --git a/lib/irrlicht/source/Irrlicht/CSkinnedMesh.h b/lib/irrlicht/source/Irrlicht/CSkinnedMesh.h index d1044b1b7..d2cc52b2e 100644 --- a/lib/irrlicht/source/Irrlicht/CSkinnedMesh.h +++ b/lib/irrlicht/source/Irrlicht/CSkinnedMesh.h @@ -61,7 +61,7 @@ namespace scene virtual void animateMesh(f32 frame, f32 blend); //! Preforms a software skin on this mesh based of joint positions - virtual void skinMesh(f32 strength=1.f, SkinningCallback sc = NULL, int offset = -1); + virtual void skinMesh(f32 strength=1.f); //! returns amount of mesh buffers. virtual u32 getMeshBufferCount() const; @@ -113,9 +113,6 @@ namespace scene //! Sets Interpolation Mode virtual void setInterpolationMode(E_INTERPOLATION_MODE mode); - //! Convertes the mesh to contain tangent information - virtual void convertMeshToTangents(bool(*predicate)(IMeshBuffer*)); - //! Does the mesh have no animation virtual bool isStatic(); @@ -172,14 +169,12 @@ namespace scene void convertForSkinning(); void computeWeightInfluence(SJoint *joint, size_t &index, WeightInfluence& wi); - - void buildAllGlobalAnimatedMatrices(SJoint *Joint=0, SJoint *ParentJoint=0); - u32 getTotalJoints() const { return m_total_joints; } + void buildAllGlobalAnimatedMatrices(SJoint *Joint=0, SJoint *ParentJoint=0); f32 AnimationFrames; - - core::array<SJoint*> RootJoints; + + core::array<SJoint*> RootJoints; private: void toStaticPose(); @@ -197,8 +192,7 @@ private: void calculateGlobalMatrices(SJoint *Joint,SJoint *ParentJoint); - void skinJoint(SJoint *Joint, SJoint *ParentJoint, f32 strength=1.f, - SkinningCallback sc = NULL, int offset = -1); + void skinJoint(SJoint *Joint, SJoint *ParentJoint, f32 strength=1.f); void calculateTangents(core::vector3df& normal, core::vector3df& tangent, core::vector3df& binormal, @@ -229,8 +223,6 @@ private: bool PreparedForSkinning; bool AnimateNormals; bool HardwareSkinning; - u32 m_total_joints; - u32 m_current_joint; }; } // end namespace scene diff --git a/src/graphics/mesh_tools.cpp b/src/graphics/mesh_tools.cpp index dc5808f54..7f29e36b9 100644 --- a/src/graphics/mesh_tools.cpp +++ b/src/graphics/mesh_tools.cpp @@ -16,21 +16,17 @@ // along with this program; if not, write to the Free Software // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. -#include "graphics/mesh_tools.hpp" - -#include "graphics/central_settings.hpp" -#include "graphics/irr_driver.hpp" -#include "graphics/shaders.hpp" -#include "modes/world.hpp" -#include "tracks/track.hpp" #include "utils/log.hpp" +#include "utils/vec3.hpp" #include <irrlicht.h> #include <IMesh.h> #include <IMeshBuffer.h> #include <SSkinMeshBuffer.h> -void MeshTools::minMax3D(scene::IMesh* mesh, Vec3 *min, Vec3 *max) +namespace MeshTools +{ +void minMax3D(scene::IMesh* mesh, Vec3 *min, Vec3 *max) { Vec3 extend; *min = Vec3( 999999.9f); @@ -103,407 +99,4 @@ void MeshTools::minMax3D(scene::IMesh* mesh, Vec3 *min, Vec3 *max) } // for i<getMeshBufferCount } // minMax3D -// Copied from irrlicht -void calculateTangents( - core::vector3df& normal, - core::vector3df& tangent, - core::vector3df& binormal, - const core::vector3df& vt1, const core::vector3df& vt2, const core::vector3df& vt3, // vertices - const core::vector2df& tc1, const core::vector2df& tc2, const core::vector2df& tc3) // texture coords -{ - core::vector3df v1 = vt1 - vt2; - core::vector3df v2 = vt3 - vt1; - normal = v2.crossProduct(v1); - normal.normalize(); - - // binormal - - f32 deltaX1 = tc1.X - tc2.X; - f32 deltaX2 = tc3.X - tc1.X; - binormal = (v1 * deltaX2) - (v2 * deltaX1); - binormal.normalize(); - - // tangent - - f32 deltaY1 = tc1.Y - tc2.Y; - f32 deltaY2 = tc3.Y - tc1.Y; - tangent = (v1 * deltaY2) - (v2 * deltaY1); - tangent.normalize(); - - // adjust - - core::vector3df txb = tangent.crossProduct(binormal); - if (txb.dotProduct(normal) < 0.0f) - { - tangent *= -1.0f; - binormal *= -1.0f; - } -} - -// Copied from irrlicht -static inline core::vector3df getAngleWeight(const core::vector3df& v1, - const core::vector3df& v2, - const core::vector3df& v3) -{ - // Calculate this triangle's weight for each of its three vertices - // start by calculating the lengths of its sides - const f32 a = v2.getDistanceFromSQ(v3); - const f32 asqrt = sqrtf(a); - const f32 b = v1.getDistanceFromSQ(v3); - const f32 bsqrt = sqrtf(b); - const f32 c = v1.getDistanceFromSQ(v2); - const f32 csqrt = sqrtf(c); - - // use them to find the angle at each vertex - return core::vector3df( - acosf((b + c - a) / (2.f * bsqrt * csqrt)), - acosf((-b + c + a) / (2.f * asqrt * csqrt)), - acosf((b - c + a) / (2.f * bsqrt * asqrt))); -} - -// Copied from irrlicht -template <typename T> -void recalculateTangentsT(scene::IMeshBuffer* buffer, bool recalculate_normals, bool smooth, bool angle_weighted) -{ - if (!buffer || (buffer->getVertexType() != video::EVT_TANGENTS)) - return; - - const u32 vtxCnt = buffer->getVertexCount(); - const u32 idxCnt = buffer->getIndexCount(); - - T* idx = reinterpret_cast<T*>(buffer->getIndices()); - video::S3DVertexTangents* v = - (video::S3DVertexTangents*)buffer->getVertices(); - - if (smooth) - { - u32 i; - - for (i = 0; i != vtxCnt; ++i) - { - if (recalculate_normals) - v[i].Normal.set(0.f, 0.f, 0.f); - v[i].Tangent.set(0.f, 0.f, 0.f); - v[i].Binormal.set(0.f, 0.f, 0.f); - } - - //Each vertex gets the sum of the tangents and binormals from the faces around it - for (i = 0; i<idxCnt; i += 3) - { - // if this triangle is degenerate, skip it! - if (v[idx[i + 0]].Pos == v[idx[i + 1]].Pos || - v[idx[i + 0]].Pos == v[idx[i + 2]].Pos || - v[idx[i + 1]].Pos == v[idx[i + 2]].Pos - /*|| - v[idx[i+0]].TCoords == v[idx[i+1]].TCoords || - v[idx[i+0]].TCoords == v[idx[i+2]].TCoords || - v[idx[i+1]].TCoords == v[idx[i+2]].TCoords */ - ) - continue; - - //Angle-weighted normals look better, but are slightly more CPU intensive to calculate - core::vector3df weight(1.f, 1.f, 1.f); - if (angle_weighted) - weight = getAngleWeight(v[i + 0].Pos, v[i + 1].Pos, v[i + 2].Pos); - core::vector3df localNormal; - core::vector3df localTangent; - core::vector3df localBinormal; - - calculateTangents( - localNormal, - localTangent, - localBinormal, - v[idx[i + 0]].Pos, - v[idx[i + 1]].Pos, - v[idx[i + 2]].Pos, - v[idx[i + 0]].TCoords, - v[idx[i + 1]].TCoords, - v[idx[i + 2]].TCoords); - - if (recalculate_normals) - v[idx[i + 0]].Normal += localNormal * weight.X; - v[idx[i + 0]].Tangent += localTangent * weight.X; - v[idx[i + 0]].Binormal += localBinormal * weight.X; - - calculateTangents( - localNormal, - localTangent, - localBinormal, - v[idx[i + 1]].Pos, - v[idx[i + 2]].Pos, - v[idx[i + 0]].Pos, - v[idx[i + 1]].TCoords, - v[idx[i + 2]].TCoords, - v[idx[i + 0]].TCoords); - - if (recalculate_normals) - v[idx[i + 1]].Normal += localNormal * weight.Y; - v[idx[i + 1]].Tangent += localTangent * weight.Y; - v[idx[i + 1]].Binormal += localBinormal * weight.Y; - - calculateTangents( - localNormal, - localTangent, - localBinormal, - v[idx[i + 2]].Pos, - v[idx[i + 0]].Pos, - v[idx[i + 1]].Pos, - v[idx[i + 2]].TCoords, - v[idx[i + 0]].TCoords, - v[idx[i + 1]].TCoords); - - if (recalculate_normals) - v[idx[i + 2]].Normal += localNormal * weight.Z; - v[idx[i + 2]].Tangent += localTangent * weight.Z; - v[idx[i + 2]].Binormal += localBinormal * weight.Z; - } - - // Normalize the tangents and binormals - if (recalculate_normals) - { - for (i = 0; i != vtxCnt; ++i) - v[i].Normal.normalize(); - } - for (i = 0; i != vtxCnt; ++i) - { - v[i].Tangent.normalize(); - v[i].Binormal.normalize(); - } - } - else - { - core::vector3df localNormal; - for (u32 i = 0; i<idxCnt; i += 3) - { - calculateTangents( - localNormal, - v[idx[i + 0]].Tangent, - v[idx[i + 0]].Binormal, - v[idx[i + 0]].Pos, - v[idx[i + 1]].Pos, - v[idx[i + 2]].Pos, - v[idx[i + 0]].TCoords, - v[idx[i + 1]].TCoords, - v[idx[i + 2]].TCoords); - if (recalculate_normals) - v[idx[i + 0]].Normal = localNormal; - - calculateTangents( - localNormal, - v[idx[i + 1]].Tangent, - v[idx[i + 1]].Binormal, - v[idx[i + 1]].Pos, - v[idx[i + 2]].Pos, - v[idx[i + 0]].Pos, - v[idx[i + 1]].TCoords, - v[idx[i + 2]].TCoords, - v[idx[i + 0]].TCoords); - if (recalculate_normals) - v[idx[i + 1]].Normal = localNormal; - - calculateTangents( - localNormal, - v[idx[i + 2]].Tangent, - v[idx[i + 2]].Binormal, - v[idx[i + 2]].Pos, - v[idx[i + 0]].Pos, - v[idx[i + 1]].Pos, - v[idx[i + 2]].TCoords, - v[idx[i + 0]].TCoords, - v[idx[i + 1]].TCoords); - if (recalculate_normals) - v[idx[i + 2]].Normal = localNormal; - } - } -} - -// Copied from irrlicht -void recalculateTangents(scene::IMeshBuffer* buffer, bool recalculate_normals, bool smooth, bool angle_weighted) -{ - if (buffer && (buffer->getVertexType() == video::EVT_TANGENTS)) - { - if (buffer->getIndexType() == video::EIT_16BIT) - recalculateTangentsT<u16>(buffer, recalculate_normals, smooth, angle_weighted); - else - recalculateTangentsT<u32>(buffer, recalculate_normals, smooth, angle_weighted); - } -} - -// Copied from irrlicht -void recalculateTangents(scene::IMesh* mesh, bool recalculate_normals, bool smooth, bool angle_weighted) -{ - if (!mesh) - return; - - const u32 mesh_buffer_count = mesh->getMeshBufferCount(); - for (u32 b = 0; b<mesh_buffer_count; ++b) - { - recalculateTangents(mesh->getMeshBuffer(b), recalculate_normals, smooth, angle_weighted); - } -} - -#ifndef SERVER_ONLY -bool MeshTools::isNormalMap(scene::IMeshBuffer* mb) -{ - if (!CVS->isGLSL()) - return false; - return (mb->getMaterial().MaterialType == Shaders::getShader(ES_NORMAL_MAP) && - mb->getVertexType() != video::EVT_TANGENTS); -} -#endif - -// Copied from irrlicht -scene::IMesh* MeshTools::createMeshWithTangents(scene::IMesh* mesh, - bool(*predicate)(scene::IMeshBuffer*), - bool recalculate_normals, bool smooth, - bool angle_weighted, - bool calculate_tangents) -{ - return mesh; - if (!mesh) - return 0; - - scene::ISkinnedMesh* sm = dynamic_cast<scene::ISkinnedMesh*>(mesh); - if (sm) - { - createSkinnedMeshWithTangents(sm, predicate); - return sm; - } - - // copy mesh and fill data into SMeshBufferTangents - - const u32 mesh_buffer_count = mesh->getMeshBufferCount(); - - bool needs_normal_map = false; - for (u32 b = 0; b < mesh_buffer_count; ++b) - { - scene::IMeshBuffer* original = mesh->getMeshBuffer(b); - if (predicate(original)) - { - needs_normal_map = true; - break; - } - } - - if (!needs_normal_map) - { - return mesh; - } - scene::SMesh* clone = new scene::SMesh(); - - for (u32 b = 0; b<mesh_buffer_count; ++b) - { - scene::IMeshBuffer* original = mesh->getMeshBuffer(b); - const u32 idxCnt = original->getIndexCount(); - const u16* idx = original->getIndices(); - - if (!predicate(original)) - { - clone->addMeshBuffer(original); - continue; - } - - scene::SMeshBufferTangents* buffer = new scene::SMeshBufferTangents(); - - buffer->Material = original->getMaterial(); - buffer->Vertices.reallocate(idxCnt); - buffer->Indices.reallocate(idxCnt); - - core::map<video::S3DVertexTangents, int> vertMap; - int vertLocation; - - // copy vertices - - const video::E_VERTEX_TYPE vType = original->getVertexType(); - video::S3DVertexTangents vNew; - for (u32 i = 0; i<idxCnt; ++i) - { - switch (vType) - { - case video::EVT_STANDARD: - { - const video::S3DVertex* v = - (const video::S3DVertex*)original->getVertices(); - vNew = video::S3DVertexTangents( - v[idx[i]].Pos, v[idx[i]].Normal, v[idx[i]].Color, v[idx[i]].TCoords); - } - break; - case video::EVT_2TCOORDS: - { - const video::S3DVertex2TCoords* v = - (const video::S3DVertex2TCoords*)original->getVertices(); - vNew = video::S3DVertexTangents( - v[idx[i]].Pos, v[idx[i]].Normal, v[idx[i]].Color, v[idx[i]].TCoords); - } - break; - case video::EVT_TANGENTS: - { - const video::S3DVertexTangents* v = - (const video::S3DVertexTangents*)original->getVertices(); - vNew = v[idx[i]]; - } - break; - default: - break; - } - core::map<video::S3DVertexTangents, int>::Node* n = vertMap.find(vNew); - if (n) - { - vertLocation = n->getValue(); - } - else - { - vertLocation = buffer->Vertices.size(); - buffer->Vertices.push_back(vNew); - vertMap.insert(vNew, vertLocation); - } - - // create new indices - buffer->Indices.push_back(vertLocation); - } - buffer->recalculateBoundingBox(); - - // add new buffer - clone->addMeshBuffer(buffer); - buffer->drop(); - } - - clone->recalculateBoundingBox(); - if (calculate_tangents) - recalculateTangents(clone, recalculate_normals, smooth, angle_weighted); - - scene::IMeshCache* meshCache = irr_driver->getSceneManager()->getMeshCache(); - io::SNamedPath path = meshCache->getMeshName(mesh); - if (path.getPath() == "") - { - // This mesh is not in irrlicht cache, drop it directly - assert(mesh->getReferenceCount() == 1); - mesh->drop(); - return clone; - } - else - { - // Cache the calcuated tangent mesh with path - irr_driver->removeMeshFromCache(mesh); - scene::SAnimatedMesh* amesh = new scene::SAnimatedMesh(clone); - clone->drop(); - meshCache->addMesh(path, amesh); - Track* track = Track::getCurrentTrack(); - if (track) - { - irr_driver->grabAllTextures(amesh); - track->addCachedMesh(amesh); - return amesh; - } - amesh->drop(); - return amesh; - } - -} - -void MeshTools::createSkinnedMeshWithTangents(scene::ISkinnedMesh* mesh, - bool(*predicate)(scene::IMeshBuffer*)) -{ - return; - mesh->convertMeshToTangents(predicate); -} +} // namespace MeshTools diff --git a/src/graphics/mesh_tools.hpp b/src/graphics/mesh_tools.hpp index 8529ef137..e57c15ab8 100644 --- a/src/graphics/mesh_tools.hpp +++ b/src/graphics/mesh_tools.hpp @@ -21,30 +21,17 @@ namespace irr { - namespace scene { class IMesh; class IMeshBuffer; class ISkinnedMesh; } + namespace scene { class IMesh; } } using namespace irr; - -#include "utils/vec3.hpp" +class Vec3; /** * \ingroup graphics */ namespace MeshTools { - void minMax3D(scene::IMesh* mesh, Vec3 *min, Vec3 *max); - - bool isNormalMap(scene::IMeshBuffer* mb); - - // Copied from irrlicht - scene::IMesh* createMeshWithTangents(scene::IMesh* mesh, - bool(*predicate)(scene::IMeshBuffer*), bool recalculateNormals = false, - bool smooth = false, bool angleWeighted = false, - bool calculateTangents = true); - - void createSkinnedMeshWithTangents(scene::ISkinnedMesh* mesh, - bool(*predicate)(scene::IMeshBuffer*)); - + void minMax3D(scene::IMesh* mesh, Vec3* min, Vec3* max); } // MeshTools #endif diff --git a/src/graphics/sp/sp_mesh.hpp b/src/graphics/sp/sp_mesh.hpp index c340f563d..982382d74 100644 --- a/src/graphics/sp/sp_mesh.hpp +++ b/src/graphics/sp/sp_mesh.hpp @@ -69,8 +69,7 @@ public: // ------------------------------------------------------------------------ virtual void animateMesh(f32 frame, f32 blend) {} // ------------------------------------------------------------------------ - virtual void skinMesh(f32 strength=1.f, SkinningCallback sc = NULL, - int offset = -1) {} + virtual void skinMesh(f32 strength = 1.0f) {} // ------------------------------------------------------------------------ virtual u32 getMeshBufferCount() const { return (unsigned)m_buffer.size(); } @@ -110,8 +109,6 @@ public: // ------------------------------------------------------------------------ virtual void setInterpolationMode(E_INTERPOLATION_MODE mode) {} // ------------------------------------------------------------------------ - virtual void convertMeshToTangents(bool(*predicate)(IMeshBuffer*)) {} - // ------------------------------------------------------------------------ virtual bool isStatic() { return m_all_armatures.empty(); } // ------------------------------------------------------------------------ virtual bool setHardwareSkinning(bool on) { return true; } diff --git a/src/graphics/sp/sp_mesh_node.cpp b/src/graphics/sp/sp_mesh_node.cpp index 3d6aa2500..11a03dbf6 100644 --- a/src/graphics/sp/sp_mesh_node.cpp +++ b/src/graphics/sp/sp_mesh_node.cpp @@ -149,7 +149,7 @@ void SPMeshNode::OnAnimate(u32 time_ms) } // OnAnimate // ---------------------------------------------------------------------------- -IMesh* SPMeshNode::getMeshForCurrentFrame(SkinningCallback sc, int offset) +IMesh* SPMeshNode::getMeshForCurrentFrame() { if (m_mesh->isStatic() || !m_animated) { diff --git a/src/graphics/sp/sp_mesh_node.hpp b/src/graphics/sp/sp_mesh_node.hpp index 19f9a7f55..70e4580cb 100644 --- a/src/graphics/sp/sp_mesh_node.hpp +++ b/src/graphics/sp/sp_mesh_node.hpp @@ -90,8 +90,7 @@ public: // ------------------------------------------------------------------------ virtual void animateJoints(bool calculate_absolute_positions = true) {} // ------------------------------------------------------------------------ - virtual irr::scene::IMesh* getMeshForCurrentFrame(SkinningCallback sc = NULL, - int offset = -1); + virtual irr::scene::IMesh* getMeshForCurrentFrame(); // ------------------------------------------------------------------------ virtual IBoneSceneNode* getJointNode(const c8* joint_name); // ------------------------------------------------------------------------ diff --git a/src/tracks/model_definition_loader.cpp b/src/tracks/model_definition_loader.cpp index da9f1f8f2..436af70c6 100644 --- a/src/tracks/model_definition_loader.cpp +++ b/src/tracks/model_definition_loader.cpp @@ -22,7 +22,6 @@ using namespace irr; #include "config/user_config.hpp" #include "graphics/irr_driver.hpp" #include "graphics/lod_node.hpp" -#include "graphics/mesh_tools.hpp" #include "io/xml_node.hpp" #include "modes/world.hpp" #include "tracks/track.hpp" @@ -87,14 +86,6 @@ LODNode* ModelDefinitionLoader::instanciateAsLOD(const XMLNode* node, scene::ISc continue; } - scene::ISkinnedMesh* sm = - dynamic_cast<scene::ISkinnedMesh*>(a_mesh); - if (sm) - { - MeshTools::createSkinnedMeshWithTangents(sm, - &MeshTools::isNormalMap); - } - a_mesh->grab(); //cache.push_back(a_mesh); irr_driver->grabAllTextures(a_mesh); @@ -134,7 +125,6 @@ LODNode* ModelDefinitionLoader::instanciateAsLOD(const XMLNode* node, scene::ISc continue; } - a_mesh = MeshTools::createMeshWithTangents(a_mesh, &MeshTools::isNormalMap); irr_driver->setAllMaterialFlags(a_mesh); a_mesh->grab(); diff --git a/src/tracks/track.cpp b/src/tracks/track.cpp index c1d221bd5..8eea3d338 100644 --- a/src/tracks/track.cpp +++ b/src/tracks/track.cpp @@ -1181,8 +1181,7 @@ bool Track::loadMainTrack(const XMLNode &root) merged_mesh->addMesh(mesh); merged_mesh->finalize(); #ifndef SERVER_ONLY - tangent_mesh = MeshTools::createMeshWithTangents(merged_mesh, &MeshTools::isNormalMap); - + tangent_mesh = merged_mesh; adjustForFog(tangent_mesh, NULL); #else tangent_mesh = merged_mesh; @@ -1310,9 +1309,6 @@ bool Track::loadMainTrack(const XMLNode &root) full_path.c_str()); continue; } -#ifndef SERVER_ONLY - a_mesh = MeshTools::createMeshWithTangents(a_mesh, &MeshTools::isNormalMap); -#endif // The meshes loaded here are in irrlicht's mesh cache. So we // have to keep track of them in order to properly remove them diff --git a/src/tracks/track_object_presentation.cpp b/src/tracks/track_object_presentation.cpp index 247d3cbc3..3a7bc830f 100644 --- a/src/tracks/track_object_presentation.cpp +++ b/src/tracks/track_object_presentation.cpp @@ -27,7 +27,6 @@ #include "graphics/irr_driver.hpp" #include "graphics/light.hpp" #include "graphics/material_manager.hpp" -#include "graphics/mesh_tools.hpp" #include "graphics/particle_emitter.hpp" #include "graphics/particle_kind_manager.hpp" #include "graphics/stk_particle.hpp" @@ -433,23 +432,6 @@ TrackObjectPresentationMesh::TrackObjectPresentationMesh( throw std::runtime_error("Model '" + model_name + "' cannot be found"); } -#ifndef SERVER_ONLY - if (!animated) - { - m_mesh = MeshTools::createMeshWithTangents(m_mesh, - &MeshTools::isNormalMap); - } - else - { - scene::ISkinnedMesh* sm = - dynamic_cast<scene::ISkinnedMesh*>(m_mesh); - if (sm) - { - MeshTools::createSkinnedMeshWithTangents(sm, - &MeshTools::isNormalMap); - } - } -#endif init(&xml_node, parent, enabled); } // TrackObjectPresentationMesh @@ -494,18 +476,10 @@ TrackObjectPresentationMesh::TrackObjectPresentationMesh( if (animated) { m_mesh = irr_driver->getAnimatedMesh(model_file); - scene::ISkinnedMesh* sm = - dynamic_cast<scene::ISkinnedMesh*>(m_mesh); - if (sm) - { - MeshTools::createSkinnedMeshWithTangents(sm, - &MeshTools::isNormalMap); - } } else { - m_mesh = MeshTools::createMeshWithTangents( - irr_driver->getMesh(model_file), &MeshTools::isNormalMap); + m_mesh = irr_driver->getMesh(model_file); } } #endif