5

単一の Web-GL「プログラム」で複数のフラグメントシェーダーを連続して実行できるかどうかは誰にもわかりませんか? シェーダー効果を使用して、WPF で記述したコードを複製しようとしています。WPF プログラムでは、複数の境界線で画像をラップし、各境界線に効果を付けます (同じ画像で複数の効果を連続して実行できるようにします)。

4

4 に答える 4

10

おそらくあなたの質問を少し明確にする必要があると思いますが、とにかく答えることに挑戦します:

WebGL は、事実上、必要な数の異なるシェーダーをサポートできます。(もちろん、使用可能なメモリなどの実際的な制限はありますが、あまりにも多くのシェーダーを作成して、それらにぶつかるのにかなり苦労する必要があります。) 実際、ほとんどの「現実世界」の WebGL/OpenGL アプリケーションは、多くの異なる組み合わせを使用します。シェーダーを使用して、画面にレンダリングされる最終シーンを生成します。(簡単な例: 水は通常、周囲の他の環境とは異なるシェーダーまたはシェーダー セットでレンダリングされます。)

レンダリング コマンドをディスパッチする場合、一度にアクティブにできるシェーダー プログラムは 1 つだけです。現在アクティブなプログラムは、呼び出しによって指定され、gl.useProgram(shaderProgram);その後、描画されたジオメトリがそのプログラムでレンダリングされます。複数の異なるシェーダーを必要とするエフェクトをレンダリングする場合は、シェーダーごとにグループ化し、各バッチを個別に描画する必要があります。

 gl.useProgram(shader1);
 // Setup shader1 uniforms, bind the appropriate buffers, etc.
 gl.drawElements(gl.TRIANGLES, shader1VertexCount, gl.UNSIGNED_SHORT, 0); // Draw geometry that uses shader1

 gl.useProgram(shader2);
 // Setup shader2 uniforms, bind the appropriate buffers, etc.
 gl.drawElements(gl.TRIANGLES, shader2VertexCount, gl.UNSIGNED_SHORT, 0); // Draw geometry that uses shader2

 // And so on...
于 2012-07-09T02:33:02.923 に答える
6

他の答えは正しい軌道に乗っています。1 つのシェーダーまたはフレーム バッファー内のすべての効果を適用するシェーダーをオンザフライで作成し、一度に 1 つずつ効果を適用する必要があります。ここに後者の例があります

WebGL 画像処理 続き

于 2012-07-09T16:19:01.617 に答える
4

Toji が示唆したように、質問を明確にする必要があるかもしれません。私の理解が正しければ、一連の後処理効果を画像に適用したいと考えていると思います。

あなたの質問に対する簡単な答えは次のとおりです。いいえ、1 つの頂点シェーダーで複数のフラグメント シェーダーを使用することはできません。

ただし、これを実現するには 2 つの方法があります。1 つ目は、すべてを 1 つのフラグメント シェーダーに記述し、最後にそれらを結合することです。これは、必要な効果によって異なります。次に、複数のシェーダー プログラム (エフェクトごとに 1 つ) を作成し、結果をフラグメント バッファー オブジェクト (テクスチャーにレンダリング) に書き込むことができます。各シェーダーは前の効果の結果を取得し、次の効果を適用します。これは少し複雑になりますが、最も柔軟なアプローチです。

于 2012-07-09T08:24:03.747 に答える
1

1 つのレンダー パスで複数のシェーダーを実行する場合は、次のようにします (例は何もないところから引っ張ってきました)。

  1. 頂点の色
  2. テクスチャ
  3. 点灯

...各ステージが単一のWebGLProgramオブジェクトにアタッチされ、各ステージが独自のmain()機能を備えている場合、いいえ、GLSLはこのようには機能しません。

GLSL は C/C++ のように機能します。C/C++ では、プログラムのエントリ ポイントとして機能する単一のグローバルmain()関数と、任意の数のライブラリがそれに接続されています。上記の 4 つの例はそれぞれ、独自にコンパイルされたが単一のプログラムにリンクされ、単一の関数によって呼び出される個別の「ライブラリ」である可能性がありますが、GLSL でのそのような定義は全体で共有されるため、main()それぞれが独自の関数を定義するとは限りません。main()プログラム全体。

残念ながらmain()、使用するシェーダーごとに (少なくとも) 個別の関数を作成する必要があり、ライブラリ自体を再利用する予定がある場合でも、多くの冗長なプログラミングが発生します。そのため、 Jax用の GLSL ライブラリを管理するために、美化された文字列マングラーを作成することになりました。コードが私のフレームワークの外でどれほど役立つかはわかりませんが、自由に見て、役に立つと思うものを利用してください。関連するファイルは次のとおりです。

幸運を!

于 2012-07-13T16:37:50.940 に答える