AfterglowRender 是一款基于 Vulkan API 开发的光栅化渲染器, 聚焦渲染算法验证与通用图形开发场景. 它为设计验证渲染实现和通用图形算法提供了一套轻量, 灵活且稳定的运行时开发调试解决方案.

基于 AfterglowRender 的框架, 你可以如 ShaderToy [1] 般自由调试和修改 Shader 代码, 修改内容会完全实时地呈现在屏幕上. 相较于 ShaderToy 对 Fragment Shader 的深耕, AfterglowRender 既同时支持对 Vertex Shader 和 Fragment Shader 修改, 也支持对不同的渲染阶段 (如着色阶段, 后处理阶段) 的 Shader 进行单独的修改, 同时也可以随时引入外部资源 (如纹理贴图, 模型等) 到 Shader 中使用而无需关心绑定细节. 所有内容均可做到实时生效, 提供便捷高效的 Shader 开发体验.

此外, AfterglowRender 还提供了一套通用计算的开发工作流, 通过编写 Compute Shader 充分开发 GPU 的通用计算能力. 譬如你可以在 Compute Shader 当中生成任意 模型网格, 实例化数据 亦或是 纹理贴图, 并应用于包括 Compute Shader 在内的任何 Shader 阶段上. 该工作流同样支持实时运行时调试.
AfterglowRender 中实现了一套材质系统, 用于实现对 图形 API 接口封装 及 关联资源状态管理. 藉由材质系统, 编写图形效果时无需再费心于与底层 API 的交互和资源绑定细节, 仅需编写简单 资源声明 和 核心 Shader 代码, 即可控制材质效果开发.
该系统在形式上类似于 Unity 的 ShaderLab[2], 但是将 材质资产 和 Shader 代码 进行了拆分, 材质资产 负责管理 管线状态 和 资源声明, Shader 代码 则仅负责核心逻辑实现.
| 材质资产 | Shader 资产 |
|---|---|
![]() |
![]() |
在 AfterglowRender 所有类型的着色器均以 main 函数为入口.
在 材质资产 文件中, 你可以定义诸如 图元装配方式, 图形管线阶段, 光栅填充模式 等渲染管线状态, 用以实现各类用途不同的材质.
材质资产文档: Documents/AssetStruct/Material.md
图元装配模式: 描述顶点数据的装配方式, 如点, 条带, 三角形, 扇形, Cluster 等.
剔除模式: 决定三角形光栅化的朝向剔除条件, 有 不剔除(双面渲染), 正面剔除 和 背面剔除 模式.
图形管线阶段: 定义材质作用于完整渲染流程的具体阶段, 如阴影, 延迟几何, 延迟光照, 前向绘制, 半透明绘制, 后处理等.
光栅填充模式: 用于控制光栅化结果如何填充, 目前支持 实体绘制 和 线框绘制.
材质系统支持自定义 Shader 所需的纹理资产与自定义参数. 这些参数可以在 材质资产 中定义, 并在 材质实例资产 中覆写, 也直接通过组件控制 Material 和 MaterialInstance 实例以实现运行时的玩法交互, 逻辑类似于 UnrealEngine 的材质与材质实例 [3].
实时修改材质资产中的纹理声明

得益于材质系统的封装, 编写着色器代码时无需再在 CPU 和 GPU 两端分别定义严格对齐的资源声明, 仅需要在材质资产中的完成自定义声明, 即可在着色器中使用对应资源.
同时, AfterglowRender 中还存在一系列内置资源关键字, 可通过着色器文档查询.
着色器内部变量文档: Documents/AssetStruct/Shader.md
出于追求最大图形程度开发便利的考量, AfterglowRender 构建了一套独有的 GPU 通用计算工作流 工作流程. 简而言之, AfterglowRender 的 GPU 通用计算工作流 支持无额外 CPU 代码开发的 Compute Shader 全流程开发, 覆盖数据生成, 共享到渲染应用的完整链路.
该工作流与 材质系统 相兼容, 这意味着你可以直接在 材质资产 中定义从 "ComputeShader 生成数据资产 -> Vertex/Fragment Shader 渲染输出" 的完整流程, 而不需要对 CPU 端代码进行额外修改.
Compute Workflow 示意
ComputeTask 是该工作流中的核心概念, 是任务组划分的基础单元. 如果类比于 Unity, 从功能层面可以将 ComputeTask 理解成一个将 ComputeShader 相关的多数 行为, 生命周期 和 资源管理 进行封装的 MonoBehaviour 类, 并提供了运行时所需接口和参数控制.
通过 ComputeTask 的参数配置, 你可以控制 ComputeShader 的 工作组大小, 执行频率 及 SSBO 创建和引用.
ComputeTask 资产定义

