2

私は初心者で、opengl (Blender) の 3D モデリング プログラムで作成した小さな潜水艦を表示しようとしています。

潜水艦は、その端に球が交差する長い円柱を使用して構築されています。

私が得ている問題は、結果を見ると、円柱を通して球全体が見えることです。球体を通して円柱の端も見えます。これは、照明をオンにすると表示されます。アンビエント照明と拡散照明を使用しています。円柱の外側にある球の半分を見たいだけで、内部は見たくありません。

面カリングをオンにすると、両方のオブジェクトの前面が削除されますが、球体がはっきりと見えます。

以下に、すべての opengl パラメータを設定する onSurfaceCreated 関数を貼り付けました。どんな提案でも大歓迎です!

@Override
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
    //
    gl.glEnable(GL10.GL_DEPTH_TEST);
    //gl.glMatrixMode(GL10.GL_PROJECTION);

    gl.glMatrixMode(GL10.GL_MODELVIEW);

    gl.glEnable(GL10.GL_POLYGON_OFFSET_FILL);

    gl.glEnable(GL10.GL_LIGHTING);
    gl.glEnable(GL10.GL_LIGHT0);

    // Define the ambient component of the first light
    float[] light0Ambient = {0.1f, 0.1f, 0.1f, 1.0f};        
    gl.glLightfv(gl.GL_LIGHT0, gl.GL_AMBIENT, FloatBufferFromFloatArray(light0Ambient, 4));

    // Define the diffuse component of the first light
    float[] light0Diffuse = {0.7f, 0.7f, 0.7f, 1.0f};
    gl.glLightfv(gl.GL_LIGHT0, gl.GL_DIFFUSE, FloatBufferFromFloatArray(light0Diffuse, 4));

    // Define the specular component and shininess of the first light
    float[] light0Specular = {0.7f, 0.7f, 0.7f, 1.0f};
    float light0Shininess = 0.4f;
    //gl.glLightfv(gl.GL_LIGHT0, gl.GL_SPECULAR, FloatBufferFromFloatArray(light0Specular, 4));        

    // Define the position of the first light
    float[] light0Position = {1.0f, 0.0f, 0.0f, 0.0f};
    gl.glLightfv(gl.GL_LIGHT0, gl.GL_POSITION, FloatBufferFromFloatArray(light0Position, 4)); 

    // Define a direction vector for the light, this one points correct down the Z axis
    float[] light0Direction = {0.0f, 0.0f, -1.0f};
    //gl.glLightfv(gl.GL_LIGHT0, gl.GL_SPOT_DIRECTION, FloatBufferFromFloatArray(light0Direction, 3));

    // Define a cutoff angle. This defines a 90° field of vision, since the cutoff
    // is number of degrees to each side of an imaginary line drawn from the light's
    // position along the vector supplied in GL_SPOT_DIRECTION above
    //gl.glLightf(gl.GL_LIGHT0, gl.GL_SPOT_CUTOFF, 180.0f);

    gl.glEnable(GL10.GL_CULL_FACE);
    // which is the front? the one which is drawn counter clockwise
    gl.glFrontFace(GL10.GL_CCW);
    // which one should NOT be drawn
    gl.glCullFace(GL10.GL_BACK);

    gl.glClearDepthf(10f);
    gl.glPolygonOffset(1.0f, 2);

    initShape();

    gl.glScalef(0.5f, 0.5f, 0.5f);
}
4

5 に答える 5

1

ご覧のとおり、「シーングラフの初期化」についてはまだ考えているようです。それはOpenGLがどのように機能するかではありません(そう、これは私が答えとしてこれを書くのは3回連続です)。onSurfaceCreatedで行っていることはすべて、実際には表示ルーチンに属しています。OpenGLはシーングラフではありません。その状態を必要とするものを描画する直前に、必要なすべての状態を設定します。

そこにその関数「initShape」があるようです。私はこれがあなたの意図したことをしていないと思います。

于 2011-01-09T22:56:58.153 に答える
1

onDrawFrame() を見てみましょう。あなたの投影法は何ですか。法線が反転していて、投影がめちゃくちゃになっていて、おかしくなっている可能性があります。

深度バッファまたは深度テストに問題がある可能性もあります。

編集:球と交差しているポリゴンから深度カリングが見られるため、深度テストは問題ではないようです。ジオメトリに問題があるようです。

カメラを動かせるようにします。そうすれば、周りを見回して、何がおかしいのかを理解できます。

于 2011-01-10T00:15:41.590 に答える
1

深度バッファーが有効になっている EGL コンテキストがありますか? GLSurfaceView を使用している場合、SimpleEGLConfigChooser(true) であるはずの SimpleEGLConfigChooser(false) のようなものを探している可能性があります。

于 2011-01-09T23:59:01.447 に答える
1

背面カリングの問題かどうかを確認してみましたか? をに変更してglEnable(GL_CULL_FACE)確認glDisableしてください。間違いなくそうではないことを確認してください。同じメッシュ上に両方のワインディング順序が存在する可能性があるため、カリングはモデルのある部分では正しくても、別の部分では間違っている可能性があります。これを無効にして問題がないことを確認するのが最も簡単です。

それか、何らかの理由で深度バッファなしでサーフェスが作成された可能性がありますか? EGLConfig パラメーターをチェックして、そうでないことを確認してください。通常、デフォルトでは深度バッファで作成されますが、その動作をオーバーライドすることができます。

また、決して見ることのない内部面を持つものをモデル化しても、リアルタイム パフォーマンスに良い影響を与えることはありません。少なくともブレンダーでブール演算「or」を使用して内部面を取り除くことを検討する必要がありますが、最終的には、ポリゴン数だけでなく、モデルのトポロジーにも細心の注意を払ってモデルを作成することをお勧めします。三角形のストリップに合わせます (これは、現在発生している問題の言い訳にはなりません。これは、将来のための単なるメモです)。

于 2011-01-09T23:23:04.630 に答える
0

テクスチャを使用している場合は、使用しているブレンド機能を確認してください。オーバーラップするピクセルが、上書きされるのではなく、オーバーレイ効果のように乗算される場合があります。

于 2012-05-01T11:53:30.653 に答える