feat: IBL 预积分 GPU compute 化 + 环境资产入 Assets 层(动态切换)
CPU 逐像素卷积(venice 4k 阻塞 7.36s)→ 4 个 compute shader 一次性 提交:equirect→cube / irradiance / prefilter×5mip / BRDF LUT。 Cubemap 瘦身为纯资源持有类,生成职责移交 IblGenerator; 环境经 AssetManager 缓存(EnvRef),Renderer::SetEnvironment 动态换绑(RenderPass::OnEnvironmentChanged 广播)。 调试视图 +4:EnvCube / Irradiance / Prefilter / BRDF LUT。 性能前后对比(RTX 5060 Laptop,venice_dawn_1_4k.hdr): - 改造前 CPU:7.36 s(主线程阻塞) - 改造后 GPU:HDR decode 127-134ms + 资源 22-35ms + compute 17-19ms ≈ 165-190ms(约 40×);Neutral 兜底 ~6ms - 运行中动态切换环境同量级(ms 级 GPU,decode 占大头) 冒烟:两构建目录 0 警告;运行期 0 validation(含两次环境切换 + 调试视图 9-12 轮播自动化验证)。
This commit is contained in:
@@ -25,10 +25,11 @@ namespace Engine
|
||||
|
||||
vk::DescriptorPool DescriptorManager::CreateChunk() const
|
||||
{
|
||||
std::array<vk::DescriptorPoolSize, 3> poolSizes = {
|
||||
std::array<vk::DescriptorPoolSize, 4> poolSizes = {
|
||||
vk::DescriptorPoolSize(vk::DescriptorType::eUniformBuffer, kChunkSets),
|
||||
vk::DescriptorPoolSize(vk::DescriptorType::eCombinedImageSampler, kChunkSets),
|
||||
vk::DescriptorPoolSize(vk::DescriptorType::eStorageBuffer, kChunkSets),
|
||||
vk::DescriptorPoolSize(vk::DescriptorType::eStorageImage, kChunkSets),
|
||||
};
|
||||
|
||||
vk::DescriptorPoolCreateInfo poolInfo;
|
||||
@@ -133,6 +134,26 @@ namespace Engine
|
||||
m_Device.GetDevice().updateDescriptorSets(write, {});
|
||||
}
|
||||
|
||||
void DescriptorManager::UpdateStorageImage(const vk::DescriptorSet set,
|
||||
const u32 binding,
|
||||
const vk::ImageView view) const
|
||||
{
|
||||
// storage image 写(compute 输出):layout 必须 eGeneral
|
||||
vk::DescriptorImageInfo imageInfo;
|
||||
imageInfo.setImageView(view)
|
||||
.setImageLayout(vk::ImageLayout::eGeneral);
|
||||
|
||||
vk::WriteDescriptorSet write;
|
||||
write.setDstSet(set)
|
||||
.setDstBinding(binding)
|
||||
.setDstArrayElement(0)
|
||||
.setDescriptorType(vk::DescriptorType::eStorageImage)
|
||||
.setDescriptorCount(1)
|
||||
.setImageInfo(imageInfo);
|
||||
|
||||
m_Device.GetDevice().updateDescriptorSets(write, {});
|
||||
}
|
||||
|
||||
vk::PipelineLayout DescriptorManager::CreatePipelineLayout(vk::DescriptorSetLayout layout,
|
||||
const u32 pushConstantSize) const
|
||||
{
|
||||
@@ -154,18 +175,18 @@ namespace Engine
|
||||
}
|
||||
|
||||
vk::PipelineLayout DescriptorManager::CreatePipelineLayout(const std::vector<vk::DescriptorSetLayout>& layouts,
|
||||
const u32 pushConstantSize) const
|
||||
const u32 pushConstantSize,
|
||||
const vk::ShaderStageFlags pushStages) const
|
||||
{
|
||||
vk::PipelineLayoutCreateInfo info;
|
||||
info.setSetLayouts(layouts);
|
||||
|
||||
std::array<vk::PushConstantRange, 1> pushRanges;
|
||||
if (pushConstantSize > 0) {
|
||||
// 与 ShaderManager 一致:程序级 vertex|fragment 声明。
|
||||
// 与 ShaderManager 一致:程序级声明(默认 vertex|fragment)。
|
||||
// 注意 vkCmdPushConstants 的 stageFlags 必须覆盖 range 的
|
||||
// 全部 stage(VUID-01796),因此 push 调用点也要带双 stage
|
||||
pushRanges[0].setStageFlags(vk::ShaderStageFlagBits::eVertex |
|
||||
vk::ShaderStageFlagBits::eFragment)
|
||||
// 全部 stage(VUID-01796),因此 push 调用点也要带同样的 stage
|
||||
pushRanges[0].setStageFlags(pushStages)
|
||||
.setOffset(0)
|
||||
.setSize(pushConstantSize);
|
||||
info.setPushConstantRanges(pushRanges);
|
||||
|
||||
Reference in New Issue
Block a user