GPU 通用计算工作流文档: Documents/AssetStruct/ComputeMaterial.md
SSBO 可以分成 纹理 和 自定义结构体 两类.
自定义结构体: 不同于 材质系统 中限制的固定类型的 Scalar, Vector 和 Texture 参数, 通用计算工作流 中 SSBO (Shader Storage Buffer Object) 的声明提供了极其自由的配置维度, 你可以将标量 (Scalar) 到矩阵 (Matrix) 等任意维度的 着色器基础数据类型 进行任意组合, 系统会 自动 为结构体填充合适的偏移, 以满足 SSBO 结构体的内存对齐需求.
纹理: 支持 1D / 2D / 3D 纹理, 相比结构结构化数据具备更细的元素粒度 (结构化数据要求 16 bytes 对齐); 且支持以采样 (Sample) 的方式获取数据.
此外, 在 SSBO 的声明当中, 你还可以配置 buffer 所属着色器阶段, 读写性, 初始化模式, 元素数量 等参数.
我以往在进行视觉开发时, 存在多个视效间孤立难以交互的痛点, 其中有一部分原因是平台设计上的取舍. 但从硬件的角度来说, 我们所需要的数据实际上皆位于 GPU Memory. 对于相对较大的 Buffer 数据而言, 在不考虑数据流送的情景下, 从 "本地" 进行加载的成本于从 "全局" 加载其实是一致的 .
故此, AfterglowRender 中提供了一套 SSBO 共享机制, 谓之 "External SSBOs". 正如其字面含义, 可以在当前的 ComputeTask 及材质中使用外部 (其他 ComputeTask) 的 SSBOs.
基于该设计, 我们可以实现诸多全局性的交互效果:
| 地形碰撞避让 | 地貌关联染色 |
|---|---|
![]() |
![]() |
工作流初步支持 GPU-Driven Rendering, 可通过 Compute Shader 生成和更新间接绘制缓冲区 (Indirect Buffer),摆脱指令调度对 CPU 的依赖性, 实现更为灵活且高性能的图形功能开发.
下图演示了使用 GPU 实现的视锥剔除.

当前的 IndirectDraw 以 ComputeTask 为单元进行分发, 为尽可能消除 CPU Host 端绘制指令调用, 后续有计划构建一个全局性的间接绘制管理机制.
为方便场景数据管理, AfterglowRender 中搭建了一套基于 Entity-Component (EC) 模式的场景管理系统. 出于开发直觉与易用性的考量, 并未完全采用当下流行的 ESC (Entity-Component System) 架构 [4]. 但依然借鉴了 ESC 的部分思想, 例如组件布局的 内存连续性 以及 统一更新 的系统等; 但组件本身并非纯数据格式, 其包含数据与方法两个部分.
场景管理器

AfterglowRender 中实现了一个 非侵入式静态反射 方案[5][6]. 基于反射系统, 你可以实现如下功能:
反射调用示例

