feat: 搭建 Vulkan 1.4 渲染器骨架,绘制旋转 3D 立方体

使用 Vulkan 1.4 现代路径初始化引擎骨架:
- 用 Shader Object (VK_EXT_shader_object) 替代传统 VkPipeline
- 用 Dynamic Rendering 替代 RenderPass/Framebuffer
- 用 Synchronization2 管理 barrier

核心模块:
- Window:GLFW 封装,GLFW_NO_API 模式,兼容 Wayland
- Log:spdlog 封装
- Types:u32/u64/f32 类型别名

Vulkan 后端:
- Device:Instance、PhysicalDevice、LogicalDevice、Queue 及 feature 查询
- Swapchain:Image、ImageView、DepthBuffer、Recreate
- ShaderManager:SPIR-V 加载与 ShaderEXT 创建
- CommandManager:CommandPool 与主 CommandBuffer
- SyncManager:per-frame Fence 与 ImageAvailable semaphore,per-image RenderFinished semaphore,2 frames in flight
- MemoryAllocator:内存子分配器,256MB block,persistent mapping
- Buffer:VertexBuffer、IndexBuffer、UniformBuffer 封装
- UniformBuffer:每帧上传 MVP 矩阵
- DescriptorManager:DescriptorSetLayout、DescriptorPool、DescriptorSet 及更新

Renderer:
- 协调所有子系统
- 绘制每面不同颜色的旋转 3D 立方体
- 启用 depth test,MVP 矩阵由 GLM 计算

构建:
- CMake 组织 Engine 静态库与 App 可执行文件
- glfw、glm、spdlog 通过 add_subdirectory 引入
This commit is contained in:
2026-09-20 23:09:40 +08:00
parent 706ee2301e
commit 381b7c0aa6
38 changed files with 2423 additions and 12 deletions
+83
View File
@@ -0,0 +1,83 @@
//
// Created by atdunbg on 2026/9/20.
//
#include <Engine/Vulkan/DescriptorManager.h>
#include <Engine/Vulkan/Device.h>
#include <Engine/Core/Log.h>
namespace Engine
{
DescriptorManager::DescriptorManager(Device& device)
: m_Device(device)
{
vk::DescriptorPoolSize poolSize;
poolSize.setType(vk::DescriptorType::eUniformBuffer)
.setDescriptorCount(kMaxSets);
vk::DescriptorPoolCreateInfo poolInfo;
poolInfo.setMaxSets(kMaxSets)
.setPoolSizes(poolSize)
.setFlags(vk::DescriptorPoolCreateFlagBits::eFreeDescriptorSet);
m_Pool = m_Device.GetDevice().createDescriptorPool(poolInfo);
ENGINE_INFO("DescriptorManager created");
}
DescriptorManager::~DescriptorManager()
{
m_Device.GetDevice().destroyDescriptorPool(m_Pool);
}
vk::DescriptorSetLayout DescriptorManager::CreateUniformBufferLayout(u32 binding)
{
vk::DescriptorSetLayoutBinding layoutBinding;
layoutBinding.setBinding(binding)
.setDescriptorType(vk::DescriptorType::eUniformBuffer)
.setDescriptorCount(1)
.setStageFlags(vk::ShaderStageFlagBits::eVertex |
vk::ShaderStageFlagBits::eFragment);
vk::DescriptorSetLayoutCreateInfo layoutInfo;
layoutInfo.setBindings(layoutBinding);
return m_Device.GetDevice().createDescriptorSetLayout(layoutInfo);
}
vk::PipelineLayout DescriptorManager::CreatePipelineLayout(vk::DescriptorSetLayout layout)
{
vk::PipelineLayoutCreateInfo info;
info.setSetLayouts(layout);
return m_Device.GetDevice().createPipelineLayout(info);
}
vk::DescriptorSet DescriptorManager::AllocateDescriptorSet(vk::DescriptorSetLayout layout)
{
vk::DescriptorSetAllocateInfo allocInfo;
allocInfo.setDescriptorPool(m_Pool)
.setSetLayouts(layout);
auto sets = m_Device.GetDevice().allocateDescriptorSets(allocInfo);
return sets[0];
}
void DescriptorManager::UpdateUniformBuffer(vk::DescriptorSet set, u32 binding,
vk::Buffer buffer, u64 size)
{
vk::DescriptorBufferInfo bufferInfo;
bufferInfo.setBuffer(buffer)
.setOffset(0)
.setRange(size);
vk::WriteDescriptorSet write;
write.setDstSet(set)
.setDstBinding(binding)
.setDstArrayElement(0)
.setDescriptorType(vk::DescriptorType::eUniformBuffer)
.setDescriptorCount(1)
.setBufferInfo(bufferInfo);
m_Device.GetDevice().updateDescriptorSets(write, {});
}
} // namespace Engine