29

私はSDL2テクスチャの背後にあるロジックに固執しています。私にとって、あなたがそれらに引き寄せることができないので、それらは無意味です。

私のプログラムでは、いくつかのサーフェス(またはSDL2に切り替える前のサーフェス)があり、それらをつなぎ合わせてレイヤーを形成しました。SDL_RenderCopyさて、同じ効果を作成するには、テクスチャポインタを使用するため、いくつかのレンダラーとテクスチャを作成する必要があるようです。

それだけでなく、すべてのレンダラーはウィンドウから来る必要があります。これは私が理解していることですが、それでも私をもう少し汚します。

これはすべて非常にかさばり、遅いようです。私は何かが足りないのですか?テクスチャに直接描画する方法はありますか?テクスチャのポイントは何ですか?サーフェスであったものの代わりに複数の(数百ではないにしても)レンダラーを使用しても安全ですか?

4

3 に答える 3

39

SDL_Textureオブジェクトはビデオ カード メモリのできるだけ近くに保存されるため、GPU によって簡単に高速化できます。サイズ変更、アルファ ブレンディング、アンチエイリアシング、およびほとんどすべての計算負荷の高い操作は、このパフォーマンスの向上によって深刻な影響を受ける可能性があります。プログラムがテクスチャでピクセルごとのロジックを実行する必要がある場合は、テクスチャを一時的にサーフェスに変換することをお勧めします。ストリーミング テクスチャを使用して回避策を達成することも可能です。

編集:この回答はかなりの注目を集めているので、私の提案を詳しく説明したいと思います。

ワークフローを使用Texture -> Surface -> Textureしてピクセルごとの操作を適用する場合は、レンダリング サイクルごとに再計算する必要がない限り、最終的なテクスチャをキャッシュしてください。このソリューションのテクスチャはSDL_TEXTUREACCESS_STATICフラグで作成されます。

ストリーミング テクスチャ (作成フラグはSDL_TEXTUREACCESS_STREAMING) は、ピクセル データのソースがネットワーク、デバイス、フレーム サーバー、または SDL アプリケーションの完全な範囲を超えたその他のソースであり、ソースからのフレームのキャッシュが非効率的であることが明らかな場合に推奨されます。または動作しません。

SDL_TEXTUREACCESS_TARGETテクスチャがフラグ付きで作成されている場合、テクスチャの上にレンダリングすることができます。これにより、描画操作のソースが他のテクスチャに制限されますが、これは最初に必要なものである可能性があります。「レンダー ターゲットとしてのテクスチャ」は、SDL2 の最新かつ最もサポートされていない機能の 1 つです。

好奇心旺盛な読者のためのオタク情報:

SDL 実装の性質上、最初の 2 つの方法はアプリケーション レベルの読み取り操作とコピー操作に依存しますが、推奨されるシナリオ向けに最適化されており、リアルタイム アプリケーションに対して十分高速です。

アプリケーション レベルからのデータのコピーは、GPU での後処理と比較すると、ほとんどの場合低速です。要件が SDL が提供できるものよりも厳しく、ロジックが外側のピクセル データ ソースに依存しない場合は、SDL サーフェスからペイントされた未加工の OpenGL テクスチャを割り当て、それらにシェーダー(GPU ロジック) を適用するのが賢明です。

シェーダーは、GPU アセンブリにコンパイルされる言語である GLSL で記述されています。ハードウェア/GPU アクセラレーションは、実際には GPU コアで並列化されたコードを指し、シェーダーを使用することは、レンダリング目的でそれを達成するための推奨される方法です。

注意!生の OpenGL テクスチャおよびシェーダーを SDL レンダリング関数および構造と組み合わせて使用​​すると、予期しない競合が発生したり、ライブラリによって提供される柔軟性が失われたりする可能性があります。

TLDR; テクスチャの変更は面倒な場合がありますが、サーフェスよりもテクスチャをレンダリングして操作する方が高速です。

于 2012-11-26T16:33:38.610 に答える
8

SDL2 テクスチャを STREAMING タイプとして作成することにより、テクスチャ全体またはピクセルの領域のみをロックおよびロック解除して、直接ピクセル操作を実行できます。SDL2 サーフェスの前に作成し、次のようにロック/ロック解除でリンクする必要があります。

SDL_Surface surface = SDL_CreateSurface(..);
SDL_LockTexture(texture, &rect, &surface->pixels, &surface->pitch);
// paint into surface pixels
SDL_UnlockTexture(texture);

重要なのは、より大きなサイズのテクスチャに描画し、描画がインクリメンタル (リアルタイムのデータ グラフなど) である場合は、更新する実際の領域のみをロックおよびロック解除することです。そうしないと、メモリのコピーが重くなり、操作が遅くなります。

私は妥当なパフォーマンスを経験しており、使用モデルを理解するのはそれほど難しくありません。

于 2013-05-22T09:44:29.520 に答える
7

SDL2 では、オフスクリーン レンダリング / テクスチャへの直接レンダリングが可能です。使用する関数は次のとおりです。

int SDL_SetRenderTarget(SDL_Renderer *renderer, SDL_Texture *texture);

これは、レンダラーが SDL_RENDERER_TARGETTEXTURE を有効にしている場合にのみ機能します。

于 2013-09-22T11:23:58.883 に答える