光照计算漫谈

光照计算在计算机图形学中是一个核心的概念,用于模拟光与物体表面相互作用的效果。一个基本的光照模型通常包括三个主要成分:环境光照(Ambient),漫反射光照(Diffuse),和镜面反射光照(Specular)。以下是这些成分的简化公式:

环境光照(Ambient Lighting):

glsl
复制
vec3 ambient = ambientLightIntensity * materialAmbientColor;
其中 ambientLightIntensity 是环境光的强度(通常是一个颜色向量),materialAmbientColor 是材质的环境光颜色。

漫反射光照(Diffuse Lighting):

glsl
复制
vec3 diffuse = lightIntensity * materialDiffuseColor * max(dot(normal, lightDir), 0.0);
其中 lightIntensity 是光源的强度(颜色向量),materialDiffuseColor 是材质的漫反射颜色,normal 是表面法线向量,lightDir 是从表面点指向光源的单位向量,dot 是点积运算,max 确保光照不会是负值(即光源在表面的背面时不产生光照)。

镜面反射光照(Specular Lighting):

glsl
复制
vec3 specular = lightIntensity * materialSpecularColor * pow(max(dot(viewDir, reflectDir), 0.0), shininess);
其中 materialSpecularColor 是材质的镜面反射颜色,viewDir 是从表面点指向观察者(相机)的单位向量,reflectDir 是光线入射方向关于法线的反射向量,shininess 是材质的光泽度(高光泽度产生更紧凑的高光),pow 是幂函数,用于模拟镜面高光的衰减。

将这三个成分结合起来,我们得到了一个基本的光照模型:

glsl
复制
vec3 finalColor = ambient + diffuse + specular;
这个模型称为Phong光照模型,它是计算机图形学中最基础的光照模型之一。在实际应用中,可能还会考虑其他因素,如阴影、光源衰减、光源颜色、材质属性等。

在更现代的图形管线中,特别是在使用基于物理的渲染(PBR)时,光照计算在基于物理的渲染(PBR)中,光照计算会更加复杂和真实,因为它基于物理原理来模拟光与材质的相互作用。PBR通常使用双向反射分布函数(Bidirectional Reflectance Distribution Function, BRDF)来计算漫反射和镜面反射。以下是PBR中使用的一些核心概念和计算公式:

微面体模型(Microfacet Model):
这个模型假设表面由很多微小的面(微面体)组成,每个微面体都可以反射光线。这个模型的核心是BRDF,它通常包括菲涅尔项(Fresnel)、几何遮蔽项(Geometry)、和粗糙度分布项(Roughness Distribution)。

菲涅尔项(Fresnel):
菲涅尔效应描述了表面反射光线的比例如何随着观察角度的变化而变化。Schlick的近似公式是一个常用的简化版本:

glsl
复制
vec3 F0 = mix(vec3(0.04), albedo, metalness);
vec3 fresnel = F0 + (1.0 - F0) * pow(1.0 - dot(viewDir, halfVec), 5.0);
其中 F0 是在垂直入射时的反射率,albedo 是材质的基础颜色,metalness 表示材质的金属度,viewDir 是观察方向,halfVec 是半角向量(光线方向和观察方向的中间向量)。

几何遮蔽项(Geometry / Geometric Occlusion):
几何遮蔽项考虑了微面体之间的相互遮挡,这影响了光线能够反射到观察者眼中的比例。一个常用的几何遮蔽函数是Schlick-GGX:

glsl
复制
float geometrySchlickGGX(float NdotV, float roughness) {
float a = roughness;
float k = (a * a) / 2.0;
float nom = NdotV;
float denom = NdotV * (1.0 - k) + k;
return nom / denom;
}

float geometrySmith(vec3 N, vec3 V, vec3 L, float roughness) {
float NdotV = max(dot(N, V), 0.0);
float NdotL = max(dot(N, L), 0.0);
float ggx1 = geometrySchlickGGX(NdotV, roughness);
float ggx2 = geometrySchlickGGX(NdotL, roughness);
return ggx1 * ggx2;
}
其中 N 是法线向量,V 是观察方向,L 是光源方向,roughness 是材质的粗糙度。

粗糙度分布项(Roughness Distribution / Normal Distribution Function, NDF):
粗糙度分布项描述了微面体的朝向分布,影响反射光的聚焦程度。GGX/Trowbridge-Reitz是一个流行的NDF,用于模拟粗糙表面:

