1

opengl 3.3、radeon 3870HD、c++を使用します。

データのインターリーブされた配列について質問がありました。アプリケーション構造をベクトルで取得しました。これは、データとしてバッファオブジェクトに送信されます。このようなもの:

struct data{
  int a;
  int b;
  int c;
};

std::vector<data> datVec;
...
glBufferData(GL_ARRAY_BUFFER, sizeof(data)*datVec.size(), &datVec[0], GL_DYNAMIC_DRAW);

これは大丈夫です私はこれを頻繁に使用します。しかし、私が作成するのはインターリーブされた配列なので、データは次のようになります。

a1,b1,c1,a2,b2,c2,a3,b3,c3

これをGPUで処理するために送信し、変換フィードバックを使用して、たとえばb変数などのバッファーに読み戻します。したがって、次のようになります。

bU1, bU2, bU3

更新された値をインターリーブされたバッファーにコピーしたいのですが、これはglCopyBufferSubDataのような単一のコマンドで実行できますか?これは、オフセットとサイズがストライドではないため、適切ではありません(おそらく、c ++のmemcpyのようなものです)...結果は次のようになります。

a1, bU1, c1, a2, bU2, c2, a3, bU3, c3

そうでない場合は、これらの2つの鉱山よりも優れたアプローチがありますか?

  1. 更新されたバッファをマップし、アプリの一時ストレージに値をコピーし、更新されたマップを解除し、データバッファをマップし、それを繰り返して新しい値を設定します

  2. 定数バッファーと可変バッファーで別々のバッファー。定数は時間の経過とともに同じままですが、glCopyBufferSubDataを使用すると、変数を1回の呼び出しで更新できます。

ありがとう

4

2 に答える 2

1

glMapBufferは、あなたがしていることに対してより良い解決策のようです。

私の知る限り、基本的な考え方は、バッファーをアドレススペースにマップしてから、独自の更新方法を使用して手動でバッファーを更新することです(反復ループの可能性があります)。

glBindBuffer(GL_ARRAY_BUFFER, buffer_id);
void *buffer = glMapBuffer(GL_ARRAY_BUFFER, GL_WRITE_ONLY);

if (buffer == NULL)
  //Handle Error, usually means lack of virtual memory

for (int i = 1; i < bufferLen; i += stride /* 3, in this case */)
  buffer[i] = newValue;

glUnmapBuffer(GL_ARRAY_BUFFER);
于 2011-02-15T15:39:13.557 に答える
0

動的部分を静的部分(ポイント2)で分離します。

それでもそれらを単一のバッファにインターリーブしたままにしておきたい場合で、予備のビデオメモリがある場合は、次のようにすることができます。

  1. 元のインターリーブされたアレイをバックアップアレイにコピーします。これには、元々の動的コンポーネントだけでなく、すべてのコンポーネントのメモリが必要です。
  2. フィードバックを元のインターリーブに変換し、静的な値を変更せずに保持します。
于 2011-02-15T18:21:28.157 に答える