Vulkan窗口调整大小时重建swapchain与viewport动态状态的差异及选型
Vulkan窗口resize两种实现方案的区别与适用场景
核心区别
- 方案1:重建
swapchain及关联对象
核心逻辑是窗口尺寸变化后,直接销毁旧的swapchain,基于新的窗口尺寸重新创建swapchain,同时重新创建所有和swapchain绑定的对象,包括framebuffer、render pass(如果依赖swapchain图像格式/尺寸)、深度缓冲、纹理采样相关的视图等。整个过程需要等待设备空闲,避免现有渲染指令访问已销毁的资源。- 性能开销:开销较高,重建过程会产生短暂的卡顿,需要额外处理旧资源的生命周期,避免内存泄漏。
- 能力范围:可以适配任意窗口尺寸变化,支持
swapchain图像格式、呈现模式、图像数量的同步调整,完全匹配新的窗口可绘制区域。
- 方案2:动态
viewport状态适配
核心逻辑是在创建图形管线时就将VK_DYNAMIC_STATE_VIEWPORT和VK_DYNAMIC_STATE_SCISSOR设置为动态状态,窗口尺寸变化时不需要重建swapchain,只需要在录制命令缓冲时调用vkCmdSetViewport和vkCmdSetScissor传入新的尺寸即可。- 性能开销:开销极低,只需要修改命令缓冲的参数,不需要销毁重建任何资源,无卡顿。
- 能力范围:无法适配
swapchain本身尺寸和窗口尺寸不匹配的情况,如果窗口拉伸超过了初始创建swapchain时的最大尺寸,会出现画面裁剪、拉伸变形或者黑边。
适用场景
- 选择重建
swapchain方案的场景:- 应用支持无限制的窗口缩放,或者需要支持全屏/窗口化切换的场景
- 对画面显示质量要求高,不能接受拉伸变形、黑边或者裁剪的场景
- 应用本身就有定期重建资源的逻辑,或者resize触发频率较低的场景
- 选择动态
viewport方案的场景:- 应用的窗口尺寸只会在预设的小范围内调整,或者初始创建
swapchain时就设置了足够大的最大尺寸的场景 - 对resize过程的流畅度要求极高,不能接受任何卡顿的实时渲染场景
- 临时适配小范围尺寸调整,配合重建
swapchain做优化:比如用户拖拽窗口边缘调整大小的过程中用动态viewport临时适配,拖拽结束后再重建swapchain匹配最终尺寸,兼顾流畅度和显示质量。
- 应用的窗口尺寸只会在预设的小范围内调整,或者初始创建
注意:大部分生产级Vulkan应用会结合两种方案使用,拖拽调整过程中用动态
viewport避免高频重建卡顿,调整结束后再重建swapchain保证画面正确。
内容的提问来源于stack exchange,提问作者Balgy
相关产品推荐
相关产品推荐

