2013年03月30日

環境マッピングについて

以前から環境マッピングの使い方がおかしい気がしていたので色々まとめてみました。
間違っていたら教えてください。

スカイドーム用のパノラマ画像は、左右が±180度、上下が±90度の範囲で映っている画像だと思います。
スカイドームでは、大きい球のモデルに対して、その内側にテクスチャとして貼り付けるものだと思います。

skydome_0001.png

この画像を球に貼り付けるためには、極座標系に変換する必要があります。
極座標系に関しては、Wikipediaを参考にしました[1]。
極座標系とは、座標を動径と偏角で表現したもので、球座標系⇔ワールド座標系の変換は以下の計算でできます。

skydome_0002.png

パノラマ画像の座標系と球座標系は、以下の図のような対応になります。

skydome_0003.png

以上の情報から、画像の座標系から極座標系の変換は、以下のようになります。

skydome_0004.png

この極座標系をワールド座標に変換するためには、最初に示した式を使います。

skydome_0005.png

今度は逆に、ワールド座標系からパノラマ画像の座標を求めたい場合は、これまでと逆の計算をすればよい、ということになります。

skydome_0006.png

スカイドームにテクスチャとして貼り付ける場合にはテクスチャ座標が必要ですので、上記の計算で球の頂点座標からパノラマ画像の座標を計算し、その座標をST座標に変換してやれば、スカイドーム用の球モデルを作成できる、というわけです。おそらく。

とりあえず一般的な使用方法?として、地面を仮定して、視線ベクトルの反射/屈折を計算した結果を以下に示します。
スカイドームにつきましては、[2]のussy様のHDR画像を使用させていただいております。



続いて、Image Based Lightingについてです。
これは、環境マッピングの画像を光源として利用しようというもので、これも使い方としていろいろあります。

大域照明を計算しようと思うと、周囲全てから当たる光を計算する必要がありますが、環境マップを光源として使用した場合も、半球状の光の反射方向全てを計算するのは計算時間的に難しいです。
そこで、16方向など、設定した数のみ計算する方法や、環境マップから光源を作成して、それを用いる手法などがあるようです。
今回は、パノラマ画像からk-means法でk個の光源を計算する方法[3]を試してみました。

パノラマ画像の各画素において、極座標系→ワールド座標系に変換して、そのワールド座標を元にk-means法で領域分割しました。
下の画像は、200個の光源を生成したもので、見やすいように画像をスムージングしています。

light200.png

この光源200個を平行光源と考えて、拡散反射成分(法線ベクトルと光源ベクトルの内積)と、鏡面反射成分(反射ベクトルと光源ベクトルの内積)を使って計算した場合、以下のような結果になりました。

skydome000_200.png

一応球→平面及び平面→球に当たった場合は加算しないようにしていますので、環境遮蔽のような効果はでていますが、何か変な線のような模様が出ておかしいです。
色の計算方法がおかしいのか、サンプル数(光源数)が少ないのか、どうなのでしょうね。

一応サンプル数を増やしたらどうなるのかの実験ということで、2500個の光源を生成してみました。

light2500.png

これを使って同じ方法で計算した結果、以下のようになりました。

skydome000_2500.bmp

一応滑らかになりましたが、計算時間がかかりすぎですね。

実行結果



次は球面調和関数を使う方法について試してみたいですが、理解できるかどうか微妙なところです。

[1] http://ja.wikipedia.org/wiki/極座標系
[2] http://www.nicovideo.jp/watch/sm10968092
[3] 倉地 紀子著, “CG Magic: レンダリング”, オーム社
posted by シンドラー at 18:18| Comment(0) | TrackBack(0) | OpenGL & Metasequoia | 更新情報をチェックする
この記事へのコメント
コメントを書く
コチラをクリックしてください

この記事へのトラックバック