ゲームグラフィックス特論
第10回 環境による照明

2

周囲の光による陰影
環境光

3

任意光源の放射測定• 𝐥𝐥 方向の微小立体角 𝑑𝑑𝜔𝜔𝑖𝑖 の放射輝度（接空間 𝐭𝐭, 𝐛𝐛, 𝐧𝐧）

𝑑𝑑𝑑𝑑
𝐿𝐿𝑖𝑖 𝐥𝐥 =𝑑𝑑𝜔𝜔𝑖𝑖 cos 𝜃𝜃𝑖𝑖
• 物体表面上のこの光源による放射照度
𝑑𝑑𝑑𝑑 = 𝐿𝐿𝑖𝑖 𝐥𝐥 𝑑𝑑𝜔𝜔𝑖𝑖 cos 𝜃𝜃𝑖𝑖

• したがって，物体表面上の天球全体からの放射照度は天空上の放射輝度に入射角の余弦をかけたものの総和

半球 Ω の範囲ではcos 𝜃𝜃𝑖𝑖 は負にならない

𝐸𝐸 = � 𝐿𝐿𝑖𝑖 𝐥𝐥 𝑑𝑑𝜔𝜔𝑖𝑖 cos 𝜃𝜃𝑖𝑖
Ωnθi
Ω

ldωi

4

放射輝度
• BRDFの 定義

𝑑𝑑𝐿𝐿𝑜𝑜 𝐯𝐯
𝑓𝑓 𝐥𝐥, 𝐯𝐯 =, 𝑑𝑑𝑑𝑑 = 𝐿𝐿𝑖𝑖 𝐥𝐥 𝑑𝑑𝜔𝜔𝑖𝑖 cos 𝜃𝜃𝑖𝑖𝑑𝑑𝑑𝑑 𝐥𝐥l• 𝐯𝐯 方向への放射輝度 𝐿𝐿𝑜𝑜 𝐯𝐯 は𝐿𝐿𝑜𝑜 𝐯𝐯 = � 𝑓𝑓 𝐥𝐥, 𝐯𝐯 ⨂𝐿𝐿𝑖𝑖 𝐥𝐥 cos 𝜃𝜃𝑖𝑖 𝑑𝑑𝜔𝜔𝑖𝑖• 極座標で表せば
2𝜋𝜋𝐿𝐿𝑜𝑜 𝜃𝜃𝑜𝑜 , 𝜙𝜙𝑜𝑜 = �𝜋𝜋2

�𝜙𝜙𝑖𝑖 =0 𝜃𝜃𝑖𝑖 =0Ωnθoθi

φφo φit𝑓𝑓 𝜃𝜃𝑖𝑖 , 𝜙𝜙𝑖𝑖 , 𝜃𝜃𝑜𝑜 , 𝜙𝜙𝑜𝑜 ⨂𝐿𝐿𝑖𝑖 𝜃𝜃𝑖𝑖 , 𝜙𝜙𝑖𝑖 cos 𝜃𝜃𝑖𝑖 sin 𝜃𝜃𝑖𝑖 𝑑𝑑𝜃𝜃𝑖𝑖 𝑑𝑑𝜙𝜙𝑖𝑖
𝑑𝑑𝜙𝜙𝑖𝑖 は sin 𝜃𝜃𝑖𝑖 に比例するv𝑑𝑑𝜔𝜔𝑖𝑖 = sin 𝜃𝜃𝑖𝑖 𝑑𝑑𝜃𝜃𝑖𝑖 𝑑𝑑𝜙𝜙𝑖𝑖

5面光源• 天球の一部を切り取ったもの

ωL nELlLvLL面光源n定数とみなす

θi

L

点光源／平行光線

𝐿𝐿𝑜𝑜 𝐯𝐯 = � 𝑓𝑓 𝐥𝐥, 𝐯𝐯 ⨂𝐿𝐿𝐿𝐿 cos 𝜃𝜃𝑖𝑖 𝑑𝑑𝜔𝜔𝑖𝑖 ≈ 𝐸𝐸𝐿𝐿 cos 𝜃𝜃𝑖𝑖𝐿𝐿
𝝎𝝎𝑳𝑳

面光源の面積v

この近似誤差は光源が小さいか物体表面が粗ければ小さくなる

6

完全拡散反射面• 完全拡散反射面の放射輝度は放射照度に比例する

