一、Phong模型数学原理
1.1 光照叠加公式
L = k a I a + k d I d max ( 0 , n ⋅ l ) + k s I s max ( 0 , r ⋅ v ) α L = k_a I_a + k_d I_d \max(0, \mathbf{n} \cdot \mathbf{l}) + k_s I_s \max(0, \mathbf{r} \cdot \mathbf{v})^\alpha L=kaIa+kdIdmax(0,n⋅l)+ksIsmax(0,r⋅v)α
- 符号说明:
- k a , k d , k s k_a, k_d, k_s ka,kd,ks:材质的环境/漫反射/高光系数(标量)
- I a , I d , I s I_a, I_d, I_s Ia,Id,Is:光源的环境/漫反射/高光强度(三通道向量或标量)
- n \mathbf{n} n:表面单位法线向量
- l \mathbf{l} l:单位光照方向向量(从表面指向光源)
- v \mathbf{v} v:单位视线方向向量(从表面指向观察点)
- r \mathbf{r} r:反射方向单位向量
- α \alpha α:高光锐度系数(值越大高光越集中)
1.2 核心分量数学推导
1.2.1 环境光(Ambient)
L a = k a ⋅ I a L_a = k_a \cdot I_a La=ka⋅Ia
- 特性:均匀照亮场景,与几何关系和光源方向无关
- 缺陷:易导致画面“过平”,需结合其他分量使用
1.2.2 漫反射(Lambert’s Cosine Law)
L d = k d ⋅ I d ⋅ max ( 0 , n ⋅ l ) L_d = k_d \cdot I_d \cdot \max(0, \mathbf{n} \cdot \mathbf{l}) Ld=kd⋅Id⋅max(0,n⋅l)
- 几何解释:
- n ⋅ l = cos θ \mathbf{n} \cdot \mathbf{l} = \cos\theta n⋅l=cosθ,其中 θ \theta θ 为入射角
- max ( 0 , ⋅ ) \max(0, \cdot) max(0,⋅) 确保背面无光照贡献
- 能量守恒:入射角越大,单位面积接收的光能越少
1.2.3 高光反射(Phong Specular)
L s = k s ⋅ I s ⋅ max ( 0 , v ⋅ r ) α L_s = k_s \cdot I_s \cdot \max(0, \mathbf{v} \cdot \mathbf{r})^\alpha Ls=ks⋅Is⋅max(0,v⋅r)α
- 反射向量计算:
r = 2 ( n ⋅ l ) n − l \mathbf{r} = 2(\mathbf{n} \cdot \mathbf{l})\mathbf{n} - \mathbf{l} r=2(n⋅l)n−l - Blinn-Phong优化:
- 半角向量 h = l + v ∥ l + v ∥ \mathbf{h} = \frac{\mathbf{l} + \mathbf{v}}{\|\mathbf{l} + \mathbf{v}\|} h=∥l+v∥l+v
- 高光项改写为 ( n ⋅ h ) α (\mathbf{n} \cdot \mathbf{h})^\alpha (n⋅h)α,计算效率更高
1.3 坐标系变换与关键推导
1.3.1 反射向量 r \mathbf{r} r 的严格推导
设入射方向 l \mathbf{l} l 为指向表面的单位向量,法线 n \mathbf{n} n 为单位向量:
- 将 l \mathbf{l} l 分解为法线分量和切平面分量:
l = ( n ⋅ l ) n + l ⊥ \mathbf{l} = (\mathbf{n} \cdot \mathbf{l})\mathbf{n} + \mathbf{l}_{\perp} l=(n⋅l)n+l⊥ - 反射方向 r \mathbf{r} r 的法线分量反向,切平面分量不变:
r = − ( n ⋅ l ) n + l ⊥ = l − 2 ( n ⋅ l ) n \mathbf{r} = -(\mathbf{n} \cdot \mathbf{l})\mathbf{n} + \mathbf{l}_{\perp} = \mathbf{l} - 2(\mathbf{n} \cdot \mathbf{l})\mathbf{n} r=−(n⋅l)n+l⊥=l−2(n⋅l)n
1.3.2 法线矩阵 N = ( M − 1 ) T \mathbf{N} = (\mathbf{M}^{-1})^T N=(M−1)T 的证明
设模型变换矩阵为 M \mathbf{M} M,切线向量 t \mathbf{t} t 变换后为 M t \mathbf{M}\mathbf{t} Mt,法线 n \mathbf{n} n 变换后为 N n \mathbf{N}\mathbf{n} Nn。需满足:
( N n ) ⋅ ( M t ) = 0 (\mathbf{N}\mathbf{n}) \cdot (\mathbf{M}\mathbf{t}) = 0 (Nn)⋅(Mt)=0
展开得:
n T N T M t = 0 \mathbf{n}^T \mathbf{N}^T \mathbf{M} \mathbf{t} = 0 nTNTMt=0
因原始法线与切线正交( n T t = 0 \mathbf{n}^T \mathbf{t} = 0 nTt=0),需有:
N T M = I ⟹ N = ( M − 1 ) T \mathbf{N}^T \mathbf{M} = \mathbf{I} \implies \mathbf{N} = (\mathbf{M}^{-1})^T NTM=I⟹N=(M−1)T
1.3.3 视线方向 v \mathbf{v} v 的计算
在视图坐标系中,设表面点坐标为 p \mathbf{p} p,则:
v = − p ∥ p ∥ \mathbf{v} = -\frac{\mathbf{p}}{\|\mathbf{p}\|} v=−∥p∥p