可变速率着色

什么是可变速率着色?

在现代 3D 渲染引擎中,着色器比以前复杂得多。基于物理的渲染、实时全局照明和屏幕空间效果的出现,增加了渲染每帧时必须执行的 每像素 着色的数量。此外,屏幕分辨率也大幅提升,1440p 和 4K 已成为常见的目标分辨率。因此,场景渲染中的总着色成本通常代表着渲染每帧所花费的大量时间。

可变速率着色 (VRS,variable rate shading) 是一种通过降低 每像素 着色(也称为 片段 着色)的分辨率来降低着色成本的方法,同时保持渲染几何体的原始分辨率。这意味着几何边缘仍然像没有 VRS 时一样锋利。 VRS 可以与任何 3D 抗锯齿 技术(MSAA、FXAA、TAA、SSAA)结合使用。

VRS 允许以本地方式指定着色质量,这使得视口的某些部分可以比其他部分接收更详细的着色。这在虚拟现实 (VR) 中特别有用,可实现 注视点渲染 (foveated rendering),其中视口的中心比其边缘更详细。

这是使用本页底部链接的密度图,先禁用,然后启用速率着色渲染的场景:

在纹理场景中禁用可变速率着色

在纹理场景中禁用可变速率着色

在纹理场景中启用可变速率着色(质量较低但性能较高)

在纹理场景中启用可变速率着色(质量较低但性能较高)

当在具有低频细节的场景(例如具有风格化/低多边形艺术风格的场景)中使用时,可以实现类似的性能增益,但视觉质量的降低较小:

在无纹理场景中禁用可变速率着色

在无纹理场景中禁用可变速率着色

在无纹理场景中启用可变速率着色(质量较低但性能较高)

在无纹理场景中启用可变速率着色(质量较低但性能较高)

硬件支持

可变速率着色仅在特定 GPU 上受支持:

桌面端:

  • NVIDIA Turing 及更新版本(包括 GTX 1600 系列)

  • AMD RDNA2 及更新版本(集成和专用 GPU – 包括 Steam Deck)

  • Intel Arc Alchemist 及更新版本 (仅限专用 GPU)

    • 英特尔集成显卡不支持可变速率着色。

移动端 SoC:

  • 骁龙(Snapdragon) 888 及更新版本

  • MediaTek 天玑 9000 及更新版本

  • ARM Mali-G615 及更新版本

截至 2023 年 1 月,Apple 和 Raspberry Pi GPU 仍不支持可变速率着色。

在 Godot 中使用可变速率着色

备注

Forward+ 和 Forward 移动渲染方法都支持可变速率着色。 VRS 可用于 pancake(非 XR)和 XR 显示模式。

兼容渲染方法不支持可变速率着色。

在高级项目设置中, 渲染 > VRS 部分提供了控制根视口上可变速率着色的设置:

  • 模式: 控制可变速率着色模式。 Disabled 禁用可变速率着色。 Texture 使用手动创作的纹理来设置着色密度(请参阅下面的属性)。 XR 自动生成适合虚拟/增强现实中的注视点渲染的纹理。

  • 纹理: 用于控制根视口上的着色密度的纹理。仅当 ModeTexture 时使用。

对于自定义视口,必须手动将 VRS 模式和纹理设置到 Viewport 节点。

备注

在不受支持的硬件上,启用可变速率着色时不会出现视觉差异。你可以通过使用 --verbose 命令行参数 运行编辑器或项目来检查硬件是否支持可变速率着色。

创建 VRS 密度图

如果使用 Texture VRS 模式, 必须 设置要用作密度贴图的纹理。否则,将看不到任何效果。

你可以使用图像编辑器手动创建自己的 VRS 密度图,或使用其他方法生成它(例如,在 CPU 上使用 Image 类,或在 GPU 上使用着色器)。但是,动态生成 VRS 图像时请注意其性能影响。如果选择动态生成,请确保 VRS 图像生成过程足够快,以避免超出 VRS 的性能增益。

纹理必须遵循以下规则:

  • 纹理 必须 使用无损压缩格式,以便颜色可以精确匹配。

  • 以下 VRS 密度映射到各种颜色,较亮的颜色表示较低级别的着色精度:

密度

Color

注释

1×1(细节最高)

rgb(0, 0, 0) - #000000

1×2

rgb(0, 85, 0) - #005500

2×1

rgb(85, 0, 0) - #550000

2×2

rgb(85, 85, 0) - #555500

2×4

rgb(85, 170, 0) - #55aa00

4×2

rgb(170, 85, 0) - #aa5500

4×4

rgb(170, 170, 0) - #aaaa00

4×8

rgb(170, 255, 0) - #aaff00

大多数硬件不支持。

8×4

rgb(255, 170, 0) - #ffaa00

大多数硬件不支持。

8×8(细节最低)

rgb(255, 255, 0) - #ffff00

大多数硬件不支持。

例如,此 VRS 密度纹理在视口中心提供最高的着色密度,在角落提供最低的着色密度:

VRS 密度贴图纹理示例,模拟注视点渲染

VRS 密度贴图纹理示例,模拟注视点渲染

VRS 密度纹理没有尺寸或纵横比要求。但是,使用大于视口分辨率除以 GPU 的 图块大小 的 VRS 密度图并没有任何好处。切片大小决定了可以与其他切片分开更改着色密度的最小像素区域。在大多数 GPU 上,此图块大小为 8×8 像素。你可以通过使用 --verbose 命令行参数运行 Godot 来查看图块大小,正如 VRS 调试信息中打印的那样。

因此,建议保持使用相对较低的分辨率,例如 256×256(方形)或 480×270(16:9)。根据你的使用案例,与项目中最常见的视口纵横比(例如 16:9)相匹配的纹理相比,方形纹理可能更合适。

小技巧

使用可变速率着色时,你可以使用负 纹理 mipmap LOD 偏置 来减少着色率降低的区域的模糊度。

请注意,纹理 LOD 偏置是全局设置的,因此这也会影响具有完整着色率的视口区域。不要使用太低的值,否则纹理将会显得有颗粒感。

性能比较

为了了解 VRS 在理论上可以提高多少性能,以下是与本页顶部显示的纹理示例场景的性能比较。使用本页上提供的 VRS 密度图示例。

结果是在配备 NVIDIA 525.60.11 驱动程序的 GeForce RTX 4090 上收集的。

Resolution

启用 VRS

禁用 VRS

性能提升

1920×1080(全高清)

2832 FPS

3136 FPS

+10.7%

2560×1440(QHD)

2008 FPS

2256 FPS

+12.3%

3840×2160(4K)

1236 FPS

1436 FPS

+16.2%

7680×4320(8K)

384 FPS

473 FPS

+23.1%

在性能改进方面,可变速率着色在更高的目标分辨率下更有利。在高分辨率下,视觉质量的下降也不太明显。

备注

对于非 VR 游戏,你可能需要使用比本示例中使用的更不激进的 VRS 纹理。因此,有效的性能提升将会降低。