利用 反射系统 的能力, 我们得以在代码中比较优雅的实现一些原先较为麻烦的功能, 例如上文 场景实体与组件系统 中通过 反射系统 构建的的场景管理器 GUI, 仅需将支持反射的实例作为参数输入, 即可自动生成 GUI 样式.
AfterglowRender 的渲染流程中提供了一套固定的链式 RenderPasses 作为基础渲染框架, 在内部被称为 Domain. 你可以以这些固定的 Pass 作为锚点, 通过 ActionComponent 的 OnRenderBegin() 回调注册自定义的 渲染通道集 (RenderPassSet), 以实现灵活且高度自定义的渲染调度. 最终完整的渲染流程(固定 Passes + 自定义 PassSets ) 呈现的样式即为 RenderGraph[7] 的 有向无环图 ( Directed Acyclic Graph, DAG) 结构.
目前自定义渲染通道仅支持在渲染线程启动前创建.
| 基础渲染框架 | 注册自定义 PassSet |
|---|---|
![]() |
为监听诸如 Shader 代码或材质资产等文件的变化并实时更新, AfterglowRender 中设计了一个统一监听注册资产变化的机制, 在监测到资产发生变化时通过其所关联的的回调函数进行对应处理.
由于目前序列化机制暂未实现, AfterglowRender 尚未支持完整的资产体系, 只有如模型, 材质, 纹理等少数资源封装了资产类型.
为展示 AfterglowRender 灵活的资源共享体系, 我将数个原先较为孤立的展示示例整合成了一个完整且相互关联的模拟系统, 形成类似:
雨水从高地流向低地汇聚成池塘 ->
水面受温度和风力影响蒸发 ->
蒸发的水汽提高局部空气湿度并被风带到远方 ->
受对流影响或地形阻拦使湿度饱和并降雨 ->
雨水落下冲刷地形形成侵蚀地貌 ->
湿润地区生成更多植被 ->
雨水从高地流向低地汇聚成池塘 ->
....
不同的模拟可以 单独控制 开启或关闭, 以节省性能或进行特定测试.
在演示场景中, 我将局部的气候特征简化为数个属性, 如 气温, 湿度 和 空气流速, 并假设整个场景的垂直气候不变(后续计划变更为由多个薄层的 3D 纹理), 由此得以将整个世界的气候以 128x128 的纹理记录.

图像为全局气候信息的可视化呈现(局部), 箭头表示风向和风力, R 通道表示气温, G 通道表示湿度, B 通道表示降雨, 白圈为当前位置.
若要获取特定世界坐标的气候, 则可以直接采用气候贴图得到 (由采样器进行双线性插值).
湖泊或土壤中的水分会因分子运动蒸发到空气中, 使空气湿度增加; 空气中的水汽又会受到大气运动影响, 被输送到其他位置, 因水汽饱和而降雨 (上图对流挤压形成的白色部分).
在真实世界中, 大气会因为星球的自转而产生大气环流, 当前的气象模拟中尚未引入基于 Navier-Stokes Equations 的流体模拟, 因此风源使用梯度噪声方法产生, 并受周围气流及地形影响.
环境会对风产生影响, 风也同样可以影响到环境. 得益于 ExternalSSBOs 的设计, 可以使对象获取到特定位置的风流信息, 并做出相应反馈.
漂浮在空气中的粒子与草丛受风力影响

在演示场景中, 我使用基于虚拟管道 (Virtual Pipe) 模型 的浅水方程(Shallow Water Equation, SWE) 模拟水面变化[8][9][10]. 水面会受到 地形 及 风力 等因数的影响.
水往地形低处流动

风带动水面波纹产生波光粼粼的效果

基础地形使用了 条件分形噪声 的方式生成 [11], 通过将多种噪声以一定规则组合模拟出丰富的地形效果.

但基于噪声生成的地形存在各项同性的缺陷, 效果始终与真实地貌存在差异. 因此, 演示场景中还引入可以 实时运行 的全局分辨率为 4096x4096 的地形侵蚀模拟, 在基础地貌上对其进行 水蚀, 风蚀 和 热蚀 模拟. 其中对地形演化起主要效果的是 水蚀 (Hydraulic Erosion), 通过水流对地形的搬运和沉积, 模拟真实地貌效果 [12][13][14][15].
| 条件分形噪声地貌 (侵蚀前) | 地形演化 (侵蚀后) |
|---|---|
![]() |
![]() |

当地表含水量较高时, 会呈现出湿润的效果.

根据场景中的地貌和天气条件, 植被生长的类型, 样式和密度会有所变化.
没入水下的区域会使陆生植被消亡

