Vulkan笔记(十四)-同步设定绘制三角形

图形管道创建完毕就可以渲染绘制内容到屏幕了


void CVulkanApp::drawFrame()
{
    uint32_t imageIndex;
    vkAcquireNextImageKHR(logicDevice_, swapChain_, UINT64_MAX, imageAvaliableSemaphore_[curFrame], nullptr, &imageIndex);

    vkWaitForFences(logicDevice_, 1, &inFlightFence_[curFrame], VK_TRUE, UINT64_MAX);
    vkResetFences(logicDevice_, 1, &inFlightFence_[curFrame]);
    vkResetCommandBuffer(commandBuffer_[curFrame], 0);
    recordCommandBuffer(commandBuffer_[curFrame], imageIndex);
    updateUBOBuffer(curFrame);

    VkSemaphore waitSemaphores[] = { imageAvaliableSemaphore_[curFrame]};
    VkSemaphore signalSemaphores[] = { renderFinishedSemaphore_[curFrame]};
    VkPipelineStageFlags waitPipelineStages[] = { VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT};

    VkSubmitInfo submitInfo{};
    submitInfo.sType = VK_STRUCTURE_TYPE_SUBMIT_INFO;
    submitInfo.waitSemaphoreCount = 1;
    submitInfo.pWaitSemaphores = waitSemaphores;
    submitInfo.pWaitDstStageMask = waitPipelineStages;
    submitInfo.commandBufferCount = 1;
    submitInfo.pCommandBuffers = &commandBuffer_[curFrame];
    submitInfo.signalSemaphoreCount = 1;
    submitInfo.pSignalSemaphores = signalSemaphores;

    if (vkQueueSubmit(graphicsQueue_, 1, &submitInfo, inFlightFence_[curFrame]) != VK_SUCCESS)
    {
        throw std::runtime_error("failed to submit queue!");
    }

    VkSwapchainKHR swapChain[] = { swapChain_ };
    VkPresentInfoKHR presentInfo{};
    presentInfo.sType = VK_STRUCTURE_TYPE_PRESENT_INFO_KHR;
    presentInfo.waitSemaphoreCount = 1;
    presentInfo.pWaitSemaphores = signalSemaphores;
    presentInfo.swapchainCount = 1;
    presentInfo.pSwapchains = swapChain;
    presentInfo.pImageIndices = &imageIndex;
    presentInfo.pResults = nullptr;
    vkQueuePresentKHR(presentsQueue_, &presentInfo);

    curFrame = (curFrame + 1) % MAX_FRAME;
}

以下是对这段代码解释

1. 图像获取与同步准备

  • vkAcquireNextImageKHR

    从交换链获取下一帧可用的图像索引(imageIndex)。

    • UINT64_MAX表示无限等待直到图像可用;

    • imageAvaliableSemaphore_[curFrame]作为信号量,在图像就绪时被触发。

  • 同步等待与重置

    • vkWaitForFences:阻塞CPU直到前一帧的围栏(inFlightFence_[curFrame])完成(避免GPU过载)。

    • vkResetFences:重置围栏状态,为当前帧做准备。

    • vkResetCommandBuffer:重置命令缓冲区,确保其可被重新录制。


2. 命令缓冲区录制与提交

  • recordCommandBuffer

    录制绘制命令到当前帧的命令缓冲区(如绑定管线、设置视口、执行绘制调用。

  • updateUBOBuffer

    更新Uniform缓冲区数据(如模型/视图矩阵等动态数据)。

  • 提交渲染命令

    • waitSemaphores:等待 imageAvaliableSemaphore_确保图像就绪;

    • waitPipelineStages:指定等待阶段为颜色附件输出(避免提前渲染);

    • signalSemaphores:渲染完成后触发 renderFinishedSemaphore_

    • 绑定当前帧的命令缓冲区。

    • VkSubmitInfo 配置:

    • vkQueueSubmit

      提交命令到图形队列,并关联当前帧的围栏(GPU完成后触发该围栏)。


3. 图像呈现与帧循环

  • vkQueuePresentKHR

    将渲染结果提交到呈现队列:

    • 等待 renderFinishedSemaphore_确保渲染完成;

    • 指定交换链和获取的图像索引(imageIndex)。

  • 帧索引循环

    • curFrame = (curFrame + 1) % MAX_FRAME

      循环使用帧资源(实现多帧并行,如双缓冲/三缓冲)。


4. 关键同步机制解析

  • 信号量(Semaphore)

    • imageAvaliableSemaphore_:协调 图像获取 与 渲染开始(GPU间同步)。

    • renderFinishedSemaphore_:协调 渲染完成 与 图像呈现(GPU间同步)。

  • 围栏(Fence)

    • inFlightFence_:确保CPU等待GPU完成前一帧,防止命令缓冲区冲突(CPU-GPU同步)。


5. 多帧并行设计

  • MAX_FRAME的作用

    允许同时处理多帧(如设为2时,CPU可录制第N帧命令,而GPU执行第N-1帧),提升GPU利用率。

  • 资源隔离

    每帧拥有独立的命令缓冲区、信号量和围栏,避免同步干扰。

显示样式如下:

于2024年4月-2025年9月期间,研究团队在贵州习水国家级自然保护区制定39条样线,涵盖灌木林、常绿阔叶林、针叶林、常绿落叶阔叶混交林、针阔混交林等不同植被类型,每条样线分春夏秋冬4个季节采集样品,用真菌采集软件记录经纬度、海拔、采集地点、时间、生境等信息,使用佳能相机(R6 mark Ⅱ)对大型真菌进行拍照,并采集标本,标本存放于贵州省生物研究所大型真菌标本馆(HGAMF)。 通过形态学初步鉴定,结合分子生物学最终鉴定,参考已]报道的中国毒蘑菇名录开展毒蘑菇的认定。 调查到保护区内有毒真菌7目25科64种,导致中毒的主要类型有急性肾衰竭型、神经精神型胃肠炎型。最终形成贵州习水国家级自然保护区大型有毒真菌图片数据集,它由以下2个部分组成。 (1)附件1包含78张原始照片(.JPG),照片名字包括了大型有毒真菌的拉丁名中文名,若无中文名的直接用拉丁名。 (2)附件2是一个压缩文件,包含了2张工作表,其中一张表是大型有毒真菌39条样线的信息,另一张表是大型有毒真菌的中毒类型。 照片采用佳能相机R6 mark Ⅱ拍摄,物种鉴定通过多种文献核实,并经两位以上专家鉴定确认。该数据集可为研究地及周边的普通人识别有毒大型真菌提供参考,通过及时的图片对比,能有效避免误采误食大型有毒真菌,同时为因误食大型真菌可能引发的身体损伤进行了总结,能为患者及时治疗提供参考。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值