サンプルパストレーサーに鏡面反射と屈折を組み込んでみる

2009-07-20

レイトレーサーを作るシリーズ:syoyoさんのパストレーサーに鏡面反射と屈折を組み込んでみる。

視線が物体に当たったとき、サイコロを振って鏡面反射するか屈折するか拡散反射かを振り分ける(ロシアンルーレット)。 それ以前に法線と視線が同じ方向だったら、物体内部から出て行く光だとして屈折計算をする:

if (ray.dir.dot(isect.n) < 0) {
float r = random(1.0);
r -= isect.material.reflection;
if (r < 0) {
return calc_reflection(isect.p, isect.n, ray.dir, depth);
}
r -= isect.material.refraction;
if (r < 0) {
return calc_refraction(isect.p, isect.n, ray.dir, depth, 1.0, isect.material.refractive_index);
}
return calc_diffuse(isect, depth);
} else {
return calc_refraction(isect.p, isect.n.neg(), ray.dir, depth, isect.material.refractive_index, 1.0);
}

結果: Path tracer with reflection/refraction

おお、ノイジーだけどそれっぽい!集光模様も出てる!

  • 今回の設定
    • 2x2サブサンプリング、1レイあたり128パス、再帰は16段まで(反射や屈折は除く)
    • 死ぬほど重い
      • 元のパストレーサーでは、視線が何とも当たらなければ空のスカイライトで計算が打ち切られるのである程度早く収束するようだけど、コーネルボックスみたいに全体が囲まれているシーンだと光源にたどり着くまで計算するので時間がかかる
      • 光源にたどり着けなかったら結局黒になっちゃうので、最大の再帰回数はある程度大きく取らないとまずい
      • 光源にぶつかったら計算を打ち切るようにしてみた
    • マテリアルカラーを1.0にすると光の強さが減衰しないようにみえるので、0.8にしてみる
    • 光源は単位はなにか知らないけど10とか強い値にしてるのに、全体的に暗い。計算はあっているのか?トーンマッピングしたらそれっぽくなるか?
    • カラーブリーディングしすぎな気が…
  • Cornell box images by Henrik Wann Jensen 結果画面はここを参考にすること、やっぱ全然違う気がする…
  • 元ソースが綺麗でコンパクトだからいじりやすくてイイ!