2011-01-16 11 views
1

3ds Maxから.OBJファイルを正しくインポートしようとしています。前の質問のglBegin()& glEnd()を使用していますが、明らかにパフォーマンスが悪いので、今すぐglDrawElementsを使用しようとしています。glDrawElementsを使用しても.objファイルが描画されない

チェス盤やそのゲームピースなどをインポートしています。ボード上の各ゲームピースと各四角形は、構造体GroupObjectに格納されています。私がデータを保存する方法は、次のとおりです。

struct Vertex 
{ 
    float position[3]; 
    float texCoord[2]; 
    float normal[3]; 
    float tangent[4]; 
    float bitangent[3]; 
}; 

struct Material 
{ 
    float ambient[4]; 
    float diffuse[4]; 
    float specular[4]; 
    float shininess;  // [0 = min shininess, 1 = max shininess] 
    float alpha;   // [0 = fully transparent, 1 = fully opaque] 

    std::string name; 
    std::string colorMapFilename; 
    std::string bumpMapFilename; 

    std::vector<int> indices; 
    int id; 
    }; 

//A chess piece or square 
struct GroupObject 
{ 
    std::vector<Material *> materials; 
    std::string objectName; 
    std::string groupName; 
    int  index; 
}; 

すべての頂点は三角形であるため、常に3つのポイントがあります。 objファイルのfaces fセクションをループしているときに、v0、v1、& v2をMaterial-> indexに格納します。 (私は0ベースのobjファイルと私のベクトルが0ベースであることを考慮するためにv [0-2] -1を実行しています。

私はレンダリングメソッドを取得すると、そのオブジェクトに付けられたすべてのマテリアルをループします。私はマテリアル情報を設定してglDrawElementsを試してみますが、スクリーンは黒です。その材料と、それがモデルの細かい。今回を描いたので、私はGroupObject Sを選択するためのステンシルバッファを使用することができ、私はループを変更したが、画面が黒くなる。

UPDATE が交換元レンデr現在のものとループし、その結果のスクリーンショット ここに私のレンダーループがあります。私が変更したのはforループだけなので、それぞれのオブジェクトとオブジェクトの各マテリアルを順番に調べます。ここで

void GLEngine::drawModel() 
{ 
ModelTextures::const_iterator iter; 
GLuint texture = 0; 

glEnable(GL_BLEND); 
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); 

// Vertex arrays setup 
glEnableClientState(GL_VERTEX_ARRAY); 
glVertexPointer(3, GL_FLOAT, model.getVertexSize(), model.getVertexBuffer()->position); 

glEnableClientState(GL_NORMAL_ARRAY); 
glNormalPointer(GL_FLOAT, model.getVertexSize(), model.getVertexBuffer()->normal); 

glClientActiveTexture(GL_TEXTURE0); 
glEnableClientState(GL_TEXTURE_COORD_ARRAY); 
glTexCoordPointer(2, GL_FLOAT, model.getVertexSize(), model.getVertexBuffer()->texCoord); 

glUseProgram(blinnPhongShader); 

objects = model.getObjects(); 
// Loop through objects... 
for(int i=0 ; i < objects.size(); ++i) 
{ 
    ModelOBJ::GroupObject *object = objects[i]; 

    // Loop through materials used by object... 
    for(int j=0 ; j<object->materials.size() ; ++j) 
    { 
     ModelOBJ::Material *pMaterial = object->materials[j]; 

     glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, pMaterial->ambient); 
     glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, pMaterial->diffuse); 
     glMaterialfv(GL_FRONT_AND_BACK, GL_SPECULAR, pMaterial->specular); 
     glMaterialf(GL_FRONT_AND_BACK, GL_SHININESS, pMaterial->shininess * 128.0f); 

     if (pMaterial->bumpMapFilename.empty()) 
     { 

      //Bind the color map texture. 
      texture = nullTexture; 
      if (enableTextures) 
      { 
       iter = modelTextures.find(pMaterial->colorMapFilename); 

       if (iter != modelTextures.end()) 
        texture = iter->second; 
      } 

      glActiveTexture(GL_TEXTURE0); 
      glEnable(GL_TEXTURE_2D); 
      glBindTexture(GL_TEXTURE_2D, texture); 

      //Update shader parameters. 
      glUniform1i(glGetUniformLocation(
       blinnPhongShader, "colorMap"), 0); 
      glUniform1f(glGetUniformLocation(
       blinnPhongShader, "materialAlpha"), pMaterial->alpha); 
     } 
     //glDrawElements(GL_TRIANGLES, pMaterial->triangleCount * 3, GL_UNSIGNED_INT, &pMaterial->indices.front()); 
     glDrawElements(GL_TRIANGLES, pMaterial->triangleCount * 3, GL_UNSIGNED_INT, model.getIndexBuffer() + pMaterial->startIndex); 

    } 

} 
glDisableClientState(GL_NORMAL_ARRAY); 
glDisableClientState(GL_TEXTURE_COORD_ARRAY); 
glDisableClientState(GL_VERTEX_ARRAY); 
glBindTexture(GL_TEXTURE_2D, 0); 
    glUseProgram(0); 
    glDisable(GL_BLEND); 
} 