土地湿度高的区域草丛更长更密

AfterglowRender 支持了完整的 ACES2 色彩编码系统[16], 并通过 CPU 端预计算色偏表和 GPU 端预计算 HDR-LUT 消除了实时开销.

ACES2 包含 InputTransform (IDT), LookTransform (LMT) 和 OutputTransform (ODT) 等多道工序, 在渲染程序中, 我们假设工作色彩空间 (Working Colorspace) 为 ACEScg (AP1), 因此 InputTransform (IDT) 部分可以固定. 核心部分主要位于 OutputTransform (ODT). ACES2 的 OutputTransform 包含 ToneMapping, Chroma Compression, GamutCompression, White Limiting, Display Encoding 等工序; 经过以上一系列的变换, 将色彩呈现至指定色域和色温的屏幕上.
图中展示 ACES2 OutputTransform 的变换过程, 为方便观察, 每一个阶段皆已应用 EOTF.

AfterglowRender 的 BRDF 基于 Cook-Torrance 微表面模型[17], PBR 接口设计基于 Brent Burley 提出的 Physically-Based Shading 模型[18]. 并支持多种 DiffuseBRDF, Distribution, GeometryOcclusion, Fresnel 和 EnvBRDF 模型的各项同性, 各项异性实现可供组合使用.
此外, 其中还包含一个快速次表面散射实现[24].

Flocks, Herds and Schools: A Distributed Behavioral Model[19] 这篇 Paper 以分布式的思路 对个体行为进行建模, 通过个体间的交互自然而然地产生自然的集群的现象. 基于 通用计算工作流, 演示场景中对论文内容进行了复现, 包含其主要核心思想:
并在其中引入了对环境交互的支持(地形避障等).

通过 IndirectDraw, 我们得以在 GPU 内更新绘制状态, 在无需 CPU 控制的情况下实现更灵活的实例绘制需求. 例如切换实例网格或控制实例数量.
示例场景中, 地形草地应用了 IndirectDraw, 以实现 GPU-Based Frustum culling.
| GrassInstancing (视角内) | GrassInstancing (视角外) |
|---|---|
![]() |
![]() |
为便于程序化生成内容的开展, 我在 Shader 中整合了一些噪声算法, 包含多种 离散噪声 以及 连续噪声 函数[6][7][8], 下面展示了部分基础的噪声形态:
| Hash2D | InterplatedNoise2D | PerlinNoise3D | SimplexNoise3D | WorleyNoise3D |
|---|---|---|---|---|
![]() |
![]() |
![]() |
![]() |
![]() |
通过将不同 Scale 的 连续噪声 以一定权重叠加, 得到更加丰富多样的 分形噪声, 比如下图效果为 SimplexNoise2D 的分形噪声:

在实时渲染中逐帧计算噪声, 尤其是 分形噪声, 从性能的层面来说并不是一个明智的选择. 因此针对分形噪声的应用, 我使用上文提及的 GPU 通用计算工作流 将分形噪声在场景初始化时计算并存入 StorageTexture 中, 仅需要单次初始化, 对性能影响微乎其微. 以此来取代繁琐的外部软件加工噪声图导入<->返工的工作流.
AfterglowRender 引入了一系列基于镜头效果模拟或是色彩理论所实现的后处理算法, 共同构成了最终的画面表现.

Chromatic Aberration 是一种模拟镜头边缘像差的视觉效果.

Film Grain 模拟老式胶片相机成像时产生的颗粒感, 用于提升画面的复古感和电影感.

Vignette 模拟相机镜头边缘产生的暗角, 用于强调重心画面并提升沉浸感.

Bloom 据 UnrealDocumentation 的定义[21], 是光线在眼角膜或镜头中发生的散射, 是一种用于表现强烈光源或反射的视觉技巧.

AfterglowRender 中的 Bloom 通过 自定义渲染通道 实现, 并通过拆分水平垂直模糊, 预计算高斯卷积核等方式进行性能优化.

示例场景使用指数高度雾表达场景雾效, 并通过环境光照模拟大气散射效果, 以极低成本实现了尚可的效果.

