#include"model.h" #include"mesh.h" #include"material.h" #include"vector.h" #include"util.h" #include #include #include #include #include #include using namespace std; using namespace Assimp; namespace vb01{ void Model::processNode(aiNode *node, const aiScene *scene, Node *currentNode){ for(int i=0;imNumMeshes;i++){ aiMesh *mesh=scene->mMeshes[node->mMeshes[i]]; processMesh(mesh,scene,currentNode); } for(int i=0;imNumChildren;i++){ Node *childNode=new Node(); currentNode->attachChild(childNode); processNode(node->mChildren[i],scene,childNode); } } void Model::processMesh(aiMesh *mesh, const aiScene *scene, Node *currentNode){ const int numTris=mesh->mNumFaces; Mesh::Vertex *vertices=new Mesh::Vertex[3*numTris]; u32 *indices=new u32[3*numTris]; for(int i=0;i<3*numTris;i++){ Mesh::Vertex v; v.pos.x=mesh->mVertices[i].x; v.pos.y=mesh->mVertices[i].y; v.pos.z=mesh->mVertices[i].z; v.norm.x=mesh->mNormals[i].x; v.norm.y=mesh->mNormals[i].y; v.norm.z=mesh->mNormals[i].z; v.tan.x=mesh->mTangents[i].x; v.tan.y=mesh->mTangents[i].y; v.tan.z=mesh->mTangents[i].z; v.biTan.x=mesh->mBitangents[i].x; v.biTan.y=mesh->mBitangents[i].y; v.biTan.z=mesh->mBitangents[i].z; if(mesh->mTextureCoords[0]){ v.texCoords.x=mesh->mTextureCoords[0][i].x; v.texCoords.y=mesh->mTextureCoords[0][i].y; } else v.texCoords=Vector2::VEC_ZERO; vertices[i]=v; } for(int i=0;imFaces[i].mNumIndices; for(int j=0;jmFaces[i].mIndices[j]; } } //if(mesh->mMaterialIndex>=0){ // aiMaterial *material=scene->mMaterial[mesh->mMaterialIndex]; //} currentNode->attachMesh(new Mesh(vertices,indices,numTris)); } Model::Model(string path,bool b) : Node(){ if(b){ Importer importer; const aiScene *scene=importer.ReadFile(path,aiProcess_Triangulate | aiProcess_FlipUVs | aiProcess_GenNormals | aiProcess_CalcTangentSpace); if(!scene||scene->mFlags&AI_SCENE_FLAGS_INCOMPLETE||!scene->mRootNode){ cout<<"Failed to load model:"<mRootNode,scene,this); } else{ int numTris,numVerts,numGroups,v=0,u=0,vg=0,b=0; Mesh::Vertex *vertices; Mesh::VertexGroup *groups=new Mesh::VertexGroup[5]; unsigned int *indices; Vector3 *pos,*norm; ifstream in(path); string l; bool verts=false,uv=false,vertexGroups=false,bones=false; while(getline(in,l)){ if(l.substr(0,8)=="numFaces"){ numTris=atoi(l.substr(9,string::npos).c_str()); vertices=new Mesh::Vertex[numTris*3]; indices=new unsigned int[numTris*3]; } else if(l.substr(0,11)=="numVertices"){ numVerts=atoi(l.substr(12,string::npos).c_str()); pos=new Vector3[numVerts]; norm=new Vector3[numVerts]; } else if(l.substr(0,9)=="numGroups"){ numGroups=atoi(l.substr(10,string::npos).c_str()); groups=new Mesh::VertexGroup[numGroups]; } if(l=="vertices:"){ verts=true; continue; } else if(l=="uv:"){ verts=false; uv=true; continue; } else if(l=="groups:"){ uv=false; vertexGroups=true; continue; } else if(l=="bones:"){ vertexGroups=false; bones=true; continue; } if(verts||uv||vertexGroups||bones){ int numCoords=1; if(verts)numCoords=6; else if(uv)numCoords=3; else if(vg)numCoords=3; else if(groups)numCoords=1; int nextSpace=0; int *spaceIds=new int[numCoords-1]; for(int i=0;iattachMesh(new Mesh(vertices,indices,numTris)); } } Model::~Model(){ delete children[0]->getMesh(0)->getMaterial(); vector descendants; getDescendants(this,descendants); for(Node *node : descendants) for(Mesh *mesh : node->getMeshes()) mesh->setMaterial(nullptr); while(!children.empty()){ Node *c=children[children.size()-1]; dettachChild(c); delete c; } } void Model::update(){ Node::update(); } void Model::setMaterial(Material *mat){ vector descendants; getDescendants(this,descendants); for(Node *node : descendants) for(Mesh *mesh : node->getMeshes()) mesh->setMaterial(mat); } void Model::setCastShadow(bool castShadow){ vector descendants; getDescendants(this,descendants); for(Node *node : descendants) for(Mesh *mesh : node->getMeshes()) mesh->setCastShadow(castShadow); this->castShadow=castShadow; } void Model::setReflect(bool reflect){ vector descendants; getDescendants(this,descendants); for(Node *node : descendants) for(Mesh *mesh : node->getMeshes()) mesh->setReflect(reflect); this->reflect=reflect; } void Model::setWireframe(bool wirefame){ vector descendants; getDescendants(this,descendants); for(Node *node : descendants) for(Mesh *mesh : node->getMeshes()) mesh->setWireframe(wirefame); this->wireframe=wireframe; } }