2

透明な部分がいくつかあるテクスチャが 1 つあります。面が不透明なマテリアル (または単純な場合は色) であるオブジェクトに適用したいのですが、最終的なオブジェクトは透明になります。最終オブジェクトを完全に不透明にしたい。

これが私のコードです:

まず、マテリアルを設定します。

   glDisable(GL_COLOR_MATERIAL);
   glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT);
   glColor4f(0.00, 0.00, 0.00, 1.00);
   glColorMaterial(GL_FRONT_AND_BACK, GL_DIFFUSE);
   glColor4f(0.80, 0.80, 0.80, 1.00);
   glColorMaterial(GL_FRONT_AND_BACK, GL_SPECULAR);
   glColor4f(0.01, 0.01, 0.01, 1.00);
   glEnable(GL_COLOR_MATERIAL);

次に、VBO をセットアップします。

   glBindTexture(GL_TEXTURE_2D, object->texture);
   glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);

   glBindBuffer(GL_ARRAY_BUFFER, object->object);
   glVertexPointer(3, GL_FLOAT, sizeof(Vertex), ver_offset);
   glTexCoordPointer(2, GL_FLOAT, sizeof(Vertex), tex_offset);
   glNormalPointer(GL_FLOAT, sizeof(Vertex), nor_offset);

そして最後にオブジェクトを描画します

   glEnable(GL_BLEND);
   glDisable(GL_DEPTH_TEST);

   glDisable(GL_TEXTURE_2D);
   glBlendFunc(GL_ONE, GL_ZERO);
   glDrawArrays(GL_TRIANGLES, 0, object->num_faces);

   glEnable(GL_TEXTURE_2D);
   glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
   glDrawArrays(GL_TRIANGLES, 0, object->num_faces);

   glDisableClientState(GL_VERTEX_ARRAY);
   glDisableClientState(GL_TEXTURE_COORD_ARRAY);

   glDisable(GL_BLEND); 
   glEnable(GL_DEPTH_TEST);

glBlendFunc() にさまざまな引数を渡そうとしましたが、優勢ではありませんでした。ここにソースをアップロードしました: http://dpaste.com/83559/

更新 これを取得しますが、 これ必要です (またはテクスチャなしでこれが必要です)。

2枚目と3枚目はglmで作成したものです。ソースを調べましたが、OpenGL に関する知識が限られているため、あまり理解できませんでした。

4

5 に答える 5

3

オブジェクトに 2 つのテクスチャを適用しようとしている場合、実際には 2 つのテクスチャを設定し、マルチテクスチャリングを使用してこの外観を実現する必要があります。あなたの方法はジオメトリを2回描画しているため、パフォーマンスが大幅に浪費されています。

マルチテクスチャリングは、ジオメトリを 1 回描画するだけで、2 つのテクスチャ ユニットからサンプリングするだけです。これをシェーダーで行うことも (実際に行うべき方法)、固定関数パイプラインを引き続き使用することもできます (参照: http://bluevoid.com/opengl/sig00/advanced00/notes/node62.html ) 。

于 2009-08-21T13:52:22.630 に答える
1

私の知る限り、ブレンド関数はフラグメントの色を取ります (テクスチャの色とは対照的です)。そのため、ブレンドを使用してオブジェクトをもう一度描画すると、三角形が透明になります。

達成したいことは、multitexturingを使用して実行できます。

于 2009-08-21T13:52:41.193 に答える
0

GL_DECALブレンドを無効にして、テクスチャ関数をではなく に設定してシングル パスを描画してみてくださいGL_MODULATE。これにより、テクスチャのアルファ チャネルに基づいて頂点カラーとテクスチャ カラーがブレンドされますが、アルファ チャネルは頂点カラーに設定されたままになります。

これは、テクスチャが不透明だった頂点の色に適用された照明を無視することに注意してください。ただし、説明に基づいて、これは意図した効果のように聞こえます。

于 2009-08-23T17:35:53.153 に答える
0

実際の問題が何であるかのスクリーンショットを提供できなかったため、これは単なる推測ですが、なぜ深さテストを無効にするのですか? 標準の GL_LESS を使用して最初のパスで深度テストを有効にし、次に GL_EQUAL を使用して 2 番目のパスを実行したいですか?

編集:

すなわち

glEnable(GL_BLEND);
glEnable(GL_DEPTH_TEST);  // ie do not disable
glDepthFunc( GL_LESS );   // only pass polys have a z value less than ones already in the z-buffer (ie are in front of any previous pixels)

glDisable(GL_TEXTURE_2D);
glBlendFunc(GL_ONE, GL_ZERO);
glDrawArrays(GL_TRIANGLES, 0, object->num_faces);

// for the second pass we only want to blend pixels where they occupy the same position 
// as in the previous pass.  Therefore set to equal and only pixels that match the
// previous pass will be blended together.
glDepthFunc( GL_EQUAL );

glEnable(GL_TEXTURE_2D);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glDrawArrays(GL_TRIANGLES, 0, object->num_faces);

glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);

glDisable(GL_BLEND); 
于 2009-08-21T13:53:07.980 に答える
-1

ピクセル シェーダーを使用すると、はるかに簡単になります。それ以外の場合は、マルチパス レンダリングまたは複数のテクスチャが必要だと思います。ここで包括的な詳細を見つけることができます: http://www.opengl.org/resources/faq/technical/transparency.htm

于 2009-08-21T13:47:30.530 に答える