cdiff は面の拡散反射色定数• したがって，この放射照度は完全拡散反射面の放射照度は入射光の放射照度に入射角の余弦をかけたもの
Lambert の余弦法則

7ベクトル放射照度

Θ は p を囲む球全体
点 𝐩𝐩 は様々な形や大きさや放射輝度分布の光源に囲まれている: p から l 方向の放射輝度

これを 𝐞𝐞 の方向から到来する光に集約する（ベクトル放射照度）ベクトル8ベクトル放射照度による放射照度

正味の放射照度
裏面に光が当たらなければ表面 (𝐧𝐧 の方向) の放射照度から裏面の放射照度を引いたもの

9ベクトル放射照度と波長• ベクトル放射照度は単一の波長が対象• 異なる色の光源が与えられたとき• 集約したベクトルは波長ごとに異なる方向を向く• 全ての光源が同じスペクトル分布のとき

rL• ベクトルは全て同じ方向を向く• したがってpL
𝑐𝑐𝐿𝐿 は光源色

rlp• 中心 𝐩𝐩𝐿𝐿 半径 𝑟𝑟𝐿𝐿 の球体の光源 (表面の放射輝度 𝐿𝐿𝐿𝐿 )放射照度は光源の半径の二乗に比例し距離の二乗に反比例する

10

環境光
• 間接光の放射輝度が到来方向に対して不変であるとみなす• 放射輝度は定数で表される→ 𝐿𝐿𝐴𝐴

• 間接光がないシーンは全然リアルではない• 物体の光が当たらない部分は完全に黒LA

11

環境光
環境光なし

環境光あり

12

環境光による放射輝度• 放射輝度は面の法線 𝐧𝐧 や視線 𝐯𝐯 に無関係

𝜋𝜋

• シェーディングの際はこれを直接光の成分に加える

13

環境光による放射輝度• 任意の BRDF に対して環境光

光源• 環境光反射率 𝑅𝑅𝐴𝐴 𝐯𝐯
環境光も BRDFの影響を受ける

環境光の反射率は視点に依存する14

環境光による放射輝度• 環境光の反射係数 𝑐𝑐𝑎𝑎𝑎𝑎𝑎𝑎

完全拡散反射面

そのほかの場合

拡散反射色 cdiff と等しい
拡散反射色 cdiff
鏡面反射色 cspec

重み付け和

15

環境マッピング
周囲の光源のテクスチャによる表現

16

環境マッピング (Environment Mapping)• 環境（周囲の情景）をテクスチャとしてマッピングする• 曲面への映り込みを擬似的に表現する• 反射マッピング (Reflection Mapping)• 手順の概略• 視点から発射された視線が物体表面上で反射した方向を求める• 反射方向に置かれたテクスチャを標本化して，物体表面上の反射点の陰影計算に使う• 手法• Blinn と Newell の方法• Sphere Mapping• Cube Mapping• Dual Paraboloid Mapping

17

Environment Mapping の例テクスチャnv

r

ポットの注ぎ口が写り込んでいない18

Blinn と Newell の方法• 反射ベクトルを極座標に変換する• 極座標のパラメータを使ってテクスチャを標本化• テクスチャ画像は「正距円筒図法」

19

バーテックスシェーダ#version 410
in vec4 pv;// 頂点位置
in vec3 nv;// 頂点の法線ベクトル
uniform mat4 mw;// モデルビュー変換行列
uniform mat3 mg;// 法線変換行列
out vec2 t;// テクスチャ座標
const float PI = 3.141593;
reflect() はベクトル v の法線 n に対する正反射方向を求める組み込み関数

