1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
|
#include "hzpch.h"
#include "SVGFPass.h"
#include "Hazel/Core/Application.h"
#include "Hazel/Scene/SceneManager.h"
#include "Hazel/Renderer/RenderResource/RenderResourceManager.h"
#include "Hazel/Renderer/RenderResource/PipelineCache.h"
#include <Hazel/Renderer/RenderResource/Shader.h>
namespace GameEngine {
void SVGFPass::Init()
{
m_Shader = std::make_shared<Shader>("postprocess/SVGF", SHADER_FREQUENCY_COMPUTE)->GetRHIShader();
RHIRootSignatureInfo info = {};
info.AddEntryFromReflect(m_Shader);
info.AddEntry(RENDER_RESOURCEMANAGER->GetGlobalResourcePreFrameRootSignature()->GetInfo())
.AddPushConstant({4,SHADER_FREQUENCY_COMPUTE });
m_RootSignature = APP_DYNAMICRHI->CreateRootSignature(info);
RHIComputePipelineInfo pipelineInfo = {};
pipelineInfo.computeShader = m_Shader;
pipelineInfo.rootSignature = m_RootSignature;
m_Pipeline = APP_DYNAMICRHI->CreateComputePipeline(pipelineInfo);
}
void SVGFPass::Build(RDGBuilder& builder)
{
auto& [w, h] = APP_WINDOWSIZE;
RDGTextureHandle pathTracingDirectRes = builder.GetTexture("PathTracingdirectRes");
if (pathTracingDirectRes.ID() == UINT32_MAX) { return; }
RDGTextureHandle pathTracingIndirectRes = builder.GetTexture("PathTracingIndirectRes");
RDGTextureHandle velocity = builder.GetTexture("GBufferVelocity");
RDGBufferHandle exposureData = builder.GetBuffer("ExposureData");
RDGTextureHandle directFilterRes = builder.CreateTexture("PathTracing_SVGF_directFilterRes")
.Exetent({ w, h ,1 })
.Format(FORMAT_R32G32B32A32_SFLOAT)
.AllowRenderTarget()
.AllowReadWrite()
.Finish();
RDGTextureHandle forPinpongTexture = builder.CreateTexture("PathTracing_SVGF_forPinpongTexture")
.Exetent({ w, h ,1 })
.Format(FORMAT_R32G32B32A32_SFLOAT)
.AllowRenderTarget()
.AllowReadWrite()
.Finish();
RDGTextureHandle inDirectFilterRes = builder.CreateTexture("PathTracing_SVGF_inDirectFilterRes")
.Exetent({ w, h ,1 })
.Format(FORMAT_R32G32B32A32_SFLOAT)
.AllowRenderTarget()
.AllowReadWrite()
.Finish();
// 直接光
for (int i = 0; i < 5; i++) {
builder.CreateComputePass(GetName() + "_DirectRes" + std::to_string(i))
.RootSignature(m_RootSignature)
.PassIndex(i)
.ReadWrite(1, 0, 0, i == 0 ? directFilterRes : i % 2 == 1 ? forPinpongTexture : directFilterRes)
.ReadWrite(1, 1, 0, i == 0 ? pathTracingDirectRes : i % 2 == 1 ? directFilterRes : forPinpongTexture)
.ReadWrite(1, 2, 0, velocity)
.Execute([&](RDGPassContext context) {
auto& [w, h] = APP_WINDOWSIZE;
RHICommandListRef command = context.command;
command->SetComputePipeline(m_Pipeline);
command->BindDescriptorSet(context.descriptors[1], 1);
uint32_t curIndex = context.passIndex[0];
command->PushConstants(&curIndex, sizeof(uint32_t), SHADER_FREQUENCY_COMPUTE);
command->BindDescriptorSet(RENDER_RESOURCEMANAGER->GetGlobalResourcePerFrameDescriptorSet(), 0);
command->Dispatch((w + 15) / 16, (h + 15) / 16, 1);
})
.Finish();
}
// 间接光
for (int i = 0; i < 5; i++) {
builder.CreateComputePass(GetName() + "_DirectRes" + std::to_string(i))
.RootSignature(m_RootSignature)
.PassIndex(i)
.ReadWrite(1, 0, 0, i == 0 ? inDirectFilterRes : i % 2 == 1 ? forPinpongTexture : inDirectFilterRes)
.ReadWrite(1, 1, 0, i == 0 ? pathTracingIndirectRes : i % 2 == 1 ? inDirectFilterRes : forPinpongTexture)
.ReadWrite(1, 2, 0, velocity)
.Execute([&](RDGPassContext context) {
auto& [w, h] = APP_WINDOWSIZE;
RHICommandListRef command = context.command;
command->SetComputePipeline(m_Pipeline);
command->BindDescriptorSet(context.descriptors[1], 1);
uint32_t curIndex = context.passIndex[0];
command->PushConstants(&curIndex, sizeof(uint32_t), SHADER_FREQUENCY_COMPUTE);
command->BindDescriptorSet(RENDER_RESOURCEMANAGER->GetGlobalResourcePerFrameDescriptorSet(), 0);
command->Dispatch((w + 15) / 16, (h + 15) / 16, 1);
})
.Finish();
}
}
}
|