は、上記の方法が描くものです: http://img844.imageshack.us/img844/3793/chess4.png

私はそれが重要だ行方不明ですか分かりません。それが役に立つ場合は、ここで私は 'f'の顔を読んで、pMaterial-> indexのobjインポータに情報を格納します。

else if (sscanf(buffer, "%d/%d/%d", &v[0], &vt[0], &vn[0]) == 3) // v/vt/vn 
     { 
      fscanf(pFile, "%d/%d/%d", &v[1], &vt[1], &vn[1]); 
      fscanf(pFile, "%d/%d/%d", &v[2], &vt[2], &vn[2]); 

      v[0] = (v[0] < 0) ? v[0] + numVertices - 1 : v[0] - 1; 
      v[1] = (v[1] < 0) ? v[1] + numVertices - 1 : v[1] - 1; 
      v[2] = (v[2] < 0) ? v[2] + numVertices - 1 : v[2] - 1; 

currentMaterial->indices.push_back(v[0]); 
currentMaterial->indices.push_back(v[1]); 
currentMaterial->indices.push_back(v[2]); 

UPDATE 2

電流出力:私はモデルをインポート行われていたとき、私は次のコード

glDrawElements(GL_TRIANGLES, pMaterial->triangleCount * 3, GL_UNSIGNED_INT, model.getIndexBuffer() + pMaterial->startIndex); 

でモデルを修正することができましたhttp://img337.imageshack.us/img337/860/chess4s.png

+1

最後に、あなたの最後の引用符のように、glDrawElementsを実行する必要があります。または、より良いかもしれません、&pMaterial-> indices.front()。私は今これを見ていて、他の問題を見つけたと思っていますが、まだ何も考えていません。 –

+0

返事をありがとう。私はあなたの提案も試みましたが、まだ何も描かれていませんでした。ちょうど黒い背景。私は何か簡単なことが分かっているので、私はソースコード全体をどこかに投稿したいと思っています。私はちょうどそれをあまりにも長く見ていると思う – Nathan

+0

私の記事の末尾に更新を追加しました – Nathan

答えて

0

、I triangleCountを実行していた& startIndexのように設定します。これは私の解決策でした:

for (int i = 0; i < static_cast<int>(m_attributeBuffer.size()); i++) 
{ 
    if (m_attributeBuffer[i] != materialId) 
    { 
     materialId = m_attributeBuffer[i]; 
     ++numMaterials; 
    } 
} 

// Allocate memory for the materials and reset counters. 
m_numberOfObjectMaterials = numMaterials; 
m_materials.resize(m_numberOfObjectMaterials); 
numMaterials = 0; 
materialId = -1; 

// Build the meshes. One mesh for each unique material. 
for (int i = 0; i < static_cast<int>(m_attributeBuffer.size()); i++) 
{ 
    if (m_attributeBuffer[i] != materialId) 
    { 
     materialId = m_attributeBuffer[i]; 
     m = m_ObjectMaterials[materialId]; 
     m->startIndex = i * 3; 
     m->triangleCount = 0; 
     ++m->triangleCount; 
    } 
    else 
    { 
     ++m->triangleCount; 
    } 
} 
関連する問題