This is the documentation for Enlighten.
7.1.2.1. 入力ライティングの概念
低レベル ランタイム
入力ライティングに関係するすべての関数とクラスは EnlightenInputLighting.h
で定義されており、ここにはカスタム ライト タイプを有効にするすべてのソースも含まれています。
入力ライティングは 2 つのステージに分かれます。
- 直接入力ライティング
- 間接入力ライティング
使用されるクラスや概念については以下で説明します。入力ライティングの提供に関する詳細は、フレームごとのウォークスルーの入力ライティングの提供で確認できます。
直接入力ライティング
直接入力ライティング ステージは、DoDirectinputLighting()
関数を介して実行されます。この関数は、DirectInputLightingParameters
オブジェクトを入力として受け取り、出力として単一の IncidentLightingBuffer
を作成します。この入射光バッファは、関数に渡される一連のライトの入射光を表します。IncidentLightingBuffer
で表される情報は他にないため、一連のライトに変更がない限りはキャッシュと更新が可能です。
DirectInputLighting
ソルバーは自動的にこれらのキャッシュ計算を事前に実施し、さらに作業が必要ない場合は早期に停止します。この機能の使用例としては、更新の頻度に応じてライトをグループ化し、各グループで DoDirectinputLighting()
を実行してそれぞれに固有の IncidentLightingBuffer
を生成します。これらの複数の IncidentLightingBuffers
は、次に以下で説明する IndirectInputLighting
ステージへの入力として使用できます。
詳細については、EnlightenInputLighting.h
の DoDirectinputLighting()
と CalcRequiredScratchSpaceMemory()
関数をご覧ください。
間接入力ライティング
間接入力ライティング ステージは、IncidentLightingBuffers、AlbedoBuffer、EmissiveBuffer、BounceBuffer、TransparencyWorkspace
の配列を入力として受け取り、単一の完全な InputLightingBuffer
を出力として生成します。これは、その後のラジオシティおよび Probe Solver ステージへの入力として使用されるオブジェクトと同じものです。また、IndirectInputLighting
ステージはフレーム間でのライティングの変化量も計算します。このデータは、一時的なコヒーレンスに使用されます。
詳細については、EnlightenInputLighting.h
の DoIndirectInputLighting()
関数をご覧ください。
IncidentLightingBuffer クラス
ユーザーが IncidentLightingBuffer
を割り当てる必要があります。詳細については、EnlightenLights.h
の CalcIncidentLightingBufferSize()
と CreateIncidentLightingBuffer()
関数をご覧ください。
入力ワークスペース
入力ワークスペースは、ラジオシティ計算で使われる入力サンプル ポイント (ダスター) のランタイム データ ストレージです。
入力ライティング バッファ
入力ライティング バッファは、システムの各クラスタの現在のライト値と、クラスタをまたぐバウンスをサポートするデータ構造体を格納します。これは、入力ライティング データを主要な Enlighten 解決関数に渡すためのメカニズムです。ライティング バッファに必要なメモリ量は、Enlighten::CalcInputLightingBufferSize
を介して取得できます。
入力サンプル ポイントをライティングするための入力ワークスペースの使用
入力ワークスペースはプリコンピュート中に構築され、入力サンプル ポイントで基本的なライティング機能を実施するために必要なすべての格納しています。入力サンプル ポイントに詳細な可視性を計算する能力はありません。必要な場合、ユーザーが提供する必要があります。以下の「可視性と入力ワークスペース」をご覧ください。
アプリケーションが入力サンプル ポイントをライティングする方法は 2 つあります。
- 生データ (位置、法線、マテリアル情報) を使用してサンプル ポイントをライティングします。これは通常、GPU でテクスチャにレンダリングすることによって行います。前述のとおり、このライティングは、拡散サーフェス アルベドカラーのみを重要とする簡素化されたシェーダーで実施できます。ライト値の配列が生成されると、入力ワークスペースに渡す必要があります。
- 入力ワークスペースに組み込まれたライティング機能を使用して、サンプル ポイントをライティングします。利用できるライト タイプは、ポイント ライト、スポット ライト、ディレクショナル ライトです。また、オプションとしてサンプルごとの可視性情報を個別に入力ワークスペースに渡し、ライティング機能を調節するために使うことができます。
可視性と入力ワークスペース
入力ワークスペースのライティング機能は、あらゆるライトに対してサンプルごとの可視性を適用することができます。各ライトはオプションで可視性のストレージ ブロックを有しており、入力サンプル ポイント (「ダスター」) あたり 1 ビットです。これが visibilityData
パラメーターに渡されると、ライティング機能が適切な可視性データのビットを読み取り、可視性が 1 だった場合にのみサンプル ポイントのライティングの寄与を追加します。
しかし、この可視性データの配列は個別に生成して入力ワークスペースに渡す必要があります。
- 可能な方法の 1 つは、シャドーマップ ルックアップを使用して GPU で可視性データを計算することです。GPU と CPU を分割するソリューション (入力ワークスペースを介した GPU での可視性、CPU でのライティング) の利点は、可視性を完全に動的にできる一方で、GPU が知る必要のあるものはダスター ポイントの位置だけであり、残りのライティング計算を CPU に任せることができることです。また、可視性とライティングは同じレートで更新する必要もありません。可視性は GPU フレーム レートに紐づけられますが、ライティングは値が異なる場合もあるラジオシティのフレーム レートで実行できます。
- ディレクショナル ライトについてのもう 1 つの可能な方法は、プリコンピュートされた可視性情報を使用することです。Enlighten プリコンピュートにより生成される可視性データは、ディレクショナル ライト向けにプリコンピュートされた可視性情報と静的ジオメトリです。
Enlighten::SetDirectionalVisibility()
を呼び出すことで渡せます。
ライティング計算の結果のキャッシュ
前述のとおり、IncidentLightingBuffers
はライティング値のみを格納するため、レベル ロード時などにライトの静的グループに対して 1 度作成できます。
入力ライティング バッファも同様にユーザーが制御し、再使用も可能です。キャッシュされた値は Enlighten::AddCachedValuesToInputWorkspace
を使用して入力ワークスペースに追加できます。これは入力ライティングだけではなく、システム自体も一定である場合、つまり静的アルベドとエミッシブ ライティングがある場合にのみ役立ちます。従って、Enlighten3
では静的入力ライティング バッファではなく、静的入射光バッファを使用します。
カスタム ライト タイプ
新しく、Enlighten に組み込まれた実装のないカスタム ライト タイプを追加できます。この方法については、EnlightenCustomerLights.h
を参照してください。提供されているテンプレートと説明に従って独自のライト クラスを実装できます。
カスタム入射光バッファ
一部の入力ライティング計算を GPU にオフロードしたい場合があります。DoDirectInputLighting()
関数の GPU への実装はまだ提供されていませんが、シェーディングされたサンプル ポイントから IncidentLightingBuffer
を生成する手段がいくつか提供されています。詳細については、AddDusterValuesToInputWorkspace
関数をご覧ください。