椿の日記

たぶんプログラムの話をします

球面調和関数の練習

f:id:tbk:20121229032125j:plain

やったこと

やっと時間取れたので実装してみました。上段はリファレンスとなる通常の照明計算、下段はそれを球面調和関数の係数空間で計算しました。左から順にそれぞれ次のような照明計算を行いました。

  • Lambertian BRDF * DirectionalLight
  • Phong BRDF * DirectionalLight
  • Lambertian BRDF * ConstantLight
  • Lambertian BRDF * (DirectionalLight + ConstantLight) + Phong BRDF * DirectionalLight

Lambertian BRDFやPhong BRDFの球面調和関数展開は「Lambertian Reflectance and Linear Subspaces(Basri and Jacobs)」にあるので、こちらを参考にします。平行光源はデルタ分布の光源と考えれば球面調和関数展開の係数が求まります。定数光源のほうはY_{00}だけ使って展開すればいいです。

疑問など

シェーダ内でY_{lm}(\omega)を必要とするのですが、どうやって与えるのが普通なんだろう。今回はシェーダ内で漸化式を解きながら計算したけど、どうも処理が重かった…。

あと、Phong BRDFでshininessが32とかになると、球面調和関数を次数15くらいまで伸ばさないとまともに近似できないらしい。次数15になると256項も必要になります。うーむ。