void repo::core::RepoNodeCamera::toAssimp(aiCamera *camera) const { //-------------------------------------------------------------------------- // Name camera->mName = aiString(name); //-------------------------------------------------------------------------- // Aspect ratio camera->mAspect = aspectRatio; //-------------------------------------------------------------------------- // Far clipping plane camera->mClipPlaneFar = farClippingPlane; //-------------------------------------------------------------------------- // Near clipping plane camera->mClipPlaneNear = nearClippingPlane; //-------------------------------------------------------------------------- // Field of view camera->mHorizontalFOV = fieldOfView; //-------------------------------------------------------------------------- // Look at vector camera->mLookAt = lookAt; //-------------------------------------------------------------------------- // Position vector camera->mPosition = position; //-------------------------------------------------------------------------- // Up vector camera->mUp = up; }
void ImporterTest :: testMemoryRead (void) { const aiScene* sc = pImp->ReadFileFromMemory(InputData_abRawBlock,InputData_BLOCK_SIZE, aiProcessPreset_TargetRealtime_Quality,"3ds"); CPPUNIT_ASSERT(sc != NULL); CPPUNIT_ASSERT(sc->mRootNode->mName == aiString("<3DSRoot>")); CPPUNIT_ASSERT(sc->mNumMeshes == 1 && sc->mMeshes[0]->mNumVertices ==24 && sc->mMeshes[0]->mNumFaces ==12); }
std::vector<aiMesh*> ModelLoader::find(const std::string &name){ info("MESH", name); std::vector<aiMesh*> out; for(int i=0; i<scene->mNumMeshes; i++){ if(scene->mMeshes[i]->mName == aiString(name)){ out.push_back(scene->mMeshes[i]); } } return out; }
aiBone* makeBone(const char* name, aiVertexWeight weights[], unsigned int numWeights) { aiVertexWeight* heapedWeights = new aiVertexWeight[numWeights]; memcpy(heapedWeights, weights, numWeights * sizeof(aiVertexWeight)); aiBone* bone = new aiBone(); bone->mName = aiString(name); bone->mNumWeights = numWeights; bone->mOffsetMatrix = aiMatrix4x4(); bone->mWeights = heapedWeights; return bone; }
void _loadPNGTexture( std::vector<Texture2D> & xTextures , const char * xPath , eTexture2DType const xLocalEquivalent ) { SISULOG( "IN _loadPNGTexture" ); std::cerr << "xPath = " << xPath << std::endl; DevILImage * image = new DevILImage( xPath ); Texture2D texture( xLocalEquivalent ); texture.initialize( image->getWidth( ) , image->getHeight( ) , image->toGLTextureBuffer( ) , aiString( xPath ) ); xTextures.push_back( texture ); mTextures.push_back( texture ); mTextureData.push_back( image ); SISULOG( "OUT _loadPNGTexture" ); }
AssetLoader::meshptr_type AssimpAssetLoader::loadMeshByName(const std::string name) { AssertAssetOpen(); aiNode *n; if(name == "") n = mScene->mRootNode; else n = mScene->mRootNode->FindNode(aiString(name)); meshptr_type mesh = NULL; if(n != NULL) { std::cout << "found " << name << std::endl; mesh = buildMesh(*mScene->mRootNode); } else { std::cout << "did not find " << name << std::endl; } return mesh; }
void recursive_load_meshes(const struct aiScene *sc, const struct aiNode* nd) { unsigned int n = 0; struct aiMatrix4x4 m = nd->mTransformation; // update transform aiTransposeMatrix4(&m); glPushMatrix(); glMultMatrixf((float*)&m); // draw all meshes assigned to this node for (; n < nd->mNumMeshes; ++n) { meshObject newMesh; newMesh.mesh = sc->mMeshes[nd->mMeshes[n]]; // Set up the index buffer. Each face should have 3 vertices since we // specified aiProcess_Triangulate newMesh.indexBuffer.reserve(newMesh.mesh->mNumFaces * 3); for (unsigned i = 0; i < newMesh.mesh->mNumFaces; i++) { for (unsigned j = 0; j < newMesh.mesh->mFaces[i].mNumIndices; j++) { newMesh.indexBuffer.push_back(newMesh.mesh->mFaces[i].mIndices[j]); } } aiMaterial * mat = sc->mMaterials[newMesh.mesh->mMaterialIndex]; aiString prefix = aiString("models/"); aiString root; mat->GetTexture(aiTextureType_DIFFUSE, 0, &root); if (root != aiString("")) { //printf("%s\n",root.data); prefix.Append(root.data); aiString diff = aiString(prefix); diff.Append("_d.jpg"); aiString spec = aiString(prefix); spec.Append("_s.jpg"); aiString norm = aiString(prefix); norm.Append("_n.jpg"); sf::Image * diffuseMap, * specularMap, * normalMap; std::map<aiMaterial*, sf::Image*>::iterator itr; itr = diffuse_textures.find(mat); if (itr == diffuse_textures.end()) { // No material loaded yet diffuseMap = new sf::Image(); bool loaded = diffuseMap->LoadFromFile(diff.data); if (loaded) { printf("Loaded diffuse texture %s\n", diff.data); diffuse_textures.insert(std::pair<aiMaterial *, sf::Image*>(mat, diffuseMap)); // diffuseMap->Bind(); // glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT ); // glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT ); // glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR_MIPMAP_LINEAR ); // glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR ); // glTexParameteri( GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE ); // glGenerateMipmapEXT(GL_TEXTURE_2D); } else { delete diffuseMap; } } itr = specular_textures.find(mat); if (itr == specular_textures.end()) { // No texture loaded yet specularMap = new sf::Image(); bool loaded = specularMap->LoadFromFile(spec.data); if (loaded) { printf("Loaded specular texture %s\n", spec.data); specular_textures.insert(std::pair<aiMaterial *, sf::Image *>(mat, specularMap)); // specularMap->Bind(); // glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT ); // glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT ); // glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR_MIPMAP_LINEAR ); // glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR ); // glTexParameteri( GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE ); // glGenerateMipmapEXT(GL_TEXTURE_2D); } else { delete specularMap; } } itr = normal_textures.find(mat); if (itr == normal_textures.end()) { // No texture loaded yet normalMap = new sf::Image(); bool loaded = normalMap->LoadFromFile(norm.data); if (loaded) { printf("Loaded normal texture %s\n", norm.data); normal_textures.insert(std::pair<aiMaterial *, sf::Image *>(mat, normalMap)); // normalMap->Bind(); // glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT ); // glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT ); // glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR_MIPMAP_LINEAR ); // glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR ); // glTexParameteri( GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE ); // glGenerateMipmapEXT(GL_TEXTURE_2D); } else { delete normalMap; } } newMesh.diff_string = diff; newMesh.spec_string = spec; newMesh.norm_string = norm; } else { newMesh.diff_string = aiString(""); } currentMesh_vec->push_back(newMesh); } // draw all children for (n = 0; n < nd->mNumChildren; ++n) { recursive_load_meshes(sc, nd->mChildren[n]); } glPopMatrix(); }
static bool load(std::shared_ptr<CookingTask> cookingTask) { if (!cookingTask->dataSet->loadSkeleton) return true; auto tid = Singleton<AGE::AE::ConvertorStatusManager>::getInstance()->PushTask("SkeletonLoader : loading " + cookingTask->dataSet->filePath.getShortFileName()); auto boneOrigin = cookingTask->assimpScene->mRootNode; bool hasSkeleton = false; for (unsigned int meshIndex = 0; meshIndex < cookingTask->assimpScene->mNumMeshes; ++meshIndex) { if (cookingTask->assimpScene->mMeshes[0]->HasBones()) hasSkeleton = true; } if (!hasSkeleton) { Singleton<AGE::AE::ConvertorStatusManager>::getInstance()->PopTask(tid); std::cerr << "Skeleton loader : mesh do not have skeleton." << std::endl; return true; } cookingTask->skeleton = std::make_shared<Skeleton>(); Skeleton *skeleton = cookingTask->skeleton.get(); std::uint32_t minDepth = std::uint32_t(-1); skeleton->firstBone = 0; skeleton->name = cookingTask->dataSet->filePath.getShortFileName(); for (unsigned int meshIndex = 0; meshIndex < cookingTask->assimpScene->mNumMeshes; ++meshIndex) { aiMesh *mesh = cookingTask->assimpScene->mMeshes[meshIndex]; for (unsigned int i = 0; i < mesh->mNumBones; ++i) { std::string boneName = mesh->mBones[i]->mName.data; if (skeleton->bonesReferences.find(boneName) != std::end(skeleton->bonesReferences)) continue; auto index = skeleton->bones.size(); skeleton->bones.push_back(AGE::Bone()); skeleton->bones.back().index = static_cast<uint32_t>(index); skeleton->bones.back().name = boneName; skeleton->bones.back().offset = AssimpLoader::aiMat4ToGlm(mesh->mBones[i]->mOffsetMatrix); skeleton->bonesReferences.insert(std::make_pair(boneName, static_cast<uint32_t>(index))); auto boneNode = cookingTask->assimpScene->mRootNode->FindNode(boneName.c_str()); if (!boneNode) continue; skeleton->bones.back().transformation = AssimpLoader::aiMat4ToGlm(boneNode->mTransformation); std::uint32_t depth = getDepth(boneNode); if (depth < minDepth) { minDepth = depth; skeleton->firstBone = static_cast<uint32_t>(index); boneOrigin = cookingTask->assimpScene->mRootNode->FindNode(boneName.c_str()); } } } boneOrigin = cookingTask->assimpScene->mRootNode->FindNode(skeleton->bones[skeleton->firstBone].name.c_str()); if (boneOrigin->mParent) { boneOrigin = boneOrigin->mParent; } skeleton->inverseGlobal = glm::inverse(AssimpLoader::aiMat4ToGlm(boneOrigin->mTransformation)); loadSkeletonFromAssimp(skeleton, cookingTask->assimpScene->mRootNode, minDepth); //we fill bone hierarchy for (unsigned int i = 0; i < skeleton->bones.size(); ++i) { aiNode *bonenode = cookingTask->assimpScene->mRootNode->FindNode(aiString(skeleton->bones[i].name)); if (!bonenode) continue; //we set bone transformation skeleton->bones[i].transformation = AssimpLoader::aiMat4ToGlm(bonenode->mTransformation); // we set parent if (bonenode->mParent != nullptr && skeleton->bonesReferences.find(bonenode->mParent->mName.data) == std::end(skeleton->bonesReferences)) { auto parent = bonenode->mParent; while (parent && skeleton->bonesReferences.find(parent->mName.data) == std::end(skeleton->bonesReferences)) { skeleton->bones[i].offset = glm::inverse(AssimpLoader::aiMat4ToGlm(parent->mTransformation)) * skeleton->bones[i].offset; skeleton->bones[i].transformation = AssimpLoader::aiMat4ToGlm(parent->mTransformation) * skeleton->bones[i].transformation; parent = parent->mParent; } if (parent) { skeleton->bones[i].parent = skeleton->bonesReferences.find(parent->mName.data)->second; } } else if (bonenode->mParent) { skeleton->bones[i].parent = skeleton->bonesReferences.find(bonenode->mParent->mName.data)->second; } //we set children for (unsigned int c = 0; c < bonenode->mNumChildren; ++c) { auto f = skeleton->bonesReferences.find(bonenode->mChildren[c]->mName.data); if (f == std::end(skeleton->bonesReferences)) continue; skeleton->bones[i].children.push_back(f->second); } } if (skeleton->bones.size() == 0) { std::cerr << "Skeleton loader : assets does not contain any skeleton." << std::endl; cookingTask->skeleton = nullptr; Singleton<AGE::AE::ConvertorStatusManager>::getInstance()->PopTask(tid); return false; } Singleton<AGE::AE::ConvertorStatusManager>::getInstance()->PopTask(tid); return true; }
// ------------------------------------------------------------------- // Get values for a new material description void ObjFileParser::getMaterialDesc() { // Get next data for material data m_DataIt = getNextToken<DataArrayIt>(m_DataIt, m_DataItEnd); if (m_DataIt == m_DataItEnd) { return; } char *pStart = &(*m_DataIt); while( m_DataIt != m_DataItEnd && !IsLineEnd( *m_DataIt ) ) { ++m_DataIt; } // In some cases we should ignore this 'usemtl' command, this variable helps us to do so bool skip = false; // Get name std::string strName(pStart, &(*m_DataIt)); strName = trim_whitespaces(strName); if (strName.empty()) skip = true; // If the current mesh has the same material, we simply ignore that 'usemtl' command // There is no need to create another object or even mesh here if (m_pModel->m_pCurrentMaterial && m_pModel->m_pCurrentMaterial->MaterialName == aiString(strName)) skip = true; if (!skip) { // Search for material std::map<std::string, ObjFile::Material*>::iterator it = m_pModel->m_MaterialMap.find(strName); if (it == m_pModel->m_MaterialMap.end()) { // Not found, use default material m_pModel->m_pCurrentMaterial = m_pModel->m_pDefaultMaterial; DefaultLogger::get()->error("OBJ: failed to locate material " + strName + ", skipping"); strName = m_pModel->m_pDefaultMaterial->MaterialName.C_Str(); } else { // Found, using detected material m_pModel->m_pCurrentMaterial = (*it).second; } if (needsNewMesh(strName)) createMesh(strName); m_pModel->m_pCurrentMesh->m_uiMaterialIndex = getMaterialIndex(strName); } // Skip rest of line m_DataIt = skipLine<DataArrayIt>( m_DataIt, m_DataItEnd, m_uiLine ); }
void repo::core::RepoNodeMesh::toAssimp( const std::map<const RepoNodeAbstract *, unsigned int> materialMapping, aiMesh * mesh) const { //-------------------------------------------------------------------------- // Name mesh->mName = aiString(name); //-------------------------------------------------------------------------- // Faces if (NULL != faces && 0 < faces->size()) { aiFace * facesArray = new aiFace[faces->size()]; if (NULL != facesArray) { std::copy(faces->begin(), faces->end(), facesArray); mesh->mFaces = facesArray; mesh->mNumFaces = (unsigned int) faces->size(); mesh->mPrimitiveTypes = 4; // TODO: work out the exact primitive type of each mesh! } else mesh->mNumFaces = 0; } else mesh->mNumFaces = 0; //-------------------------------------------------------------------------- // Vertices // Make a copy of vertices aiVector3D * verticesArray = new aiVector3D[vertices->size()]; if (NULL != verticesArray) { std::copy(vertices->begin(), vertices->end(), verticesArray); mesh->mVertices = verticesArray; mesh->mNumVertices = (unsigned int) vertices->size(); } else mesh->mNumVertices = 0; //-------------------------------------------------------------------------- // Normals // Make a copy of normals if (NULL != normals && 0 < normals->size()) { aiVector3D * normalsArray = new aiVector3D[normals->size()]; if (NULL != normalsArray) { std::copy(normals->begin(), normals->end(), normalsArray); mesh->mNormals = normalsArray; } } //-------------------------------------------------------------------------- // Texture coordinates // // TODO: change to support U and UVW, not just UV as done now. if (NULL != uvChannels && 0 < uvChannels->size()) { for (unsigned int i = 0; i < uvChannels->size() && i < AI_MAX_NUMBER_OF_TEXTURECOORDS; ++i) { aiVector3D * texCoords = new aiVector3D[vertices->size()]; std::copy(uvChannels->at(i)->begin(), uvChannels->at(i)->end(), texCoords); mesh->mTextureCoords[i] = texCoords; mesh->mNumUVComponents[i] = 2; // UV } } //-------------------------------------------------------------------------- // Vertex colors if(NULL != colors && 0 < colors->size()) { aiColor4D * colorsArray = new aiColor4D[colors->size()]; std::copy(colors->begin(), colors->end(), colorsArray); mesh->mColors[0] = colorsArray; } //-------------------------------------------------------------------------- // Material index // // In assimp, mesh would be expected to have only one child. // If multiple children materials are found, takes the first one std::map<const RepoNodeAbstract *, unsigned int>::const_iterator it; std::set<const RepoNodeAbstract *>::iterator childrenIt; for (childrenIt = children.begin(); childrenIt != children.end(); ++childrenIt) { it = materialMapping.find(*childrenIt); if (materialMapping.end() != it) { mesh->mMaterialIndex = it->second; break; } } }