2025-09-06 19:50:39 +08:00
|
|
|
|
---
|
|
|
|
|
|
title: 《鸣潮》中的光线追踪:用光线构建动漫风格开放世界
|
|
|
|
|
|
date: 2025-08-22 16:35:32
|
|
|
|
|
|
excerpt:
|
|
|
|
|
|
tags:
|
|
|
|
|
|
rating: ⭐
|
|
|
|
|
|
status: inprogress
|
|
|
|
|
|
destination:
|
|
|
|
|
|
share: false
|
|
|
|
|
|
obsidianUIMode: source
|
|
|
|
|
|
---
|
2025-11-30 19:55:44 +08:00
|
|
|
|
- [[UFSH2025]《鸣潮》中的光线追踪: 用光线构建动漫风格开放世界 | 王鑫 库洛游戏《鸣潮》图形渲染组长] https://www.bilibili.com/video/BV1hSW4zTEgQ/?share_source=copy_web&vd_source=fe8142e8e12816535feaeabd6f6cdc8e
|
2025-09-06 19:50:39 +08:00
|
|
|
|
# Rtx
|
|
|
|
|
|
实现功能
|
|
|
|
|
|
1. Rtx反射
|
|
|
|
|
|
2. RtxGI
|
|
|
|
|
|
3. RtxShadow
|
|
|
|
|
|
|
|
|
|
|
|
# 选型&快速验证
|
2025-11-30 19:55:44 +08:00
|
|
|
|
1. 需求:
|
|
|
|
|
|
1. 32km 32km
|
|
|
|
|
|
2. 二次元
|
|
|
|
|
|
3. TOD
|
|
|
|
|
|
4. 4060 2k 60fps
|
2025-09-06 19:50:39 +08:00
|
|
|
|
|
|
|
|
|
|
方案:
|
|
|
|
|
|
1. ReSTIR
|
|
|
|
|
|
2. Lumen(简略版,砍掉一些不需要的过程)
|
|
|
|
|
|
1. GI
|
|
|
|
|
|
2. Reflection
|
|
|
|
|
|
3. 重新开发Clipmap Irradiance Cache来代替Surface Cache
|
|
|
|
|
|
## ReSTIR
|
|
|
|
|
|
1. 时间、空间重采样
|
|
|
|
|
|
2. 计算光照
|
|
|
|
|
|
3. 使用SHaRC、NRD降噪库。
|
|
|
|
|
|
|
|
|
|
|
|
**SHaRC(Spatially Hashed Radiance Cache)**
|
|
|
|
|
|
1. 解决Multi-Bounce Problem
|
|
|
|
|
|
2. 基于世界空间稀疏哈希的Radiance Cache
|
|
|
|
|
|
3. 默认只有2次反射
|
|
|
|
|
|
|
|
|
|
|
|
**NRD(Nvidia Real-time Denoising)**
|
|
|
|
|
|
1. 基于Spatio-Temporal的降噪器,开箱即用。
|
|
|
|
|
|
2. 用于最终降噪输出。
|
|
|
|
|
|
3. 性能消耗较高:4080 2k 2.3~3.0ms
|
|
|
|
|
|
|
|
|
|
|
|
### 缺点:
|
|
|
|
|
|
1. 实现起来简单,光照效果好,但带宽性能压力大。
|
|
|
|
|
|
2. 远处、边缘有噪点。
|
|
|
|
|
|
|
|
|
|
|
|
# 功能实现与迭代经验
|
|
|
|
|
|
## ToonShading
|
|
|
|
|
|
案例1:角色自阴影
|
|
|
|
|
|
- 光栅化
|
|
|
|
|
|
- 场景:CSM
|
|
|
|
|
|
- 角色:PerObjectShadow
|
|
|
|
|
|
- Rtx
|
|
|
|
|
|
- 用剔除角色的InstanceMask做ToonShadowRay
|
|
|
|
|
|
|
|
|
|
|
|
```c++
|
|
|
|
|
|
if(IsToonShadingModel(ShadingModelID))
|
|
|
|
|
|
{
|
|
|
|
|
|
RayTracingMask |=RAY_TRACING_MASK_SHADOW_NOT_TOON;
|
|
|
|
|
|
}
|
|
|
|
|
|
```
|
|
|
|
|
|
|
|
|
|
|
|
案例2:角色接入GI
|
2025-11-30 19:55:44 +08:00
|
|
|
|
- 角色渲染与场景氛围贴合
|
|
|
|
|
|
- 角色需要接受环境反射的间接光
|
|
|
|
|
|
- 提升角色效果的通透感
|
|
|
|
|
|
- ![[WUWA_CharacterGI_1.png]]
|
|
|
|
|
|
- 风格化场景
|
|
|
|
|
|
- 高频的GI信息会破坏卡通渲染质感
|
|
|
|
|
|
- 头发与面部先做球形法线处理
|
|
|
|
|
|
- 角色整体法线朝向相机
|
|
|
|
|
|
- 低成本平滑的间接光
|
|
|
|
|
|
```c++
|
|
|
|
|
|
float3 V = -GetCameraVectorFromTranslatedWorldPosition(TranslatedWorldPosition);
|
|
|
|
|
|
if(IsToonShadingModel(Material. ShadingID))
|
|
|
|
|
|
{
|
|
|
|
|
|
Material.WorldNormal = normalize(lerp(WorldNormal, V, 0.5));
|
|
|
|
|
|
}
|
|
|
|
|
|
```
|
|
|
|
|
|
![[WUWA_CharacterGI_2.png]]
|
|
|
|
|
|
- 混合处理
|
|
|
|
|
|
- 卡渲阴影下并非全黑,避免爆掉和效果异常
|
|
|
|
|
|
- 将间接光转为HSV,限制饱和度与明度
|
|
|
|
|
|
- 乘上AO,增加层次感
|
|
|
|
|
|
- 穿日皮肤Mask,皮肤见扫GI影响
|
|
|
|
|
|
```c++
|
|
|
|
|
|
half3 IndirectLightHSV = RGBToHSVHalf(DiffuseIndirectLighting);
|
|
|
|
|
|
IndirectLightHSV.b = lerp(0, 0.3, IndirectLightHSV.b);
|
|
|
|
|
|
IndirectLightHSV.g = clamp(0, Θ.35, IndirectLightHSV.g);
|
|
|
|
|
|
```
|
|
|
|
|
|
![[WUWA_CharacterGI_3.png]]
|
2025-09-06 19:50:39 +08:00
|
|
|
|
|
|
|
|
|
|
案例3:角色接入反射
|
2025-11-30 19:55:44 +08:00
|
|
|
|
- 希望能够应用在金属特性的表面
|
|
|
|
|
|
- 增加角色效果与环境的交互细节
|
|
|
|
|
|
- 风格化处理
|
|
|
|
|
|
- 粗糙度:Clamp在0~0.3999避免转为SSR
|
|
|
|
|
|
- 金属度:当做反射强度,超过0.9为镜面反射
|
|
|
|
|
|
- 混合处理
|
|
|
|
|
|
- 在Matcap基础上相加,不影响本身金属效果
|
|
|
|
|
|
|
|
|
|
|
|
![[WUWA_CharacterReflection_1.png]]
|
|
|
|
|
|
|
|
|
|
|
|
## HybridShadow
|
|
|
|
|
|
- Billboard和Imposter等物体需要阴影
|
|
|
|
|
|
- 光追和光栅化不同,无法分离ShadowPass和BasePass
|
|
|
|
|
|
- 混合了 CSM + Ray Traced Shadow
|
|
|
|
|
|
- 通过TileClassify减少Trace的像素
|
|
|
|
|
|
|
|
|
|
|
|
### RaytracingShadows
|
|
|
|
|
|
- 美术有时候会用单向Plane遮挡光照
|
|
|
|
|
|
- 需要适配原有的美术资源的阴影逻辑
|
|
|
|
|
|
- Shadow RayFlag:
|
|
|
|
|
|
- RAY_FLAG_CULL_FRONT_FACING_TRIANGLES
|
|
|
|
|
|
|
|
|
|
|
|
### VolumtricFog
|
|
|
|
|
|
- VolumetricFog依赖CSM
|
|
|
|
|
|
- 用ShadowRay预生成3D ShadowVolume
|
|
|
|
|
|
- Inject Lighting用ShadowVolume判断Visibility
|
|
|
|
|
|
- Hybrid Shadow可以用于性能优化,减少Trace物体解耦ShadowVolume和体积雾精度,低端机性能分级
|
|
|
|
|
|
### SingleLayerWater & Translucency
|
|
|
|
|
|
- SLW需要水底颜色 +水底深度,多Trace一条光线计算水底颜色和深度,模拟散射
|
|
|
|
|
|
- 和SLW一样,多发射一条光线,每层循环Trace,手动Blend,注意控制层数
|
|
|
|
|
|
|
|
|
|
|
|
### Skybox
|
|
|
|
|
|
- 鸣潮天空盒非常好看,但也非常复杂,反射里需要能看到天空(Very Important! ! )
|
|
|
|
|
|
- 可以在RayMiss或HitT足够远的时候进行3~4次的Ray Traversal去手动Blend,反射完整天空盒
|
|
|
|
|
|
- 会造成非常严重的性能开销
|
|
|
|
|
|
![[WUWA_SkyBox1.png]]
|
|
|
|
|
|
## 性能优化
|
|
|
|
|
|
### Skybox Capture
|
2025-09-06 19:50:39 +08:00
|
|
|
|
|
2025-11-30 19:55:44 +08:00
|
|
|
|
### Payload压缩
|
2025-09-06 19:50:39 +08:00
|
|
|
|
|
2025-11-30 19:55:44 +08:00
|
|
|
|
### OMM & SER
|
|
|
|
|
|
- Opacity Micro-Map (OMM)
|
|
|
|
|
|
- 和光栅化不同,光追中实现AlphaTest需要在AHS里计算Alpha
|
|
|
|
|
|
- Encode TriangleVisibleState To BLAS
|
|
|
|
|
|
- 黄色三角形才需要走AHS计算
|
|
|
|
|
|
- Shader Execution Reordering (SER)
|
|
|
|
|
|
- GPU上的计算尽量相似,否则会产生Divergence问题
|
|
|
|
|
|
- 做GI时光线方向非常发射,材质计算复杂度也不尽相同
|
|
|
|
|
|
- Nvidia推出SER的GPU Feature,可以一定程度解决问题
|
|
|
|
|
|
- 方向一致的计算提升不大,还会寄存器使用过多导致性能下降
|