- 安装ubuntu系统
- 在nvidia官网下载版本较新的驱动,参考https://blog.csdn.net/wr1997/article/details/106909423 安装,驱动版本要在535及以上
- 安装vulkansdk
- 安装cuda11.6及以上
- 解压flatbuffers-23.5.26和VulkanSceneGraph
- 安装flatbuffer库
cd flatbuffers-23.5.26/build
cmake ..
make
sudo make install
- 安装VulkanSceneGraph库
cd VulkanSceneGraph/build
cmake ..
make
sudo make install
```4. 安装assimp库
```bash
cd assimp/build
cmake ..
make
sudo make install
- 克隆项目代码 https://github.com/GaaarretWang/cadRenderer
- dataset3、geos和obj文件夹放在cadRenderer/asset/data目录下
cd cadRenderer
bash run.sh
根目录中实现本地数据的读取,实现Rendering类和RenderingServer类,模拟服务器与客户端的数据传输,该部分仿照AR引擎中的渲染模块接口进行设计,便于迁移。asset文件夹为渲染器的实现,可以直接替换AR引擎中渲染模块的asset文件夹
// 数据集分辨率低,该参数为渲染提升分辨率的倍数
double upsample_scale = 2;
// 渲染根目录相对于可执行文件的位置,所有路径都应该相对渲染的根目录来索引
std::string rendering_dir = "../";
// 每个模型的归一化矩阵,或初始矩阵,与ar引擎对齐
std::vector<vsg::dmat4> init_model_transforms;
// 三个数组的大小应该相等,一一对应
std::vector<vsg::dmat4> model_transforms; // 可以重复
std::vector<std::string> model_paths; // 可以重复
std::vector<std::string> instance_names; // 不可重复
// true: 在相机跟踪时使用单独的shader,不进行深度剔除,总是显示模型
// false: 在非相机跟踪时使用深度剔除的shader
bool trackingShader = true;
// 在程序开始调用一次初始化
int Init();
- 图像和采样器创建
- 内存屏障和管线屏障
- 资源管理
- 环境贴图生成
- BRDF查找表生成
- 辐照度立方体贴图生成
- 预过滤环境立方体贴图生成
- 天空盒渲染
- PBR着色器设置
- 测试场景创建
创建一个2D图像和对应的图像视图。
声明:
void createImage2D(vsg::Context& context, VkFormat format, VkImageUsageFlags usage, VkExtent2D extent, ptr<vsg::Image>& image, ptr<vsg::ImageView>& imageView)
参数:
- context:vsg::Context& - Vulkan上下文
- format:VkFormat - 图像格式
- usage:VkImageUsageFlags - 图像用途标志
- extent:VkExtent2D - 图像尺寸
- image:ptr<vsg::Image>& - 输出参数,创建的图像对象
- imageView:ptr<vsg::ImageView>& - 输出参数,创建的图像视图对象
返回值: void
注意事项:
- 此函数创建的图像为2D类型,单层,无mipmap
- 图像的内存分配被注释掉,可能需要在RenderGraph编译时进行
创建一个立方体贴图图像和对应的图像视图。
声明:
void createImageCube(vsg::Context& context, VkFormat format, VkImageUsageFlags usage, VkExtent2D extent, uint32_t numMips, ptr<vsg::Image>& image, ptr<vsg::ImageView>& imageView)
参数:
- context:vsg::Context& - Vulkan上下文
- format:VkFormat - 图像格式
- usage:VkImageUsageFlags - 图像用途标志
- extent:VkExtent2D - 图像尺寸
- numMips:uint32_t - mipmap级别数量
- image:ptr<vsg::Image>& - 输出参数,创建的图像对象
- imageView:ptr<vsg::ImageView>& - 输出参数,创建的图像视图对象
返回值: void
注意事项:
- 此函数创建的是立方体贴图,包含6个面
- 图像视图的类型被设置为VK_IMAGE_VIEW_TYPE_CUBE
- 函数手动编译图像和分配内存,而不是使用vsg::createImageView
创建一个图像采样器对象。
声明:
void createSampler(uint32_t numMips, ptr<vsg::Sampler>& sampler)
参数:
- numMips:uint32_t - mipmap级别数量
- sampler:ptr<vsg::Sampler>& - 输出参数,创建的采样器对象
返回值: void
注意事项:
- 采样器使用线性过滤和线性mipmap模式
- 地址模式设置为VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE
- maxLod设置为mipmap级别数量
创建一个适用于立方体贴图的图像采样器对象。
声明:
void createSamplerCube(uint32_t numMips, ptr<vsg::Sampler>& sampler)
参数:
- numMips:uint32_t - mipmap级别数量
- sampler:ptr<vsg::Sampler>& - 输出参数,创建的采样器对象
返回值: void
注意事项:
- 采样器使用线性过滤和线性mipmap模式
- 地址模式设置为VK_SAMPLER_ADDRESS_MODE_CLAMP_TO_EDGE
- maxLod设置为mipmap级别数量
创建一个vsg::ImageInfo对象,包含图像视图、图像布局和采样器信息。
声明:
void createImageInfo(const ptr<vsg::ImageView> imageView, VkImageLayout layout, const ptr<vsg::Sampler> sampler, ptr<vsg::ImageInfo> &imageInfo)
参数:
- imageView:const ptr<vsg::ImageView> - 图像视图对象
- layout:VkImageLayout - 图像布局
- sampler:const ptr<vsg::Sampler> - 采样器对象
- imageInfo:ptr<vsg::ImageInfo>& - 输出参数,创建的ImageInfo对象
返回值: void
注意事项:
- 此函数将图像视图、布局和采样器信息组合到一个ImageInfo对象中
创建一个图像内存屏障,用于图像布局转换。
声明:
ptr<vsg::ImageMemoryBarrier> createImageMemoryBarrier(ptr<vsg::Image> image, VkImageSubresourceRange subresourceRange, VkImageLayout oldImageLayout, VkImageLayout newImageLayout)
参数:
- image:ptr<vsg::Image> - 需要进行布局转换的图像
- subresourceRange:VkImageSubresourceRange - 图像的子资源范围
- oldImageLayout:VkImageLayout - 图像的旧布局
- newImageLayout:VkImageLayout - 图像的新布局
返回值: ptr<vsg::ImageMemoryBarrier> - 创建的图像内存屏障对象
注意事项:
- 函数会根据旧布局和新布局自动设置适当的访问掩码
- 支持多种常见的布局转换场景
创建一个用于图像布局转换的管线屏障。
声明:
ptr<vsg::PipelineBarrier> createImageLayoutPipelineBarrier(ptr<vsg::Image> image, VkImageLayout oldImageLayout, VkImageLayout newImageLayout, VkImageSubresourceRange subresourceRange, VkPipelineStageFlags srcStageMask = VK_PIPELINE_STAGE_ALL_COMMANDS_BIT, VkPipelineStageFlags dstStageMask = VK_PIPELINE_STAGE_ALL_COMMANDS_BIT)
参数:
- image:ptr<vsg::Image> - 需要进行布局转换的图像
- oldImageLayout:VkImageLayout - 图像的旧布局
- newImageLayout:VkImageLayout - 图像的新布局
- subresourceRange:VkImageSubresourceRange - 图像的子资源范围
- srcStageMask:VkPipelineStageFlags - 源管线阶段掩码(默认为ALL_COMMANDS_BIT)
- dstStageMask:VkPipelineStageFlags - 目标管线阶段掩码(默认为ALL_COMMANDS_BIT)
返回值: ptr<vsg::PipelineBarrier> - 创建的管线屏障对象
注意事项:
- 此函数使用createImageMemoryBarrier创建图像内存屏障
- 默认的管线阶段掩码为ALL_COMMANDS_BIT,可以根据需要进行调整
创建一个用于图像布局转换的管线屏障,使用简化的参数。
声明:
ptr<vsg::PipelineBarrier> createImageLayoutPipelineBarrier(ptr<vsg::Image> image, VkImageAspectFlags aspectMask, VkImageLayout oldImageLayout, VkImageLayout newImageLayout, VkPipelineStageFlags srcStageMask = VK_PIPELINE_STAGE_ALL_COMMANDS_BIT, VkPipelineStageFlags dstStageMask = VK_PIPELINE_STAGE_ALL_COMMANDS_BIT)
参数:
- image:ptr<vsg::Image> - 需要进行布局转换的图像
- aspectMask:VkImageAspectFlags - 图像的方面掩码
- oldImageLayout:VkImageLayout - 图像的旧布局
- newImageLayout:VkImageLayout - 图像的新布局
- srcStageMask:VkPipelineStageFlags - 源管线阶段掩码(默认为ALL_COMMANDS_BIT)
- dstStageMask:VkPipelineStageFlags - 目标管线阶段掩码(默认为ALL_COMMANDS_BIT)
返回值: ptr<vsg::PipelineBarrier> - 创建的管线屏障对象
注意事项:
- 此函数是createImageLayoutPipelineBarrier的重载版本,简化了子资源范围的设置
- 默认子资源范围设置为单个mip级别和单个数组层
创建各种图像资源,包括环境立方体贴图、BRDF查找表、辐照度立方体贴图和预过滤环境立方体贴图。
声明:
void createResources(VsgContext& vsgContext)
参数:
- vsgContext:VsgContext& - VSG上下文对象
返回值: void
注意事项:
- 函数创建多个图像资源和相关的采样器
- 设置了同步用的VkEvent对象
- 创建了天空盒的顶点和索引数据
- 初始化了一些参数缓冲
清理和重置所有创建的资源。
声明:
void clearResources()
参数: 无
返回值: void
注意事项:
- 函数主要通过将指针设置为nullptr来清理资源
- 大部分清理代码被注释掉了,可能是为了优化性能或保留某些资源
- 清空了appData、textures、gVkEvents、gSkyboxCube和gEnvmapRect等全局变量
- 清空了shaderSets容器
加载HDR环境贴图并创建相应的图像、采样器和图像信息。
声明:
void loadEnvmapRect(VsgContext& context, const std::string& filePath)
参数:
- context:VsgContext& - VSG上下文
- filePath:const std::string& - HDR文件路径
返回值: void
注意事项:
- 使用STBI加载器读取HDR图像
- 创建一个2D数组来存储图像数据
- 设置采样器的地址模式为CLAMP_TO_EDGE
- 创建ImageInfo对象,包含采样器、图像和布局信息
使用stb_image库加载HDR文件。
声明:
float *loadHdrFile(const std::string& filepath, int& width, int& height, int& channels)
参数:
- filepath:const std::string& - HDR文件路径
- width:int& - 输出参数,图像宽度
- height:int& - 输出参数,图像高度
- channels:int& - 输出参数,图像通道数
返回值: float* - 加载的图像数据指针
注意事项:
- 使用stbi_loadf函数加载HDR文件
- 强制加载为4通道(RGBA)格式
从等距矩形HDR环境贴图生成立方体贴图。
声明:
void generateEnvmap(VsgContext& vsgContext)
参数:
- vsgContext:VsgContext& - VSG上下文
返回值: void
注意事项:
- 加载等距矩形HDR环境贴图
- 创建离屏帧缓冲用于渲染立方体贴图的每个面
- 设置图形管线,包括顶点和片段着色器
- 为立方体贴图的每个面创建渲染通道
- 使用CopyImage和BlitImage命令将渲染结果复制到立方体贴图
- 生成立方体贴图的mipmap级别
- 设置内存屏障和事件,以便后续处理
生成BRDF查找表(Look-Up Table)。
声明:
void generateBRDFLUT(VsgContext &vsgContext)
参数:
- vsgContext:VsgContext& - VSG上下文
返回值: void
注意事项:
- 创建全屏四边形顶点着色器和BRDF LUT片段着色器
- 设置渲染目标为R16G16格式的512x512图像
- 创建渲染通道、帧缓冲和渲染图
- 设置图形管线状态,包括顶点输入、光栅化、混合等
- 创建命令图并添加到查看器中执行
生成辐照度立方体贴图。
声明:
void generateIrradianceCube(VsgContext& vsgContext)
参数:
- vsgContext:VsgContext& - VSG上下文
返回值: void
注意事项:
- 使用天空盒网格着色器生成辐照度立方体贴图
- 为每个面和每个mip级别创建渲染通道
- 使用CopyImage命令将渲染结果复制到辐照度立方体贴图
- 设置内存屏障以确保正确的图像布局转换
- 等待环境立方体贴图生成完成后再开始处理
生成预过滤环境立方体贴图。
声明:
void generatePrefilteredEnvmapCube(VsgContext& vsgContext)
参数:
- vsgContext:VsgContext& - VSG上下文
返回值: void
注意事项:
- 使用天空盒网格着色器生成预过滤环境立方体贴图
- 为每个面和每个mip级别创建渲染通道
- 使用推送常量传递面索引和粗糙度信息
- 使用CopyImage命令将渲染结果复制到预过滤环境立方体贴图
- 设置内存屏障以确保正确的图像布局转换
- 等待环境立方体贴图生成完成后再开始处理
创建并返回用于渲染天空盒的VSG节点。
声明:
ptr<StateGroup> drawSkyboxVSGNode(VsgContext& context)
参数:
- context:VsgContext& - VSG上下文对象,包含渲染所需的各种资源和状态
返回值: ptr<StateGroup> - 包含天空盒渲染所需的所有状态和命令的StateGroup节点
注意事项:
- 使用自定义的顶点和片段着色器
- 设置了无面剔除和禁用深度测试的渲染状态
- 使用环境立方体贴图作为天空盒纹理
- 包含色调映射参数(曝光和伽玛)的uniform buffer
创建并返回一个自定义的基于物理的渲染(PBR)着色器集。
声明:
vsg::ref_ptr<vsg::ShaderSet> customPbrShaderSet(vsg::ref_ptr<const vsg::Options> options)
参数:
- options:vsg::ref_ptr<const vsg::Options> - VSG选项对象,包含着色器文件路径等配置信息
返回值: vsg::ref_ptrvsg::ShaderSet - 包含PBR渲染所需的所有着色器、属性绑定和描述符绑定的着色器集
注意事项:
- 使用自定义的顶点和片段着色器
- 设置了多个描述符集,包括材质、视图和自定义IBL相关的描述符
- 包含多个可选的预处理器定义
- 支持实例化、位移贴图和广告牌等特性
创建一个测试场景,包含一个11x11的球体网格,每个球体具有不同的粗糙度和金属度。
声明:
vsg::ref_ptr<vsg::Node> createTestScene(vsg::ref_ptr<vsg::Options> options, bool requiresBase = true)
参数:
- options:vsg::ref_ptr<vsg::Options> - VSG选项对象,包含场景创建所需的配置信息
- requiresBase:bool - 是否需要创建底座(默认为true,但在当前实现中未使用)
返回值: vsg::ref_ptr<vsg::Node> - 包含整个测试场景的根节点
注意事项:
- 使用customPbrShaderSet创建的着色器集
- 每个球体的粗糙度和金属度根据其在网格中的位置进行设置
- 球体被放置在一个3x3的网格中,中心位于原点
创建并返回用于IBL(基于图像的照明)演示的完整场景图。
声明:
ptr<Node> iblDemoSceneGraph(VsgContext& context)
参数:
- context:VsgContext& - VSG上下文对象,包含场景创建所需的各种资源和状态
返回值: ptr<Node> - 包含整个IBL演示场景的根节点
注意事项:
- 使用customPbrShaderSet创建自定义的PBR着色器集
- 调用createTestScene创建测试场景
- 当前实现中注释掉了一些可能用于设置IBL相关描述符集的代码 // 每次渲染循环都调用 int Update();