glsl
复制
float distributionGGX(vec3 N, vec3 H, float roughness) {
float a = roughness * roughness;
float a2 = a * a;
float NdotH = max(dot(N, H), 0.0);
float NdotH2 = NdotH * NdotH;

float nom = a2;
float denom = (NdotH2 * (a2 - 1.0) + 1.0);
denom = PI * denom * denom;

return nom / denom;

}
其中 H 是半角向量,PI 是圆周率π的值。

将这些项结合起来,我们可以得到BRDF函数,用于计算PBR中的镜面反射:

glsl
复制
vec3 brdfSpecular(vec3 N, vec3 V, vec3 L, vec3 H, vec3 albedo, float metalness, float roughness) {
vec3 F = fresnelSchlick(max(dot(H, V), 0.0), F0);
float G = geometrySmith(N, V, L, roughness);
float D = distributionGGX(N, H, roughness);

return (F * G * D) / (4.0 * max(dot(N, V), 0.0) * max(dot(N, L), 0.0));

}
最后,漫反射部分在PBR中也有所不同,通常使用Lambertian或更复杂的模型,如Disney Diffuse或Oren-Nayar。在PBR中,漫反射通常与金属度有关,非金属材质有更明显的漫反射,而金属材质的漫反射较弱或不存在。

在PBR中,漫反射通常与金属度有关,非金属材质有更明显的漫反射,而金属材质的漫反射较弱或不存在。漫反射的计算可以使用Lambertian反射模型,这是一个简单但效果不错的模型,它假设光线被均匀地散射或反射。

glsl
复制
vec3 brdfDiffuse(vec3 albedo, float metalness) {
return albedo * (1.0 - metalness) / PI;
}
在这个模型中,albedo 是材质的基础颜色,metalness 是材质的金属度,PI 是圆周率π的值。金属度决定了漫反射的强度,对于金属材质(metalness 接近1),漫反射几乎为零;对于非金属材质(metalness 接近0),漫反射则占主导。

将漫反射和镜面反射结合起来,我们可以得到最终的PBR光照模型:

glsl
复制
vec3 calculateFinalColor(vec3 N, vec3 V, vec3 L, vec3 albedo, float metalness, float roughness) {
vec3 H = normalize(V + L);
vec3 radiance = vec3(1.0); // 假设一个白色光源

// 计算漫反射和镜面反射
vec3 F0 = mix(vec3(0.04), albedo, metalness);
vec3 diffuse = brdfDiffuse(albedo, metalness);
vec3 specular = brdfSpecular(N, V, L, H, albedo, metalness, roughness) * radiance;

// 计算最终颜色
vec3 color = (diffuse + specular) * max(dot(N, L), 0.0);

return color;

}
在这个函数中,N 是法线向量,V 是观察方向,L 是光源方向,albedo 是材质的基础颜色,metalness 是材质的金属度,roughness 是材质的粗糙度,radiance 是光源的辐射亮度。

这个模型可以产生非常真实的渲染效果,因为它基于物理原理。

我们已经讨论了PBR中的漫反射和镜面反射,以及如何将它们结合起来计算最终的颜色。现在,让我们谈谈环境光遮蔽(Ambient Occlusion, AO)和基于图像的照明(Image-Based Lighting, IBL)这两个在PBR工作流中也非常重要的概念。

环境光遮蔽(Ambient Occlusion, AO):
环境光遮蔽是一种技术,用于在没有直接光照的情况下模拟局部阴影效果。它基于这样的观察:在凹角或紧密空间中,环境光很难均匀到达,因此这些区域应该更暗。AO可以通过预计算(如烘焙到纹理中)或实时算法(如SSAO,即屏幕空间环境光遮蔽)来实现。在PBR中,AO通常作为一个因子应用于最终的漫反射颜色上,减少环境光的影响。

基于图像的照明(Image-Based Lighting, IBL):
IBL是一种技术,它使用环境贴图(通常是高动态范围图像,HDR)来模拟复杂环境中的光照。这种方法可以捕捉到环境中的全局光照效果,包括反射和折射。在PBR中,IBL通常分为两个部分处理:

漫反射IBL:
通过预计算的环境贴图(如立方体贴图)来模拟环境中的漫反射光。这通常通过预滤波的立方体贴图实现,该贴图存储了环境中各个方向上的平均光照。

