基于物理的渲染(2):渲染方程
基于物理的渲染(2):渲染方程
其中
5.1 双向反射分布函数(BRDF)
BRDF表示材质性质,用于描述表面反射和次表面反射,分别用作高光反射项和漫反射项。举例来说,如果一个平面拥有完全光滑的表面(比如镜面),那么对于所有的入射光线ωi(除了一束以外)而言BRDF函数都会返回0.0 ,只有一束与出射光线ωo拥有相同(被反射)角度的光线会得到1.0这个返回值。
Cook-Torrance BRDF模型既有漫反射项又有高光反射项,在实时渲染中最为常用:
其中,
c为表面颜色。Cook-Torrance 高光反射模型如下
其中包含三个函数,D表示法线分布函数(Normal Distribution Function),F表示菲涅尔方程(Fresnel Equation),和G表示几何函数(Geometry Function)。
5.2 法线分布函数
法线分布函数用于估算微平面中法线和半程向量一致的平面数量,Trowbridge-Reitz GGX公式:
其中h表示半程向量,a表示表面粗糙度。如下图所示,粗糙度越大,微平面半程向量越分散,表面更加灰暗。
5.3 菲涅尔方程
菲涅尔方程描述的是被反射的光线对比被折射的光线所占比例。当光线碰撞到一个表面时,菲涅尔方程会根据观察角度计算得到被反射的光线的比例。菲涅尔方程是个相当复杂的方程式,一般用Fresnel-Schlick近似法求得近似解:
其中
vec3 F0 = vec3(0.04); F0 = mix(F0, surfaceColor.rgb, metalness);
然后计算得到实际反射率:
vec3 fresnelSchlick(float cosTheta, vec3 F0) { return F0 + (1.0 - F0) * pow(1.0 - cosTheta, 5.0); }
5.4 几何函数
几何函数表示了微平面相互遮挡的比例,如下图所示分为两种情况:观察方向上的集合遮蔽和光线方向上的几何阴影。
我们可以用Smith函数将两部分放到一起:
材料的粗糙度越高,微平面相互遮蔽的概率越高,Schlick-GGX几何函数
其中k由粗糙度计算而来,直接光照和环境光照参数分别为:
glsl代码如下:
float GeometrySchlickGGX(float NdotV, float k) { float nom = NdotV; float denom = NdotV * (1.0 - k) + k; return nom / denom; } float GeometrySmith(vec3 N, vec3 V, vec3 L, float k) { float NdotV = max(dot(N, V), 0.0); float NdotL = max(dot(N, L), 0.0); float ggx1 = GeometrySchlickGGX(NdotV, k); // 视线方向的几何遮挡 float ggx2 = GeometrySchlickGGX(NdotL, k); // 光线方向的几何阴影 return ggx1 * ggx2; }
这样得到最终的渲染方程:
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· winform 绘制太阳,地球,月球 运作规律
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· AI 智能体引爆开源社区「GitHub 热点速览」
· 写一个简单的SQL生成工具