void main(void){
vec3 v = -normalize(mw * pv).xyz;// 視線ベクトル
vec3 r = reflect(v, normalize(mg * nv)); // 視線の正反射方向float s = -acos(r.z) / PI;
float t = atan(r.y, r.x) * 0.5 / PI + 0.5;
t = vec2(s, t);…
GLSL の atan() は C 言語の atan2() に相当する

20

Sphere Mapping• 球体への映り込みを環境マップに使う• テクスチャは球状の鏡を撮影して得られる• カメラが映りこんでしまう• 視線方向から見た映り込みのテクスチャを使用する• 視線方向を変更できない

テクスチャ画像

球に環境マッピング

ポットに環境マッピング

21

Sphere Mapping の基底行列
v = (vx,vx,vx)

u = (ux,ux,ux)

Sphere Mapping の基底行列

ynh = (hx,hx,hx)

v: 視線方向y'O

rxn'zv'z 軸が視線 v 方向を向くよう物体を回転したときの法線ベクトルを求める

z'

22

反射方向とテクスチャ座標
y'rn' = (n'x, n'y, n'z)

視線ベクトル(n'x, n'y)hv

O

反射ベクトルv' = (0, 0, 1)z'

したがって中間ベクトルは

𝐫𝐫 方向に見えるテクスチャが (𝑛𝑛′ 𝑥𝑥 , 𝑛𝑛𝑛𝑦𝑦 ) の位置に映りこんで見える23

法線ベクトルとテクスチャ座標の対応

1y'v
1n'yv
n'-1

O-1

1n'xx'

Ou1 u
法線ベクトルの xy 座標 𝑛𝑛′ 𝑥𝑥 , 𝑛𝑛′ 𝑦𝑦をテクスチャ座標に使えばよい

24

バーテックスシェーダ#version 410
in vec4 pv;
in vec3 nv;
uniform mat4 mw;
uniform mat3 mg;
uniform mat3 ms;out vec2 t;// 頂点位置// 頂点の法線ベクトル// モデルビュー変換行列// 法線変換行列// Sphere Mapping の基底行列// テクスチャ座標

void main(void){t = normalize(ms * nv).xy * 0.5 + 0.5;…
Sphere Mapping の基底行列 ms は
法線変換行列 mg と同じなので ms → mg として構わない25

Cubic Environment Mapping• 立方体に環境マップを貼り付ける• テクスチャ画像は６枚使う• 反射方向にどのテクスチャがあるか判別する26

テクスチャの選択

どのテクスチャを標本化するかを反射ベクトルの方向で決定する27

メインプログラム
glTexImage2D(GL_TEXTURE_CUBE_MAP_NEGATIVE_X, 0, internal,WIDTH, HEIGHT, 0, GL_RGB, GL_UNSIGNED_BYTE, textureNX);
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0, internal,
WIDTH, HEIGHT, 0, GL_RGB, GL_UNSIGNED_BYTE, texturePX);
glTexImage2D(GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, 0, internal,WIDTH, HEIGHT, 0, GL_RGB, GL_UNSIGNED_BYTE, textureNY);
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_Y, 0, internal,WIDTH, HEIGHT, 0, GL_RGB, GL_UNSIGNED_BYTE, texturePY);
glTexImage2D(GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, 0, internal,WIDTH, HEIGHT, 0, GL_RGB, GL_UNSIGNED_BYTE, textureNZ);
glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_Z, 0, internal,
WIDTH, HEIGHT, 0, GL_RGB, GL_UNSIGNED_BYTE, texturePZ);
internal は内部フォーマット, WIDTH, HEIGHT は読み込むテクスチャの幅と高さ,GL_RGB と GL_UNSIGNED_BYTE は読み込みテクスチャのデータ形式

28

フラグメントシェーダ#version 410…
uniform samplerCube cubemap;…
in vec3 r;…

// Cube Map の sampler// 反射方向ベクトルはバーテックスシェーダで計算しておく

