2017-03-24 9 views
0

私はassimpについて質問したいと思います。私のコードを実行しようとすると、コンパイラとリンカはエラーは出ませんが、ReadLine関数を使うとクラッシュしますが、私が使っている部分にコメントをつけてもプログラムは正常に動作します。Assimp importer.ReadFileを使用するとOpenGLプログラムが動作しなくなる

const aiScene *scene = importer.ReadFile(path, aiProcess_Triangulate |     aiProcess_FlipUVs); 

// Check for errors 
if (!scene || scene->mFlags == AI_SCENE_FLAGS_INCOMPLETE || !scene->mRootNode) // if is Not Zero 
{ 
    cout << "ERROR::ASSIMP:: " << importer.GetErrorString() << endl; 
    return; 
} 
// Retrieve the directory path of the filepath 

this->directory = path.substr(0, path.find_last_of('/')); 

// Process ASSIMP's root node recursively 
this->processNode(scene->mRootNode, scene); 

私は私のモデルオブジェクトを作成したメインの一部:

#include "Model.h" 

Model::Model(GLchar *path) 
{ 
    this->LoadModel(path); 
} 


Model::~Model() { 
} 


void Model::Draw(Shader shader) 
{ 
    for (GLuint i = 0; i < this->meshes.size(); i++) 
    { 
     this->meshes[i].Draw(shader); 
    } 
} 


void Model::LoadModel(string path) 
{ 

    // Read file via ASSIMP 
    Assimp::Importer importer; 

    const aiScene *scene = importer.ReadFile(path, aiProcess_Triangulate | aiProcess_FlipUVs); 

    // Check for errors 
    if (!scene || scene->mFlags == AI_SCENE_FLAGS_INCOMPLETE || !scene->mRootNode) // if is Not Zero 
    { 
     cout << "ERROR::ASSIMP:: " << importer.GetErrorString() << endl; 
     return; 
    } 
    // Retrieve the directory path of the filepath 

    this->directory = path.substr(0, path.find_last_of('/')); 

    // Process ASSIMP's root node recursively 
    this->processNode(scene->mRootNode, scene); 

} 

// Processes a node in a recursive fashion. Processes each individual mesh located at the node and repeats this process on its children nodes (if any). 
void Model::processNode(aiNode* node, const aiScene* scene) 
{ 
    // Process each mesh located at the current node 
    for (GLuint i = 0; i < node->mNumMeshes; i++) 
    { 
     // The node object only contains indices to index the actual objects in the scene. 
     // The scene contains all the data, node is just to keep stuff organized (like relations between nodes). 
     aiMesh* mesh = scene->mMeshes[node->mMeshes[i]]; 

     this->meshes.push_back(this->processMesh(mesh, scene)); 
    } 

    // After we've processed all of the meshes (if any) we then recursively process each of the children nodes 
    for (GLuint i = 0; i < node->mNumChildren; i++) 
    { 
     this->processNode(node->mChildren[i], scene); 
    } 
} 

Mesh Model::processMesh(aiMesh *mesh, const aiScene *scene) 
{ 
    // Data to fill 
    vector<Vertex> vertices; 
    vector<GLuint> indices; 
    vector<Texture> textures; 

    // Walk through each of the mesh's vertices 
    for (GLuint i = 0; i < mesh->mNumVertices; i++) 
    { 
     Vertex vertex; 
     glm::vec3 vector; // We declare a placeholder vector since assimp uses its own vector class that doesn't directly convert to glm's vec3 class so we transfer the data to this placeholder glm::vec3 first. 

          // Positions 
     vector.x = mesh->mVertices[i].x; 
     vector.y = mesh->mVertices[i].y; 
     vector.z = mesh->mVertices[i].z; 
     vertex.Position = vector; 

     // Normals 
     vector.x = mesh->mNormals[i].x; 
     vector.y = mesh->mNormals[i].y; 
     vector.z = mesh->mNormals[i].z; 
     vertex.Normal = vector; 

     // Texture Coordinates 
     if (mesh->mTextureCoords[0]) // Does the mesh contain texture coordinates? 
     { 
      glm::vec2 vec; 
      // A vertex can contain up to 8 different texture coordinates. We thus make the assumption that we won't 
      // use models where a vertex can have multiple texture coordinates so we always take the first set (0). 
      vec.x = mesh->mTextureCoords[0][i].x; 
      vec.y = mesh->mTextureCoords[0][i].y; 
      vertex.TexCoords = vec; 
     } 
     else 
     { 
      vertex.TexCoords = glm::vec2(0.0f, 0.0f); 
     } 

     vertices.push_back(vertex); 
    } 

    // Now wak through each of the mesh's faces (a face is a mesh its triangle) and retrieve the corresponding vertex indices. 
    for (GLuint i = 0; i < mesh->mNumFaces; i++) 
    { 
     aiFace face = mesh->mFaces[i]; 
     // Retrieve all indices of the face and store them in the indices vector 
     for (GLuint j = 0; j < face.mNumIndices; j++) 
     { 
      indices.push_back(face.mIndices[j]); 
     } 
    } 

    // Process materials 
    if (mesh->mMaterialIndex >= 0) 
    { 
     aiMaterial* material = scene->mMaterials[mesh->mMaterialIndex]; 
     // We assume a convention for sampler names in the shaders. Each diffuse texture should be named 
     // as 'texture_diffuseN' where N is a sequential number ranging from 1 to MAX_SAMPLER_NUMBER. 
     // Same applies to other texture as the following list summarizes: 
     // Diffuse: texture_diffuseN 
     // Specular: texture_specularN 
     // Normal: texture_normalN 

     // 1. Diffuse maps 
     vector<Texture> diffuseMaps = this->LoadMaterialTexture(material, aiTextureType_DIFFUSE, "texture_diffuse"); 
     textures.insert(textures.end(), diffuseMaps.begin(), diffuseMaps.end()); 

     // 2. Specular maps 
     vector<Texture> specularMaps = this->LoadMaterialTexture(material, aiTextureType_SPECULAR, "texture_specular"); 
     textures.insert(textures.end(), specularMaps.begin(), specularMaps.end()); 
    } 

    // Return a mesh object created from the extracted mesh data 
    return Mesh(vertices, indices, textures); 
} 