镜面IBL:
镜面IBL使用同样的环境贴图,但是它会根据材质的粗糙度来选择不同级别的模糊程度。粗糙的材质会从更模糊的立方体贴图级别中采样,以模拟粗糙表面上的宽散射反射。这通常通过预计算的mipmaps来实现,每个mipmap级别代表不同的模糊程度。

将这些技术结合起来,我们可以得到一个非常全面的PBR光照模型,它不仅考虑了直接光照,也考虑了间接光照的影响。在实际应用中,这意味着物体不仅会受到直接光源的照射,还会受到周围环境的光线影响,这些光线可能来自于其他表面的反射或散射。

在实现IBL时,通常会有两个主要步骤:

预计算环境贴图:
这个步骤通常在资源的预处理阶段完成。环境贴图(通常是HDR环境贴图)会被转换成立方体贴图,并且对每个mipmap级别进行模糊处理,以模拟不同粗糙度级别的反射。这个过程称为立方体贴图的预滤波。

实时渲染时的IBL采样:
在渲染阶段,根据材质的粗糙度和反射方向,从预滤波的立方体贴图中采样,以计算镜面反射。同时,从漫反射的立方体贴图中采样,以获得环境中的间接漫反射光。

这样,最终的渲染结果会更加真实和动态,因为它不仅反映了直接光源的效果,还包括了环境中所有复杂光照的贡献。这对于创建更加沉浸式和真实感的场景至关重要。

在实际的渲染管线中,这些计算可能会非常复杂,并且需要优化以保持实时渲染的性能。例如,可以使用预计算的辐射度贴图(irradiance map)来快速近似漫反射IBL,而镜面反射IBL则可以通过粗糙度依赖的mipmap级别来优化性能。这些技术的结合使得PBR成为了现代游戏和视觉效果行业的标准。

为了进一步提高性能,开发者可能会采用以下策略:

分离预计算:将尽可能多的计算工作移到预计算阶段,这样在实时渲染时就可以减少计算负担。例如,环境贴图的预滤波和辐射度贴图的生成通常在资源的预处理阶段完成。

使用近似和简化模型:例如,可以使用简化的反射方程或者基于查找表(LUT)的方法来近似复杂的BRDF计算。

延迟渲染和前向+渲染:这些渲染技术可以帮助更有效地处理场景中的光照和材质,尤其是在有大量光源的情况下。

屏幕空间技术:例如屏幕空间反射(SSR)和屏幕空间环境光遮蔽(SSAO)可以提供更好的性能,同时仍然保持较高的视觉质量。

动态级别细节(LOD):根据物体与摄像机的距离,动态调整物体的细节级别,以减少渲染负担。

使用计算着色器和多线程:利用现代GPU的并行处理能力,通过计算着色器进行一些独立的计算任务,以及在CPU上使用多线程来准备渲染数据。

通过这些方法,PBR可以在保持视觉质量的同时,实现实时渲染。这就是为什么PBR在游戏和电影行业中如此流行:它提供了一种平衡性能和视觉真实性的有效方式。

总结一下,PBR是一个综合的渲染方法,它结合了物理正确的光照模型、高级的材质属性(如金属度和粗糙度)、环境光遮蔽、以及基于图像的照明技术,来创建出逼真的数字场景。这种方法的核心在于模拟光与物质相互作用的真实物理规律,从而在各种光照条件下都能产生一致且可信的结果。

环境光的强度乘以材质的环境光颜色,这个计算的作用是模拟在现实世界中,物体因为周围环境的光线而接收到的间接光照。在现实世界中,光线不仅直接从光源发出照射物体,还会反射在其他表面,如墙壁、地面和周围物体上,然后再照射到物体上,这就是所谓的间接光照或全局照明

在计算机图形学中,环境光通常被用来近似这种间接光照的效果,因为真实的全局照明计算非常复杂和计算密集。通过简单地将环境光的强度与材质的环境光颜色相乘,可以在不需要复杂计算的情况下,为场景中的每个物体提供一个基础的光照,确保没有任何直接光照时,物体仍然可见,从而增加场景的真实感。

这种方法不考虑物体的具体位置和形状,因此它不能模拟阴影或者光线的方向性,但它是一种计算上非常高效的方式,可以为场景提供一个基本的光照效果。在更高级的渲染技术中,如PBR,环境光遮蔽(Ambient Occlusion, AO)和基于图像的照明(Image-Based Lighting, IBL)会被用来增强环境光的效果,使其更加真实和具有方向性。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

你一身傲骨怎能输

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值