基于物理的渲染材质(PBR)
Author: Charley
PBR(Physically Based Rendering,基于物理的渲染)材质是LayaAir引擎中最常用的高品质材质类型。它通过模拟自然界的物理光照规律,使3D模型呈现出更加真实的质感,能够准确还原金属、木材、塑料、皮革等各种不同材料的外观特征。
一、PBR材质概述
Section titled “一、PBR材质概述”1.1 什么是PBR
Section titled “1.1 什么是PBR”PBR是一种基于物理规律的着色模型,其核心思想是通过物理上合理的方式来描述光线与材质表面的交互。与传统的光照模型(如Blinn-Phong)相比,PBR材质的优势在于:
- 物理正确性:遵循能量守恒定律,光照效果更加真实;
- 直观的参数:使用金属度、粗糙度等直观参数描述材质,美术调参更加方便;
- 环境一致性:材质在不同的光照环境下都能呈现合理的效果。
1.2 PBR材质类的继承关系
Section titled “1.2 PBR材质类的继承关系”在LayaAir引擎中,PBR材质的类继承关系为:
Material → PBRMaterial → PBRStandardMaterialPBRMaterial:PBR材质的基类,包含了PBR材质的通用属性(反照率、法线、遮蔽、自发光等);PBRStandardMaterial:PBR标准材质,在PBRMaterial基础上增加了金属度工作流相关属性。
在IDE中创建材质并选择PBR(Standard)Shader时,使用的就是 PBRStandardMaterial。
二、反照率(Albedo)
Section titled “二、反照率(Albedo)”反照率描述了材质表面的基础颜色,即物体本身的颜色(不包含光照信息)。
2.1 反照率颜色(albedoColor)
Section titled “2.1 反照率颜色(albedoColor)”反照率颜色定义了材质表面的固有颜色,是一个RGBA值。
(图2-1)
2.2 反照率贴图(albedoTexture)
Section titled “2.2 反照率贴图(albedoTexture)”反照率贴图用于提供逐像素的颜色信息,使材质表面呈现更丰富的细节。贴图颜色会与反照率颜色相乘。
(图2-2)
2.3 纹理平铺和偏移(tilingOffset)
Section titled “2.3 纹理平铺和偏移(tilingOffset)”控制纹理在模型表面的重复次数和偏移量。类型为 Vector4,其中:
- X、Y分量:纹理在U、V方向的重复次数(Tiling)
- Z、W分量:纹理在U、V方向的偏移量(Offset)
三、金属度与光滑度
Section titled “三、金属度与光滑度”金属度和光滑度是PBR材质的核心参数,它们共同决定了材质对光线的反射方式。
3.1 金属度(metallic)
Section titled “3.1 金属度(metallic)”金属度描述物体表面在多大程度上像金属。取值范围为0到1:
| 值 | 说明 |
|---|---|
| 0 | 非金属(绝缘体),如木头、塑料、皮革等 |
| 1 | 纯金属,如金、银、铁等 |
| 0~1 | 过渡值,用于模拟带有氧化层或涂层的金属 |
(图3-1)
3.2 光滑度(smoothness)
Section titled “3.2 光滑度(smoothness)”光滑度描述物体表面的光滑程度。取值范围为0到1:
| 值 | 说明 |
|---|---|
| 0 | 完全粗糙,漫反射为主,如未打磨的石头 |
| 1 | 完全光滑,镜面反射为主,如镜子 |
(图3-2)
注意:在某些PBR工作流中,使用”粗糙度”(Roughness)代替光滑度,两者是互补关系:
粗糙度 = 1 - 光滑度。
3.3 金属光滑度贴图(metallicGlossTexture)
Section titled “3.3 金属光滑度贴图(metallicGlossTexture)”金属光滑度贴图可以在一张纹理中同时提供金属度和光滑度信息,实现逐像素的精确控制。
3.4 光滑度数据源(smoothnessSource)
Section titled “3.4 光滑度数据源(smoothnessSource)”smoothnessSource 属性控制光滑度数据的来源,类型为 PBRMetallicSmoothnessSource:
| 值 | 说明 |
|---|---|
| 0 | 从金属光滑度贴图的Alpha通道读取 |
| 1 | 从反照率贴图的Alpha通道读取 |
四、法线贴图(Normal Map)
Section titled “四、法线贴图(Normal Map)”4.1 法线贴图(normalTexture)
Section titled “4.1 法线贴图(normalTexture)”法线贴图通过修改表面法线方向来模拟凹凸细节,而无需增加实际的几何面数。它可以让低面数模型呈现出丰富的表面细节效果。
(图4-1)
4.2 法线贴图缩放系数(normalTextureScale)
Section titled “4.2 法线贴图缩放系数(normalTextureScale)”控制法线贴图的影响强度。值越大,凹凸效果越明显;值为0时法线贴图不生效。
五、遮蔽贴图(Occlusion Map)
Section titled “五、遮蔽贴图(Occlusion Map)”5.1 遮蔽贴图(occlusionTexture)
Section titled “5.1 遮蔽贴图(occlusionTexture)”遮蔽贴图(也称AO贴图,Ambient Occlusion)用于模拟环境光在缝隙、角落等位置的遮蔽效果,使这些区域看起来更暗,增强立体感和真实感。
(图5-1)
5.2 遮蔽贴图强度(occlusionTextureStrength)
Section titled “5.2 遮蔽贴图强度(occlusionTextureStrength)”控制遮蔽效果的强度,取值范围为0到1。值为1时遮蔽效果最强,值为0时无遮蔽效果。
六、自发光(Emission)
Section titled “六、自发光(Emission)”自发光效果使材质看起来像是自身在发光,常用于LED屏幕、霓虹灯、岩浆等效果。自发光不会对周围物体产生照明效果。
6.1 开启自发光(enableEmission)
Section titled “6.1 开启自发光(enableEmission)”通过设置 enableEmission 为 true 来开启自发光功能。
6.2 自发光颜色(emissionColor)
Section titled “6.2 自发光颜色(emissionColor)”设置自发光的颜色。
6.3 自发光贴图(emissionTexture)
Section titled “6.3 自发光贴图(emissionTexture)”自发光贴图可以精确控制模型不同区域的发光效果和颜色。
6.4 自发光强度(emissionIntensity)
Section titled “6.4 自发光强度(emissionIntensity)”控制自发光的亮度强度。
七、各向异性(Anisotropy)
Section titled “七、各向异性(Anisotropy)”各向异性反射用于模拟在特定方向上具有不同反射特性的材质,如拉丝金属、丝绸、光盘等。
7.1 开启各向异性(anisotropyEnable)
Section titled “7.1 开启各向异性(anisotropyEnable)”设置 anisotropyEnable 为 true 开启各向异性功能。
7.2 各向异性属性
Section titled “7.2 各向异性属性”| 属性 | 类型 | 说明 |
|---|---|---|
anisotropy | number | 各向异性强度 |
anisotropyRotation | number | 各向异性在切线空间中的旋转角度 |
anisotropyTexture | Texture2D | 各向异性强度贴图 |
(图7-1)
八、清漆层(Clear Coat)
Section titled “八、清漆层(Clear Coat)”清漆层用于模拟表面有透明涂层的材质,如汽车漆面、漆器、包装薄膜等。
8.1 开启清漆层(clearCoatEnable)
Section titled “8.1 开启清漆层(clearCoatEnable)”设置 clearCoatEnable 为 true 开启清漆层。
8.2 清漆层属性
Section titled “8.2 清漆层属性”| 属性 | 类型 | 说明 |
|---|---|---|
clearCoat | number | 清漆层强度 |
clearCoatRoughness | number | 清漆层粗糙度 |
clearCoatTexture | BaseTexture | 清漆层强度贴图 |
clearCoatRoughnessTexture | BaseTexture | 清漆层粗糙度贴图 |
clearCoatNormalTexture | BaseTexture | 清漆层法线贴图 |
九、细节贴图与视差贴图
Section titled “九、细节贴图与视差贴图”9.1 细节贴图
Section titled “9.1 细节贴图”细节贴图用于在近距离观察时为材质添加更多的表面细节:
| 属性 | 类型 | 说明 |
|---|---|---|
detailAlbedoTexture | BaseTexture | 细节反照率贴图 |
detailNormalTexture | BaseTexture | 细节法线贴图 |
detailNormalScale | number | 细节法线缩放系数 |
detailTilingOffset | Vector4 | 细节贴图的平铺和偏移 |
9.2 视差贴图
Section titled “9.2 视差贴图”视差贴图通过偏移纹理坐标来模拟更强的深度效果:
| 属性 | 类型 | 说明 |
|---|---|---|
parallaxTexture | BaseTexture | 视差贴图 |
parallaxTextureScale | number | 视差贴图缩放系数 |
十、渲染模式
Section titled “十、渲染模式”PBR材质支持以下渲染模式,通过 renderMode 属性设置:
| 渲染模式 | 值 | 说明 |
|---|---|---|
| Opaque | 0 | 不透明渲染,默认模式,性能最优 |
| Cutout | 1 | Alpha裁剪,根据Alpha阈值决定像素是否可见 |
| Fade | 2 | 透明混合,游戏中经常使用的透明 |
| Transparent | 3 | 透明混合,物理上看似合理的透明 |
10.1 渲染质量(renderQuality)
Section titled “10.1 渲染质量(renderQuality)”PBR材质还提供了渲染质量设置(PBRRenderQuality 枚举),可在高质量和低质量之间切换,以适应不同平台的性能需求。
十一、其他属性
Section titled “十一、其他属性”| 属性 | 类型 | 说明 |
|---|---|---|
enableVertexColor | boolean | 是否支持顶点色,开启后可叠加网格的顶点颜色 |
十二、代码示例
Section titled “十二、代码示例”12.1 创建PBR标准材质
Section titled “12.1 创建PBR标准材质”// 创建PBR标准材质let pbrMat = new Laya.PBRStandardMaterial();
// 设置反照率pbrMat.albedoColor = new Laya.Color(0.8, 0.2, 0.2, 1.0);
// 设置金属度和光滑度pbrMat.metallic = 0.9;pbrMat.smoothness = 0.7;
// 加载反照率贴图Laya.loader.load("res/texture/albedo.png").then((tex: Laya.Texture2D) => { pbrMat.albedoTexture = tex;});
// 加载法线贴图Laya.loader.load("res/texture/normal.png").then((tex: Laya.Texture2D) => { pbrMat.normalTexture = tex; pbrMat.normalTextureScale = 1.0;});
// 设置渲染模式为不透明pbrMat.renderMode = Laya.PBRRenderMode.Opaque;
// 应用到模型let meshRenderer = sprite3D.getComponent(Laya.MeshRenderer);meshRenderer.sharedMaterial = pbrMat;12.2 创建自发光PBR材质
Section titled “12.2 创建自发光PBR材质”let emissiveMat = new Laya.PBRStandardMaterial();emissiveMat.albedoColor = new Laya.Color(0.1, 0.1, 0.1, 1.0);emissiveMat.metallic = 0.0;emissiveMat.smoothness = 0.5;
// 开启自发光emissiveMat.enableEmission = true;emissiveMat.emissionColor = new Laya.Color(0, 1, 0.5, 1);emissiveMat.emissionIntensity = 2.0;
meshRenderer.sharedMaterial = emissiveMat;12.3 创建各向异性PBR材质
Section titled “12.3 创建各向异性PBR材质”let anisotropicMat = new Laya.PBRStandardMaterial();anisotropicMat.albedoColor = new Laya.Color(0.8, 0.8, 0.8, 1.0);anisotropicMat.metallic = 1.0;anisotropicMat.smoothness = 0.8;
// 开启各向异性anisotropicMat.anisotropyEnable = true;anisotropicMat.anisotropy = 0.8;anisotropicMat.anisotropyRotation = 0.0;
meshRenderer.sharedMaterial = anisotropicMat;