在示例场景中所展示的水线效果, 无需额外绘制水面高度信息 的 RenderTarget, 而是可以直接通过 ExternalSSBO 获取水面高度信息, 并与相机近平面世界高度进行比较, 即可得到水线遮罩.

ArcSystemWork 的渲染方案属于传统意义上的卡通渲染. 其在美术资产上做了大量的处理, 例如通过本村线[22]实现无锯齿的内描边, 两套法线分别用于外描边和着色(包含面部着色), 预制暗部颜色贴图和顶点色中储存的各类描边和 AO 控制等.

明日方舟: 终末地 的渲染方案则是混合了 PBR 方法的风格化渲染, 其主要在脸部和皮肤的着色做了许多特殊处理, 例如基于 SDF 贴图的面部阴影, 预制 Color Ramp 条带图, 眼部对头发的半透明以及模板遮蔽的刘海投影等; 服饰部分, 为简化实现, 我直接使用了 BxDF 库中的预设方案 (GGX + SmithJointShadowingMasking + SchlickApproxFresnel) 加之风格化边缘光实现.


在 AfterglowRender 中实现 Shell Fur[23] 很简单, 只需要在网格体组件中设置 instanceCount, 并在 VertexShader 中按照 instanceID 将网格外扩即可. 我使用程序化噪声库中生成的分形 Worley 噪声作为绒毛样式, 并通过模拟 AO, 噪声梯度生成法线模拟毛发法线以强化效果.
MeshComponent 支持单模型多次绘制.
DrawCount: 绘制次数, 用于支持同模型不同材质的多次绘制 (如叠加材质, 描边等).
InstanceCount: 实例数量, 由同一材质批量绘制.



