メッシュが非表示になっているときに/後処理メッシュのアウトラインを非表示にする方法


10

3Dエンジンでアクティブなアウトラインを設定する作業をしています。選択した3Dキャラクターのハイライト効果や画面の風景です。ステンシルバッファーを操作し、満足のいく結果が得られなかった後(凹面形状の問題、カメラからの距離が原因のアウトラインの厚さ、デスクトップとラップトップ間の不整合)、エッジ検出とフレームバッファーサンプリングに切り替えて、アウトラインを取得しましたかなり満足しています。

ただし、選択したメッシュが別のメッシュの背後にある場合、アウトラインを非表示にできません。これは、残りのシーンをレンダリングした後、フレームバッファーから2Dシェーダーアウトラインをレンダリングするだけなので、私のプロセスを考えると理にかなっています。

結果の2つの画面キャプチャーを以下に示します。1つ目は「良好な」アウトラインで、2つ目は、アウトラインソースをブロックするメッシュ上にアウトラインが表示される場所です。

ここに画像の説明を入力してください

レンダリングプロセスは次のように実行されます。1)ハイライトされたメッシュのアルファのみを描画し、フレームバッファー(framebuffer1)に黒いシルエットをキャプチャします。

2)テクスチャをframebuffer1からエッジ検出を実行する2番目のシェーダーに渡します。フレームバッファ2でエッジをキャプチャします。

3)シーン全体をレンダリングします。

4)シーンの上部にあるframebuffer2からテクスチャをレンダリングします。

私は達成する方法についていくつかのアイデアを持っているので、それらの有効性、またはより単純な、またはより良い方法についてフィードバックを得たいと思っています。

最初に、シーン全体をフレームバッファーにレンダリングし、強調表示されたメッシュの可視シルエットをアルファチャネルに格納することを考えました(強調表示されたメッシュが表示されているところはすべて白で保存されています)。次に、アルファチャネルでエッジ検出を実行し、シーンフレームバッファーをレンダリングしてから、エッジを上にレンダリングします。次のような結果になります:

結果

これを実現するために、ハイライトされたオブジェクトのレンダーパス中にのみ、定義を設定して、可視ピクセルのアルファをすべて黒くすることを考えました。

私の2番目のアイデアは、上で概説した現在のレンダリングプロセスを使用することですが、選択したメッシュのシルエットをレンダリングするときに、framebuffer1のR、G、BチャネルにもX、Y、Z座標を格納します。エッジ検出が実行され、framebuffer2に格納されますが、RGB / XYZ値をアルファのエッジからシルエットに渡します。次に、シーンをレンダリングするときに、座標がframebuffer2に格納されているエッジ内にあるかどうかをテストします。その場合は、現在のフラグメントの深度をテストして、RGBチャネルから抽出された座標(カメラ空間に変換)の前か後ろかを判断します。フラグメントが深度座標の前にある場合、フラグメントは正常にレンダリングされます。フラグメントが背後にある場合は、塗りつぶされたアウトラインカラーとしてレンダリングされます。

私はこのプロジェクトにLibGDXを使用しており、WebGLとOpenGL ESをサポートしたいので、ジオメトリシェーダーや新しいGLSL関数を使用するソリューションはありません。私の提案したアプローチについて誰かがコメントしたり、より良い提案をしたりできるとしたら、本当にありがたいです。


あなたのレポを見てもらいました。許容できる回避策を見つけたことがありますか?
iKlsR 2017年

回答:


0

シーン全体をステンシルバッファーにレンダリングして、目的のアウトラインオブジェクトでビットを設定し、それ以外のビットを破棄または削除します。

次に、エッジ検出を取り除きます。これは必要ありません。代わりに、バッファを少しだけ拡大できます。したがって、各オブジェクトはわずかに大きくなります。

そこから、ステンシルバッファーに必要なアウトラインを設定できます。レンダリングしている他のオブジェクトがステンシルバッファのビットをオフにしていることを確認することがすべてです。


2
返信いただきありがとうございます。スケーリングが3Dで行われる場合、この方法は輪郭の太さや凹型の形状で同様の問題に遭遇しないでしょうか?または、2Dで行われ、輪郭が描かれたオブジェクトが画面の死点にない場合、変位の問題はありますか?
15年

0

1)フレームバッファーオブジェクトで、GPUでラプラシアンシェーダーを実行して輪郭を取得できます。

2)FBOでオブジェクトを描画するときは、最終的な深度バッファーを使用する必要があります。これにより、FBOでオブジェクトの可視部分のみを描画し、ラプラシアンは可視部分のみの輪郭を描きます。


こんにちは、返信ありがとうございます。私は自分が持っている概要を達成するためにすでにこれを行っています。私はあなたがこの回答に反対票を投じる価値があるとは思いません。
nil

0

これを明確にできるといいのですが、基本的には両方のオブジェクトが選択されているかのように両方のオブジェクトのステンシルを作成し、実際に強調表示するアイテムの境界ボックスの領域のみを保持する必要があります。

したがって、基本的には、選択した両方のオブジェクト(またはオブジェクトを閉塞するすべてのオブジェクト)の1つのステンシルバッファを作成します。これで十分です)、そしてオブジェクトのバウンディングボックスのステンシルを使用します。

それはあなたが探している効果を得るはずです。

あるいは、「悪い」結果をそのまま残すことができます。これはデータ/ゲーム、特にオブジェクトのサイズに依存しますが、ほとんどの人があまり気にしないと思います。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.