SourceChord

C#とXAML好きなプログラマの備忘録。最近はWPF系の話題が中心です。

空間分割について

すげぇ
空間分割マジすっげ!!

Realistic Ray Tracingで紹介されている方法で空間分割を実装してみたのですが、その効果は想像以上でした。
以前はオブジェクト全体を一つのバウンディングスフィアで覆っているだけだったので、ほとんど全ての三角形と交差判定をしていたため、このシーンのレンダリングで25分ほどかかってしまっていました。
が、RRT本で解説されている空間分割を実装したところ、レンダリング時間なんと1.5秒!!!
なんと約1000倍の高速化です!!
このstanford bunnyのオブジェクトはおよそ7万ポリゴンくらいあるから、そりゃ全部の三角形と交差判定してたら遅くなるよなぁ・・・


なんか俄然やる気出てきたww

空間分割のアルゴリズム

RRT本で解説されていたアルゴリズムでは、空間をxyzそれぞれの軸と平行なバウンディングボックスで分割していきます。
イメージはだいたいこんな感じ


全てのオブジェクトの親となるクラスから派生したBVHというクラスを用意。
BVHはバウンディングボックスと二つの子ノードを保持。
1.オブジェクト全体を覆うバウンディングボックスをもったBVHオブジェクトを生成。
2.BBoxを中心で2つに分割。
分割する際には、x→y→zという順番で、各軸の中心の位置で分割していきます。
分割した面に垂直な方向に三角形の並び順をソート(ソートの基準は三角形の中心位置)
3.端から分割した位置までの三角形全てを覆うBVHオブジェクトと、分割した位置から反対側までの三角形全てを覆うBVHオブジェクトを生成。
分割した二つのBVHオブジェクトを子ノードとして記録。

これをBBoxの内部が2つの三角形になるまで繰り返して分割していく。


交差判定の際には、ルートのBVHと交差するか判定し、交差するなら子ノードの二つとも交差判定をする、というのを繰り返していくものです。
軸並行なバウンディングボックスとの交差判定は比較的高速に処理できるので、これでかなり速くなりました。

おまけ

フォトンマップも少しずつ修正してます。
以前、フォトンマッピングでレンダリングしたとき、なんか暗くなったりと上手くいかなくて悩んでいたのですが、どうやらフォトンマッピングでは距離の2乗で減衰していくというのを忘れていました。
(今まで、点光源などは距離の2乗で減衰すると暗くなりすぎるので、物理ベースじゃなくていいやとその項を無視してたのです。)
で、いろいろ調べていたら、Vrayのフォトンマッピングのセッティングでは、シーンのスケールに合わせて調整するパラメータがある、って記事を見つけたので、自分のレンダラでもそのように設定してみました。
フォトンの密度推定をする際に収集したフォトンのうちの、一番外側のフォトンまでの距離を1/xにして計算するようなパラメータをつけて補正してみました。
まだ、いろいろ間違ってそうですが、今の状況↓。

あとは、球状に収集するんじゃなくて円盤状に収集するとか、円錐フィルタとかもやってみよう。