不过 Shell Fur 虽然是 instancing 实现, 但其开销依旧不可忽略. 不仅因为 VertexShader 负载与绒毛层数基本呈线性关系, 还因为在 FragmentShader 应用 clip()函数 (对应 UnrealEngine 中的 OpacityMask 混合模式) 会使 Early-Z Culling 失效, 造成 严重的 Overdraw, 极易触及 GPU 像素填充瓶颈, 降低 GPU 并行度, 对性能产生 极其严重 的影响. 因此对于传统的毛发实现我更倾向 FurCards 方法.
[1] ShaderToy [Online]. Avaliable: https://www.shadertoy.com/. Accessed on: Feb. 8, 2026.
[2] Unity Technologies. ShaderLab Syntax - Unity 2018.4 Documentation [Online]. Available: https://docs.unity.cn/2018.4/Documentation/Manual/SL-Shader.html. Accessed on: Sep. 28, 2025.
[3] Epic Games. Materials [Online]. Avaliable: https://dev.epicgames.com/documentation/en-us/unreal-engine/unreal-engine-materials. Accessed on: Feb. 8, 2026.
[4] Austin Morlan. A Simple Entity Component System (ECS) [C++] [Online]. Available: https://austinmorlan.com/posts/entity_component_system/. Accessed on: Feb. 8, 2026.
[5] WG21. P2996R0: Static Reflection [Online]. Available: https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2023/p2996r0.html. Accessed on: Oct. 4, 2025.
[6] Ubpa. USRefl: A Header-Only C++ Static Reflection Library [Online]. Available: https://github.com/Ubpa/USRefl. Accessed on: Oct. 4, 2025.
[7] Frostbite, Electronic Arts. FrameGraph: Extensible Rendering Architecture in Frostbite [Online]. Available: https://gdcvault.com/play/1024612/FrameGraph-Extensible-Rendering-Architecture-in. Accessed on: Feb. 8, 2026.
[8] J. Greenberg, A. Leroux, A well‐balanced scheme for the numerical processing of source terms in hyperbolic equations, SIAM J. Numer. Anal., 33 (1996), 1–16
[9] Dagenais, François & Vervondel, Valentin & Guzmán, Julián & Hay, Alexander & Delorme, Sébastien & Mould, David & Paquette, Eric. (2018). Extended virtual pipes for the stable and real-time simulation of small-scale shallow water. Computers & Graphics. 76. 10.1016/j.cag.2018.08.005.
[10] Michael Kass and Gavin Miller. 1990. Rapid, stable fluid dynamics for computer graphics. SIGGRAPH Comput. Graph. 24, 4 (Aug. 1990), 49–57. https://doi.org/10.1145/97880.97884
[11] Backes, Gabriel Costa & Engel, Tiago Augusto & Pozzer, Cesar Tadeu. (2018). Real-Time Massive Terrain Generation using Procedural Erosion on the GPU. Proceedings of SBGames 2018 - Computing Track – Short Papers, XVII SBGames, Foz do Iguaçu, PR, Brazil, October 29th–November 1st, 2018.
[12] F. K. Musgrave, C. E. Kolb, and R. S. Mace. 1989. The synthesis and rendering of eroded fractal terrains. SIGGRAPH Comput. Graph. 23, 3 (July 1989), 41–50. https://doi.org/10.1145/74334.74337
[13] H Schott, A Paris, L Fournier, Eric Guérin, Eric Galin. Large-scale terrain authoring through interactive erosion simulation. Journées de l’Association Française d’Informatique Graphique 2022, Nov 2022, Bordeaux, France.
[14] X. Mei, P. Decaudin and B. -G. Hu, "Fast Hydraulic Erosion Simulation and Visualization on GPU," 15th Pacific Conference on Computer Graphics and Applications (PG'07), Maui, HI, USA, 2007, pp. 47-56, doi: 10.1109/PG.2007.15.
[15] Ondřej Št'ava, Bedřich Beneš, Matthew Brisbin, and Jaroslav Křivánek. 2008. Interactive terrain modeling using hydraulic erosion. In Proceedings of the 2008 ACM SIGGRAPH/Eurographics Symposium on Computer Animation (SCA '08). Eurographics Association, Goslar, DEU, 201–210.
[16] Academy of Motion Picture Arts & Sciences. Academy Color Encoding System Documentation [Online]. Avaliable: https://draftdocs.acescentral.com/. Accessed on: Feb. 10, 2026.
[17] R. L. Cook and K. E. Torrance. 1982. A Reflectance Model for Computer Graphics. ACM Trans. Graph. 1, 1 (Jan. 1982), 7–24. https://doi.org/10.1145/357290.357293
[18] Burley, B. (2012). Physically-Based Shading at Disney. In ACM SIGGRAPH 2012 Course Notes: Practical Physically-Based Shading in Film and Game Production (August 2012). https://disneyanimation.com/publications/physically-based-shading-at-disney/
[19] Craig W. Reynolds. 1987. Flocks, herds and schools: A distributed behavioral model. SIGGRAPH Comput. Graph. 21, 4 (July 1987), 25–34. https://doi.org/10.1145/37402.37406
[20] Khronos Group. GPU Rendering and Multi-Draw Indirect [Online]. Available: https://docs.vulkan.org/samples/latest/samples/performance/multi_draw_indirect/README.html. Accessed on Feb. 11, 2026.
[21] EpicGames. Bloom in Unreal Engine [Online]. Available: https://dev.epicgames.com/documentation/en-us/unreal-engine/bloom-in-unreal-engine.
[22] Arc System Works. GuiltyGearXrd's Art Style : The X Factor Between 2D and 3D [Online]. Available: https://gdcvault.com/play/1022031/GuiltyGearXrd-s-Art-Style-The. Accessed on Feb. 12, 2026.
[23] Bkenwright. Fur Effects - Teddies, Cats, Hair .... [Online]. Available: https://xbdev.net/directx3dx/specialX/Fur/. Accessed on Feb. 13, 2026.
[24] Colin Barré-Brisebois. GDC 2011 – Approximating Translucency for a Fast, Cheap and Convincing Subsurface Scattering Look [Online]. Available: https://colinbarrebrisebois.com/2011/03/07/gdc-2011-approximating-translucency-for-a-fast-cheap-and-convincing-subsurface-scattering-look/. Accessed on Feb. 13, 2026.