1

ビデオ フレームの処理とレンダリングにシェーダーを使用しています。したがって、各描画呼び出しの前にテクスチャを更新する必要があります。すべて正常に動作しますが、とりわけOpenGL プロファイラーを実行すると、次の警告が表示されました。

アプリケーションは、現在レンダリングに使用されているテクスチャに更新しようとしました。これにより、CPU は GPU がレンダリングを完了するまで待機します。この問題を解決する 1 つの方法は、ダブル バッファまたはリング バッファ アプローチを使用して、描画呼び出しの一部として使用されるテクスチャをアプリケーションが更新しないようにすることです。もう 1 つの可能性は、テクスチャが更新される前に GPU がテクスチャの使用を終了できるように、操作の順序を変更することです。

この記事を見つけました。私の理解が正しければ、2 番目のテクスチャを追加のバッファとして使用し、最初のテクスチャと交換可能に使用することをお勧めします。だから私は自分のコードを更新しました:

//use current texture
glBindTexture(GL_TEXTURE_2D, current_texture);

//update texture data
glTexImage2D(...);

//use the next texture and bind it
current_texture = (current_texture + 1)%2;
glBindTexture(GL_TEXTURE_2D, current_texture);

[and then draw smth using this texture];

正常に動作しますが、プロファイラーから同じ警告が表示されます。3 つ、4 つ、またはそれ以上の追加テクスチャを使用しても効果はありません。

後で見つけたように、この問題は を使用して解決できますがPixel Buffer ObjectsOpenGL ES 2.0はそれらをサポートしていないようです。

ここで何が欠けていますか?

4

1 に答える 1

0

ここで何が欠けていますか?

OpenGL は非同期 API です。呼び出しは、実際のレンダリングが実行されるよりもかなり早く返される場合があります。この簡略化された描画ループを見てみましょう。

for(i=0; ; i++) {
    glBindTexture(…, tex[i % 2]);
    glTexSubImage2D(…);

    glBindTexture(…, tex[(i + 1) % 2]);
    draw_image();
}

ここがポイントです。ループが繰り返された後、i がインクリメントされます。つまり、このコードを次のように書き直すことができます。

glBindTexture(…, tex[0]);
glTexSubImage2D(…);

for(i=1; ; i++) {
    glBindTexture(…, tex[i % 2]);
    draw_image();
    glTexSubImage2D(…);
}

そして、何が起こるかは明らかだと思います。

于 2013-06-13T10:33:04.773 に答える