// Checks all material textures of a given type and loads the textures if they're not loaded yet. 
// The required info is returned as a Texture struct. 
vector<Texture> Model::LoadMaterialTexture(aiMaterial *mat, aiTextureType type, string typeName) 
{ 
    vector<Texture> textures; 

    for (GLuint i = 0; i < mat->GetTextureCount(type); i++) 
    { 
     aiString str; 
     mat->GetTexture(type, i, &str); 

     // Check if texture was loaded before and if so, continue to next iteration: skip loading a new texture 
     GLboolean skip = false; 

     for (GLuint j = 0; j < textures_loaded.size(); j++) 
     { 
      if (textures_loaded[j].path == str) 
      { 
       textures.push_back(textures_loaded[j]); 
       skip = true; // A texture with the same filepath has already been loaded, continue to next one. (optimization) 

       break; 
      } 
     } 

     if (!skip) 
     { // If texture hasn't been loaded already, load it 
      Texture texture; 
      texture.id = TextureFromFile(str.C_Str(), this->directory); 
      texture.type = typeName; 
      texture.path = str; 
      textures.push_back(texture); 

      this->textures_loaded.push_back(texture); // Store it as texture loaded for entire model, to ensure we won't unnecesery load duplicate textures. 
     } 
    } 

    return textures; 
} 

GLint TextureFromFile(const char *path, string directory) 
{ 
//Generate texture ID and load texture data 
string filename = string(path); 
filename = directory + '/' + filename; 
GLuint textureID; 
glGenTextures(1, &textureID); 

int width, height; 

unsigned char *image = SOIL_load_image(filename.c_str(), &width, &height, 0, SOIL_LOAD_RGB); 

// Assign texture to ID 
glBindTexture(GL_TEXTURE_2D, textureID); 
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, image); 
glGenerateMipmap(GL_TEXTURE_2D); 

// Parameters 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); 
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 
glBindTexture(GL_TEXTURE_2D, 0); 
SOIL_free_image_data(image); 

return textureID; 
} 

問題が発生Model.cppの一部は、これが1である: はここmodel.cppファイルです

Model ourModel("Object/models/nanosuit.obj"); 

私は1日中、解決策を探していました。誰かがそれを理解するのを助けることができたら、私は本当にうれしいでしょう。コードの他の部分が必要な場合は教えてください。

+0

クラッシュするとどのようなエラーが表示されますか? – Vallentin

+0

私はクラッシュを書きましたが、それが正しい言葉かどうかわかりません。 OpenGLで空白のウィンドウが表示され、「プログラム」の名前プログラムが動作を停止したと表示されます。 – Ciarfix

+0

「ReadLine関数を使用するとクラッシュします」と明示的に言っていますか? – Vallentin

答えて

0

まず、モデルファイルでこれがエラーであるかどうか確認してください。 Assimp-Viewerを使用してモデルをインポートすることができます。あなたがそこにそれを見ることができれば、あなたのコードが壊れているという兆候です。

モデルローダーでエラーが表示された場合は、インポーターまたはモデルが壊れている可能性があります。この場合、Asset-Importer-Libプロジェクトページ(https://github.com/assimp/assimp/issues/1215を参照)で問題を再度開いてください。

+0

AssimpViewerで見ることができます。私はyoutubeの次のチュートリアルのコードを使用しますそれは – Ciarfix

+0

うまあ、音が悪いです。あなたはモデルを提供してもらえますか? – KimKulling

+0

https://github.com/SonarSystems/Modern-OpenGL-Tutorials/tree/master/%5BMODEL%20LOADING%5D/%5B16%5D%20Model%20Class/res/models – Ciarfix

関連する問題