void main(void){
vec4 rcolor = texture(cubemap, r); // 反射方向の色…
r を正規化する必要はない

29

Dual Paraboloid Mapping• 放物面への映り込みを環境マップに使う• ２枚のテクスチャを使う• 近似的に魚眼レンズで撮影した画像が使用できる• 魚眼レンズを使えばカメラが映り込むことはない11.500.25

θ

110.5

y = x2

放物面（断面）-0.4

２つの放物面鏡への環境の映り込み

-0.2

0.2
-0.5
-1-1-1.5

d0.4

30

Paraboloid Mapping のテクスチャ座標• 反射ベクトルのとき
で表側のテクスチャを標本化するのとき
で裏側のテクスチャを標本化する31

２枚のテクスチャの合成

32

OpenGL の固定機能を使った実装• 頂点のテクスチャ座標として 𝑟𝑟𝑥𝑥

𝑟𝑟𝑦𝑦𝑟𝑟𝑧𝑧

1 𝑇𝑇 を設定する• テクスチャ変換行列に前記の行列を設定する• 表と裏の両方のテクスチャに対して標本値を求める• マルチテクスチャを使って，これらの標本値の合計をマッピングする• 一方のテクスチャの標本点が範囲内にあれば，もう一方のテクスチャは範囲外が標本化される• 範囲外の標本値を０（黒）にしておけば，常にどちらか一方だけのテクスチャの標本値が得られる• 実はこれはうまくいかない ⇒ アルファ値によるデカールなどを用いる• これにより多角形のテクスチャ座標が表と裏の両方のテクスチャにまたがっていても正しくマッピングされる

33

GLSL による実装 (フラグメントシェーダ)#version 410…
uniform sampler2D front; // 二重放物面マップの表のテクスチャ
uniform sampler2D back; // 二重放物面マップの裏のテクスチャ…
in vec3 r;…

// 反射方向ベクトルはバーテックスシェーダで計算しておく

main(){
vec2 uv = r.xy * 0.5 / (1.0 + abs(r.z)) + 0.5;
vec4 rcolor = texture(r.z >= 0.0 ? front : back, uv);…

34

Environment Map Bump Mapping
バンプマッピング

環境マップバンプマッピング

35

環境マッピングによる陰影計算
光源領域のテクスチャによる表現

36

ハイライトマッピング• 環境マッピングを使ってハイライトを表現する• 視線をZ軸 (0,0,1) と一致させた時の光線ベクトルを求める• −1 ≤ 𝑥𝑥, 𝑦𝑦 ≤ 1 の領域上で 𝑧𝑧 2 = 1 − 𝑥𝑥 2 − 𝑦𝑦 2を求める• 𝑧𝑧 > 0 なら (𝑥𝑥, 𝑦𝑦, 𝑧𝑧) を法線ベクトルとして鏡面反射光強度を求める• それをテクスチャの (0.5𝑥𝑥 + 0.5, 0.5𝑦𝑦 + 0.5)の位置に格納する• Sphere Mapping によりこのテクスチャを拡散反射光強度に加算

37

テクスチャなのでハイライトの形は自由に設定できる

38

環境マップフィルタリング• 環境マップは映り込みの表現が可能• つややかな面や拡散面の陰影に応用する• 反射光は天空光の分布とBRDFの畳み込み

完全な鏡面反射（映り込み）

鏡面反射光の分布
Shininess を映り込みに反映する

環境マップ
フィルタリング拡散反射光の分布

39

フィルタリングの方法• 環境マップを均一にぼかす• 本当は場所によってぼけ方が異なる• 目は寛容なので全体的な効果の方が重要40

環境マップフィルタリングの結果
元の環境マップ

環境マップをぼかした場合

41

完全拡散反射面の天空光による陰影
EL

Li(l)

n41lL θiL

nlvvΩ
点光源／平行光線

天空光

放射照度マップ

42

放射照度マップの作成
Ω: p の接空間の天空
n: p の法線ベクトルl: n に対して θi 回転した方向
Li(l) : 天空の l 方向の放射輝度
天空は p から十分遠いものとする

n の方向を向いた面の放射照度 En を次式で求める

この En を放射照度マップのn の方向に格納する

43

放射照度マッピング
アルベド

アルベド×(1 − 𝑅𝑅𝑠𝑠𝑠𝑠𝑠𝑠𝑠𝑠 )×放射照度マップ
法線ベクトルでサンプリング

放射照度マッピング
放射照度マップ

結果

反射環境マップ+𝑅𝑅𝑠𝑠𝑠𝑠𝑠𝑠𝑠𝑠 ×反射環境マップ
反射ベクトルでサンプリング

44

放射照度マップと陰影の変化

45

Cube Map による放射照度マップ
環境マップ

放射照度マップ

本当はもっとボケていないといけない

46

放射照度環境マッピングによる陰影

DEAD OR ALIVE 3 (c) TECMO, LTD. Team NINJA 2001

47

Reflection Space Image Based Rendering
Cabral, Olano, Nemec (1999)

48

球面調和解析
放射照度マップの関数近似

49

放射照度マップの近似

放射照度分布𝐸𝐸𝑛𝑛

𝐸𝐸 𝑛𝑛

𝐸𝐸1 𝑛𝑛

𝐸𝐸3 𝑛𝑛

𝐸𝐸2 𝑛𝑛𝐸𝐸 𝑛𝑛 ≈ 𝑐𝑐1 𝐸𝐸1 𝑛𝑛 + 𝑐𝑐2 𝐸𝐸2 𝑛𝑛 + 𝑐𝑐3 𝐸𝐸3 𝑛𝑛関数の重みづけ和による近似

50

直交基底関数の重み付け和による近似
重み付けされた直交基底関数

51

正規直交基底正規直交基底52

直交基底関数• 内積

𝑓𝑓𝑖𝑖 𝑥𝑥 , 𝑓𝑓𝑗𝑗 𝑥𝑥= � 𝑓𝑓𝑖𝑖 𝑥𝑥 𝑓𝑓𝑗𝑗 𝑥𝑥 𝑑𝑑𝑑𝑑

n： 中心から向かう方向dω： 単位球上の微小面積
Θ： 単位球全体• 空間的な関数では𝑓𝑓𝑖𝑖 𝐧𝐧 , 𝑓𝑓𝑗𝑗 𝐧𝐧= � 𝑓𝑓𝑖𝑖 𝐧𝐧 𝑓𝑓𝑗𝑗 𝐧𝐧 𝑑𝑑𝜔𝜔• 𝑓𝑓𝑖𝑖0=�1nΘ• 直交基底関数の性質, 𝑓𝑓𝑗𝑗𝑖𝑖 ≠ 𝑗𝑗
𝑖𝑖 = 𝑗𝑗

自分自身との内積は1，それ以外は 0 ⇒ 直交Θ

dω

53

直交関数基底関数による関数の近似• 近似しようとする関数 𝑓𝑓𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡 () と直交基底関数列 𝑓𝑓𝑗𝑗 () との内積

𝑘𝑘𝑗𝑗 = 𝑓𝑓𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡• より 𝑓𝑓𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡 () は次式で近似できる

𝑓𝑓𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡𝑡, 𝑓𝑓𝑗𝑗𝑛𝑛≈ � 𝑘𝑘𝑗𝑗 𝑓𝑓𝑗𝑗
𝑗𝑗=1

54

ルジャンドル陪関数• ルジャンドル多項式（ロドリゲスの公式）

𝑛𝑛: 次数 (degree)
𝑚𝑚: 位数 (order)|𝑥𝑥| ≤ 1, |𝑚𝑚| ≤ 𝑛𝑛, 𝑛𝑛 = 0, 1, 2, …

1𝑑𝑑𝑛𝑛
𝑃𝑃𝑛𝑛 𝑥𝑥 = 𝑛𝑛 � 𝑛𝑛 𝑥𝑥 2 − 1 𝑛𝑛
2 𝑛𝑛! 𝑑𝑑𝑑𝑑
: 多重階乗• ルジャンドル陪関数(一つ飛ばしの階乗)
𝑚𝑚 𝑑𝑑 𝑚𝑚
5 =5�3�1𝑃𝑃𝑛𝑛𝑚𝑚 𝑥𝑥 = −1 𝑚𝑚 1 − 𝑥𝑥 2 2𝑃𝑃𝑥𝑥
𝑛𝑛
6 =6�4�2𝑚𝑚
𝑑𝑑𝑑𝑑
• 漸化式
𝑚𝑚
𝑚𝑚
𝑛𝑛 − 𝑚𝑚 𝑃𝑃𝑛𝑛𝑚𝑚 𝑥𝑥 = 𝑥𝑥 2𝑛𝑛 − 1 𝑃𝑃𝑛𝑛−1𝑥𝑥 − 𝑛𝑛 + 𝑚𝑚 − 1 𝑃𝑃𝑛𝑛−2𝑥𝑥
𝑃𝑃𝑚𝑚𝑚𝑚 𝑥𝑥 = −1 𝑚𝑚 2𝑚𝑚 − 1𝑚𝑚
𝑃𝑃𝑚𝑚+1𝑥𝑥 = 𝑥𝑥 2𝑚𝑚 + 1 𝑃𝑃𝑚𝑚𝑚𝑚 𝑥𝑥

𝑚𝑚1 − 𝑥𝑥 2 2𝑚𝑚 = 0𝑃𝑃00 𝑥𝑥 = 1𝑃𝑃10 𝑥𝑥 = 𝑥𝑥

55𝑚𝑚
ルジャンドル陪関数 𝑃𝑃𝑛𝑛 𝑥𝑥
𝒍𝒍 = 0𝑚𝑚 = 0𝑃𝑃00 𝑥𝑥 = 1𝑚𝑚 = 1

𝒍𝒍 = 1𝑃𝑃10 𝑥𝑥 = 𝑥𝑥

𝑃𝑃11 𝑥𝑥 = − 1 − 𝑥𝑥 2

𝒍𝒍 = 223𝑥𝑥−10𝑃𝑃2 𝑥𝑥 =2𝑃𝑃21 𝑥𝑥= −3𝑥𝑥𝑚𝑚 = 21 − 𝑥𝑥 2

𝑃𝑃22 𝑥𝑥 = 3 1 − 𝑥𝑥 2

56

𝑃𝑃𝑙𝑙𝑚𝑚 𝑥𝑥 の形

57

ルジャンドル陪関数の性質+10𝑛𝑛 + 𝑚𝑚 !
� 𝑃𝑃𝑖𝑖𝑚𝑚 𝑥𝑥 𝑃𝑃𝑗𝑗𝑚𝑚 𝑥𝑥 𝑑𝑑𝑑𝑑 = � 2
�−12𝑛𝑛 + 1 𝑛𝑛 − 𝑚𝑚 !
直交𝑖𝑖 ≠ 𝑗𝑗𝑖𝑖 = 𝑗𝑗 = 𝑛𝑛

58

球面調和関数𝑌𝑌𝑙𝑙𝑚𝑚 𝜃𝜃, 𝜙𝜙

緯度方向=𝑚𝑚+ 𝑚𝑚−1 2 𝐾𝐾𝑙𝑙𝑚𝑚 𝑒𝑒 𝑖𝑖𝑖𝑖𝜙𝜙 𝑃𝑃𝑙𝑙 𝑚𝑚

経度方向𝐾𝐾𝑙𝑙𝑚𝑚 =cos 𝜃𝜃

2𝑙𝑙 + 1 𝑙𝑙 − 𝑚𝑚 !
�𝑙𝑙 + 𝑚𝑚 !
4𝜋𝜋𝐧𝐧 = 𝑥𝑥, 𝑦𝑦, 𝑧𝑧 = sin 𝜃𝜃 cos 𝜙𝜙 , sin 𝜃𝜃 sin 𝜙𝜙, cos 𝜃𝜃59

球面調和関数表 (Wikipedia に載ってた)
𝑥𝑥 = 𝑟𝑟 sin 𝜃𝜃 cos 𝜑𝜑𝑦𝑦 = 𝑟𝑟 sin 𝜃𝜃 sin 𝜑𝜑𝑧𝑧 = 𝑟𝑟 cos 𝜃𝜃60𝑚𝑚
𝑌𝑌𝑙𝑙 𝜃𝜃, 𝜙𝜙の実部(macOS 標準添付の Grapher で描いた)

61

球面調和関数の性質+𝜋𝜋�−𝜋𝜋=�+1�𝑚𝑚′𝑚𝑚
𝑌𝑌𝑙𝑙 𝜃𝜃, 𝜙𝜙 𝑌𝑌𝑙𝑙′ 𝜃𝜃, 𝜙𝜙 𝑑𝑑 cos 𝜃𝜃 𝑑𝑑𝜙𝜙−1+𝜋𝜋 𝜋𝜋−𝜋𝜋𝑚𝑚′𝑙𝑙 ′� 𝑌𝑌𝑙𝑙𝑚𝑚 𝜃𝜃, 𝜙𝜙 𝑌𝑌01𝜃𝜃, 𝜙𝜙 sin 𝜃𝜃 𝑑𝑑𝜃𝜃𝑑𝑑𝜙𝜙 = �0直交𝑙𝑙 = 𝑙𝑙 ′ , 𝑚𝑚 = 𝑚𝑚𝑚
それ以外

62

球面調和関数展開
light probe 画像の場合∞+𝑙𝑙𝑓𝑓 𝜃𝜃, 𝜙𝜙 = � � 𝑐𝑐𝑙𝑙𝑚𝑚 𝑌𝑌𝑙𝑙𝑚𝑚 𝜃𝜃, 𝜙𝜙
𝑙𝑙=0 𝑚𝑚=−𝑙𝑙+𝜋𝜋𝑐𝑐𝑙𝑙𝑚𝑚 = �+1

� 𝑓𝑓 𝜃𝜃, 𝜙𝜙 𝑌𝑌𝑙𝑙𝑚𝑚 𝜃𝜃, 𝜙𝜙 𝑑𝑑 cos 𝜃𝜃 𝑑𝑑𝜙𝜙−𝜋𝜋 −1+𝜋𝜋 𝜋𝜋=�−𝜋𝜋� 𝑓𝑓 𝜃𝜃, 𝜙𝜙 𝑌𝑌𝑙𝑙𝑚𝑚 𝜃𝜃, 𝜙𝜙 sin 𝜃𝜃 𝑑𝑑𝜃𝜃𝑑𝑑𝜙𝜙
0sin 𝜃𝜃 = 𝑥𝑥 2 + 𝑦𝑦 2cos 𝜃𝜃 = 𝑧𝑧 = 1 − 𝑥𝑥 2 − 𝑦𝑦 2(x, y)φ

63

球面調和関数写像

Robin Green, “Spherical Harmonic Lighting: The Gritty Details”

64

作例

Robin Green, “Spherical Harmonic Lighting: The Gritty Details”

65

放射照度マップの球面調和関数近似• 環境からの放射照度の総和 𝐸𝐸

𝐸𝐸 = 𝑘𝑘1 𝑐𝑐22 𝑥𝑥 2 − 𝑦𝑦 2 + 𝑘𝑘3 𝑐𝑐20 𝑧𝑧 2 + 𝑘𝑘4 𝑐𝑐00 − 𝑘𝑘5 𝑐𝑐20+2𝑘𝑘1 𝑐𝑐2−2 𝑥𝑥𝑥𝑥 + 𝑐𝑐21 𝑥𝑥𝑧𝑧 + 𝑐𝑐2−1 𝑦𝑦𝑦𝑦+2𝑘𝑘2 𝑐𝑐11 𝑥𝑥 + 𝑐𝑐1−1 𝑦𝑦 + 𝑐𝑐10 𝑧𝑧• ここで (𝑥𝑥, 𝑦𝑦, 𝑧𝑧) は法線ベクトル 𝐧𝐧

𝐧𝐧 = 𝑥𝑥, 𝑦𝑦, 𝑧𝑧 = sin 𝜃𝜃 cos 𝜙𝜙 , sin 𝜃𝜃 sin 𝜙𝜙, cos 𝜃𝜃• 拡散反射光強度 𝐼𝐼𝑑𝑑𝑑𝑑𝑑𝑑𝑑𝑑

𝐼𝐼𝑑𝑑𝑑𝑑𝑑𝑑𝑑𝑑 = 𝐾𝐾𝑑𝑑𝑑𝑑𝑑𝑑𝑑𝑑 ⨂𝐸𝐸 𝑓𝑓𝑠𝑠𝑠𝑠𝑠𝑠𝑠𝑠𝑠𝑠

𝐸𝐸 は非常に大きな値になることがあるため，HDR（ダイナミックレンジ）レンダリングが行えない（明度値に上限がある）場合は，適当なスケールファクタ 𝑓𝑓𝑠𝑠𝑠𝑠𝑠𝑠𝑠𝑠𝑠𝑠 をかける．

Ramamoorthi, R., & Hanrahan, P. (2001, August). An efficient representation for irradiance environment maps. In
Proceedings of the 28th annual conference on Computer graphics and interactive techniques (pp. 497-500).

66

小テスト－環境による照明

Moodle の小テストに解答してください67

宿題• 環境の光源による放射照度の球面調和解析による陰影付けを実装してください．

• 次のプログラムは完全拡散反射面の Lambert の余弦法則による拡散反射光による陰影を付けた図形を表示します．
• https://github.com/tokoik/ggsample10• これを環境の放射照度マップの球面調和関数による近似を用いた陰影付けに変更してください．
• 球面調和係数は uniform 変数の配列 sh に格納されています．
• sh[0] = 𝑐𝑐00 , sh[1] = 𝑐𝑐1−1 , sh[2] = 𝑐𝑐10 , sh[3] = 𝑐𝑐11 ,sh[4] = 𝑐𝑐2−2 , sh[5] = 𝑐𝑐2−1 , sh[6] = 𝑐𝑐20 , sh[7] = 𝑐𝑐21 , sh[8] = 𝑐𝑐22

• 係数は1秒ごとに自動的に切り替わります．

• ggsample10.vert をアップロードしてください68

宿題プログラムの生成画像
Lambertの余弦法則による拡散反射光

環境の放射照度の球面調和関数近似