Post Effects Overview后处理全景
Pipeline Order — How Effects Chain管线顺序 — 效果如何串联
NeoX's post-processing pipeline is a fixed sequence of render passes. The final_composite.hlsl (1412+ lines) consolidates the final assembly stage — FXAA, bloom, DOF, tone mapping, color grading, sharpening, vignette, and grain all execute in a single pass to minimize bandwidth:
NeoX 的后处理管线是固定的渲染 Pass 序列。final_composite.hlsl(1412+ 行)整合了最终合成阶段——FXAA、泛光、景深、色调映射、调色、锐化、暗角和胶片颗粒均在单次 Pass 中执行以最小化带宽:
ACES Tone Mapping — Full Reference PipelineACES 色调映射 — 完整参考管线
aces.hlsl (1109 lines) implements the complete Academy Color Encoding System reference pipeline. This is the same standard used in film production. Three main stages:
aces.hlsl(1109 行)实现了完整的学院色彩编码系统参考管线。这与电影制作中使用的标准相同。三个主要阶段:
| Stage阶段 | Function函数 | Description说明 |
|---|---|---|
| RRT | RRT(aces) | Reference Rendering Transform: scene-linear → image-state. Glow → red modifier → AP0→AP1 → desaturate 0.96 → 5-control-point log-log spline per channel参考渲染变换:场景线性→图像状态。辉光→红色修正→AP0→AP1→去饱和 0.96→逐通道 5 控制点对数样条 |
| ODT (sRGB) | ODT_sRGB_D65(oces) | Output Device Transform: 9-control-point spline → luminance scale (cinema white 48 nit) → dim surround gamma (0.9811) → desaturate 0.93 → AP1→XYZ→D60→D65→sRGB输出设备变换:9 控制点样条→亮度缩放(影院白 48 尼特)→暗环境 gamma(0.9811)→去饱和 0.93→AP1→XYZ→D60→D65→sRGB |
| ODT (HDR) | ODT_1000nits / ODT_2000nits | HDR output: 9-pt spline calibrated for 1000/2000 nit peak, no surround compensation, ST2084 (PQ) EOTF outputHDR 输出:针对 1000/2000 尼特峰值校准的 9 点样条,无环境补偿,ST2084(PQ)EOTF 输出 |
// ACES full path (aces.hlsl) float3 ACESFilm(float3 scene_linear) { float3 aces = mul(sRGB_to_AP0, scene_linear); // scene-linear sRGB → AP0 float3 oces = RRT(aces); // RRT: AP0 → OCES float3 out = ODT_sRGB_D65(oces); // ODT: OCES → display sRGB return out; } // Glow module (applied before RRT desaturation) // yc = rgb_2_yc(rgb) -- luminance proxy with chroma boost // glow_fwd: linear ramp from full gain at 2/3*mid to zero at 2*mid float glow_fwd(float yc, float glowGain, float glowMid) { if (yc <= 2/3 * glowMid) return glowGain; else if (yc >= 2 * glowMid) return 0; else return glowGain * (2*glowMid - yc) / (4/3 * glowMid); }
Temporal Anti-Aliasing (TAA)时间抗锯齿(TAA)
temporal_aa.hlsl (624 lines) implements 4 quality tiers. The highest quality mode uses Catmull-Rom history resampling and variance-based clamping with anti-flicker support:
temporal_aa.hlsl(624 行)实现 4 个质量等级。最高质量模式使用 Catmull-Rom 历史重采样和带防闪烁支持的方差截断:
| Quality质量 | Velocity dilation速度膨胀 | History filter历史滤波 | Clamping截断 | Blend factor混合系数 |
|---|---|---|---|---|
| HIGH | 5-sample cross5 采样十字 | Catmull-Rom 5-tap | Variance + anti-flicker方差 + 防闪烁 | 0.12 adaptive |
| MEDIUM | 5-sample cross5 采样十字 | Weighted bilinear加权双线性 | Variance方差 | 0.12 adaptive |
| LOW | None无 | Central sample中心采样 | Variance simple简单方差 | 0.12 fixed |
| FAST | None无 | 5-point gather5 点采集 | Luma only仅亮度 | velocity-based基于速度 |
// Key TAA steps (HIGH quality path) // 1. Velocity dilation: find closest-depth neighbor in 5-cross // 2. YCoCg color space + tone-mapped weighting (color/(luma+4)) // 3. Gaussian-weighted 3x3 current frame filter // 4. Catmull-Rom bicubic history resampling (5-tap) // 5. Variance clamping: sigma = stdDev * (1.5 + localizedAntiFlicker) // 6. ClipHistory to neighbor AABB // 7. Adaptive blend: base 0.12 modulated by speed + depth mismatch // Anti-flicker: increase clamping box when neighbor variance is high float localizedAntiFlicker = saturate(length(neighborhoodVariance) * antiFlickerStrength); sigmaScale = 1.5 + localizedAntiFlicker;
Bloom — Threshold + Separable Gaussian泛光 — 阈值 + 可分离高斯
Bloom uses a 4-pass pyramid: threshold extraction → 3-4 levels of 5-tap Gaussian blur (separate H + V passes) → composite. The threshold uses a soft knee to avoid hard cutoffs:
泛光使用 4-Pass 金字塔:阈值提取→3-4 级 5 点高斯模糊(H+V 分离 Pass)→合成。阈值使用软膝盖避免硬截断:
// bloom_bright.hlsl — soft threshold float TotalLuminance = Luminance(LinearColor) * ExposureScale; float BloomAmount = saturate((TotalLuminance - Threshold) / 2.0); return BloomAmount * LinearColor; // bloom_blur_h.hlsl — 5-tap Gaussian kernel // weights: {0.38774, 0.24477, 0.24477, 0.06136, 0.06136} // offsets: {0, +1, -1, +2, -2} * BloomWidth / RT_size
Depth of Field — Standard + Bokeh SVD景深 — 标准 + 散景 SVD
Two DOF systems are available. Standard DOF is a simple separable Gaussian blur weighted by Circle of Confusion. Bokeh DOF uses SVD (singular value decomposition) approximation to simulate shaped aperture bokeh without expensive full 2D convolution:
提供两个景深系统。标准景深是按弥散圆加权的简单可分离高斯模糊。散景景深使用 SVD(奇异值分解)近似模拟异形光圈散景,无需昂贵的完整 2D 卷积:
| System系统 | Quality质量 | Kernel卷积核 | Method方法 |
|---|---|---|---|
| Standard DOF | Full resolution全分辨率 | Gaussian | CoC-weighted blur (H then V)CoC 加权模糊(H 后 V) |
| Bokeh DOF LOW | 1/4 res | 7×7 | 3-rank SVD: circle / pentagon / hexagon3 秩 SVD:圆形/五边形/六边形 |
| Bokeh DOF HIGH | 1/2 res | 13×13 | 4-rank SVD: circle / hexagon4 秩 SVD:圆形/六边形 |
// Bokeh SVD: separable rank-r approximation of aperture kernel // Precomputed U[rank][pixel], S[rank], V[rank][pixel] from SVD of target kernel // Horizontal pass: for each rank r, weight = V[r][x] * S[r] // Vertical pass: for each rank r, weight = U[r][y] // Bokeh size scales with rcp(CoC) — wider CoC = larger bokeh disc
Eye Adaptation — Histogram-Based眼睛适应 — 基于直方图
eye_adaptation.hlsl offers two exposure computation methods. The histogram method uses a 64-bin histogram with percentile outlier removal for more robust metering in high-contrast scenes:
eye_adaptation.hlsl 提供两种曝光计算方法。直方图方法使用 64 个柱的直方图配合百分位异常值移除,在高对比度场景中实现更稳健的测光:
// Basic method: downsampled weighted average float smoothedLum = lerp(prevLum, targetLum, 1 - exp2(-dt * AdaptSpeed)); exposure = LocalExposureMultipler / max(0.0001, smoothedLum); // Histogram method: 64-bin log-luminance histogram // ComputeAverageLuminanceWithoutOutlier: // remove bottom LowPercentile% and top HighPercentile% of histogram bins // compute weighted average of remaining bins // AdaptationWeight(nx, slope): center-weighted metering // triangle function: max(1 - 2*slope*|nx - 0.5|, 0) // gives higher weight to center of frame
Color Grading — combine_lut.hlsl (677 lines)调色 — combine_lut.hlsl(677 行)
combine_lut.hlsl is the most complete color processing pass, baking a final 3D LUT that encodes white balance, film tone curve, Nuke-style color correction, gamut expansion, and device-specific output into a single texture lookup at runtime:
combine_lut.hlsl 是最完整的色彩处理 Pass,将白平衡、胶片色调曲线、Nuke 风格色彩校正、色域扩展和设备特定输出烘焙到单个 3D LUT 纹理,在运行时一次查找完成:
| Stage阶段 | Function函数 | Method方法 |
|---|---|---|
| 1. White Balance | WhiteBalance(Temp, Tint) | Planckian locus → D65 chromatic adaptation (Bradford)普朗克轨迹→D65 色适应(Bradford) |
| 2. Film Curve | FilmToneMap() | ACES-inspired: glow → red modifier → AP0→AP1 → Duiker splineACES 启发:辉光→红色修正→AP0→AP1→Duiker 样条 |
| 3. Color Correct | ColorCorrectAll() | Nuke-style: shadow / midtone / highlight — saturation, contrast, gamma, gain, offset per regionNuke 风格:暗部/中间调/高光——逐区域饱和度、对比度、gamma、增益、偏移 |
| 4. Blue Correct | BlueCorrection() | Desaturate blue channel toward white point for artistic balance向白点去饱和蓝色通道用于艺术平衡 |
| 5. Gamut Expand | ExpandGamut() | Push colors beyond sRGB toward P3/Wide-Gamut for vivid output将颜色推向 P3/宽色域以实现鲜艳输出 |
| 6. LUT blend | UnwrappedTexture3DSample() | Up to 4 blended 16^3 3D LUTs (unwrapped to 2D 256×16 strips)最多 4 个混合的 16^3 3D LUT(展开为 2D 256×16 条带) |
| 7. Output device | sRGB / Rec709 / ST2084 1000/2000 nitsRGB / Rec709 / ST2084 1000/2000 尼特 | Gamut: sRGB / P3 / Rec2020 / AP0 / AP1色域:sRGB / P3 / Rec2020 / AP0 / AP1 |
Final Composite — Everything in One Pass最终合成 — 单 Pass 完成所有
The final composite pass executes all remaining operations in sequence within a single full-screen quad draw. This avoids the bandwidth cost of separate passes for each effect:
最终合成 Pass 在单次全屏四边形绘制中按顺序执行所有剩余操作。这避免了每个效果独立 Pass 的带宽开销:
// final_composite.hlsl — execution order (simplified) float4 ps_main(Fragment input) { float2 uv = input.uv; float3 color = FXAAPass(SceneColor, uv); // FXAA 3.11 preset 5 (32 steps) color = DOFPass(color, uv, DOFBlur); // Gaussian CoC blend color = BokehDOFPass(color, uv, bokehBuf); // SVD bokeh blend color += SunShaftPass(uv); // additive volumetric shafts color += BloomPass(color, BloomTex) // + dirty lens overlay + LensFlarePass(uv, sunPos); // 8-ghost hexagon flare color = TonemapCommonPS(color, uv); // ACES + color correct + LUT // Inside TonemapCommonPS: // grain jitter (temporal noise) → chromatic aberration (CA fringe) // → sharpen (neighbor luminance difference) // → vignette (cos^4 law radial darkening) // → grain intensity → color LUT lookup (3D unwrapped) // → linear → sRGB gamma return float4(color, 1); }
Effect Reference Table效果参考表
| File文件 | Effect效果 | Algorithm算法 |
|---|---|---|
| aces.hlsl | ACES Tone Mapping | Full ACES reference: RRT + ODT (sRGB / HDR 1000/2000 nit)完整 ACES 参考:RRT + ODT(sRGB / HDR) |
| temporal_aa.hlsl | TAA | 4 quality tiers; Catmull-Rom history; variance clamping; YCoCg; adaptive blend4 质量等级;Catmull-Rom 历史;方差截断;YCoCg;自适应混合 |
| bloom_bright.hlsl | Bloom threshold泛光阈值 | Soft-knee luminance threshold: (lum - thresh) / 2软膝盖亮度阈值 |
| bloom_blur_h/v.hlsl | Bloom blur泛光模糊 | 5-tap Gaussian {0.387, 0.245×2, 0.061×2}; multi-mip pyramid5 点高斯;多级金字塔 |
| dof_blur_h/v.hlsl | Standard DOF标准景深 | CoC-weighted separable GaussianCoC 加权可分离高斯 |
| bokeh_dof.hlsl | Bokeh DOF散景景深 | Low-rank SVD approximation of 7×7 / 13×13 aperture kernel7×7 / 13×13 光圈核的低秩 SVD 近似 |
| eye_adaptation.hlsl | Auto Exposure自动曝光 | 64-bin log-luminance histogram + percentile outlier removal; temporal smoothing64 柱对数亮度直方图 + 百分位异常值移除;时间平滑 |
| sun_shafts.hlsl | God Rays耶稣光 | Radial blur from sun position; depth-masked; multi-pass从太阳位置径向模糊;深度遮蔽;多 Pass |
| combine_lut.hlsl | Color Grading调色 | White balance + filmic curve + Nuke color correct + 4×3D LUT blend; baked to LUT白平衡 + 胶片曲线 + Nuke 色彩校正 + 4×3D LUT 混合;烘焙到 LUT |
| fxaa.hlsl | FXAA | NVIDIA FXAA 3.11 preset 5 (32 search steps, edge threshold 1/8, subpix 3/4)NVIDIA FXAA 3.11 预设 5(32 步搜索,边缘阈值 1/8) |
| final_composite.hlsl | Final Assembly最终合成 | FXAA + DOF + Bloom + Lens Flare + Tone Map + Color Correct + Sharpen + Vignette + Grain (single pass)FXAA + 景深 + 泛光 + 镜头光晕 + 色调映射 + 调色 + 锐化 + 暗角 + 颗粒(单 Pass) |
| color_grading.hlsl | LUT PassLUT Pass | Simple 16^3 3D LUT lookup (gamma-encoded); used for simple per-shot LUT override简单 16^3 3D LUT 查找(gamma 编码);用于简单镜头 LUT 覆盖 |
| velocity.hlsl | Motion Vectors运动向量 | ClipToPrevClip reprojection; xy velocity → velocity buffer (feeds TAA)ClipToPrevClip 重投影;xy 速度→速度缓冲(供 TAA 使用) |
| lens_flare.hlsl | Lens Flare镜头光晕 | 8-ghost hexagonal bokeh flare with aspect-correct UV and per-ghost color tint8 幽灵六边形散景光晕,宽高比正确 UV,逐幽灵颜色着色 |
| filmic_tonemapping.hlsl | Filmic Curve胶片曲线 | Haarm-Peter Duiker spline approximation (toe + shoulder); used as alternative to ACESHaarm-Peter Duiker 样条近似(趾部 + 肩部);用作 ACES 的替代 |
res_upgrade/shader/posteffects/ first, then falls back to res/shader/posteffects/ for any file not present in res_upgrade/. This means the new engine has all post effects from both directories combined. Effects residing in res/shader/posteffects/ (available to new engine via fallback): motion blur, radial blur, outline-to-RT pass, volume fog pass, screen-space distortion pass, Kuwahara filter, programmable lens flares, and more. bokeh_dof.hlsl (SVD approximation) is a new addition in res_upgrade/ that supplements the standard DOF. aces.hlsl and final_composite.hlsl exist in both directories with identical content — the res_upgrade/ versions take priority at runtime.
新引擎完整功能集:新引擎优先读取 res_upgrade/shader/posteffects/,对 res_upgrade/ 中不存在的文件回退到 res/shader/posteffects/。这意味着新引擎拥有两个目录的所有后处理效果。存放于 res/shader/posteffects/ 中的效果(新引擎通过回退机制使用):运动模糊、径向模糊、outline-to-RT Pass、体积雾 Pass、屏幕空间扭曲 Pass、Kuwahara 滤波器、可编程镜头光晕等。bokeh_dof.hlsl(SVD 近似)是 res_upgrade/ 中新增的,补充标准景深。aces.hlsl 和 final_composite.hlsl 在两个目录中均存在且内容相同——运行时 res_upgrade/ 版本优先。