您的位置:首页 > 编程语言

Vulkan编程指南翻译 第五章 展现 第5节 开始呈现

2017-03-03 16:04 435 查看
5.6 开始显示

显示,是在队列上下文中发生的操作。一般,提交到队列的命令缓冲区中的命令被执行时,会产生用来显示

图像,所以,这些图像只有在渲染操作完成后才能展示给用户。一个系统中一个设备可以支持多个队列,

它们不必都支持显示。在你可以使用队列来在画幕上显示之前,你必须判断队列是否支持在某个画幕上

显示。

要想知道一个队列是否支持显示,传递物理设备,画幕,队列组到vkGetPhysicalDeviceSurfaceSupportKHR()函数

并调用,函数原型如下:
VkResult vkGetPhysicalDeviceSurfaceSupportKHR(
VkPhysicalDevice physicalDevice,
uint32_t queueFamilyIndex,
VkSurfaceKHR surface,
VkBool32* pSupported);

需要查询的物理设备通过physicalDevice传递。所有的队列都属于一个队列族,所有属于一个队列族

的队列都被认为有相同的属性。因此,只需要判断一个队列所属的族是否支持显示。队列组索引通过

queueFamilyIndex传递。

队列显示的能力取决于画幕。例如,一些队列可能在操作系统上的两个窗口显示,但是并没有全屏显示这样的物理设备

直接访问权限。因此,你想显示所在的画幕通过surface传递。

如果vkGetPhysicalDeviceSurfaceSupportKHR()调用成功,在某个队列族的队列在surface这个画幕上

的能力通过会被写入的pSupported指针表示--VK_TRUE表示支持,VK_FALSE表示缺乏支持。如果有错误,

vkGetPhysicalDeviceSurfaceSupportKHR()将返回一个错误码,pSupported的值就不会被覆写。

在图像能够被显示之前,它必须被正确的布局。这个布局状态是VK_IMAGE_LAYOUT_PRESENT_SRC_KHR。

图像可从一个布局迁移到另一个布局,我们在第二章“内存和资源”中讲解过。” Listing5.2 

将展示如何使用图像内存屏障把图像从VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL迁移到

VK_IMAGE_LAYOUT_PRESENT_SRC_KHR布局。
Listing 5.2: Transitioning an Image to Present Source

const VkImageMemoryBarrier barrier =
{
VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER, // sType
nullptr, // pNext
VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, // srcAccessMask
VK_ACCESS_MEMORY_READ_BIT, // dstAccessMask
VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL, // oldLayout
VK_IMAGE_LAYOUT_PRESENT_SRC_KHR, // newLayout
0, // srcQueueFamilyIndex
0, // dstQueueFamilyIndex
sourceImage, // image
{ // subresourceRange
VK_IMAGE_ASPECT_COLOR_BIT, // aspectMask
0, // baseMipLevel
1, // levelCount
0, // baseArrayLayer
1, // layerCount
}
};

vkCmdPipelineBarrier(cmdBuffer,
VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT,
VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT,
0,
0, nullptr,
0, nullptr,
1, &barrier);

注意,图像内存屏障在一个命令缓冲区内执行,这个命令缓冲区应该提交到一个队列以被执行。

一旦图像处于 VK_IMAGE_LAYOUT_PRESENT_SRC_KHR布局,它就可以通过调用vkQueuePresentKHR()被显示给用户了

其原型为:
VkResult vkQueuePresentKHR(
VkQueue queue,
const VkPresentInfoKHR* pPresentInfo);

图像提交以显示的队列通过queue指定。这个命令剩下的参数通过一个VkPresentInfoKHR

类型的实例传递,该类型定义为:
typedef struct VkPresentInfoKHR {
VkStructureType sType;
const void* pNext;
uint32_t waitSemaphoreCount;
const VkSemaphore* pWaitSemaphores;
uint32_t swapchainCount;
const VkSwapchainKHR* pSwapchains;
const uint32_t* pImageIndices;
VkResult* pResults;
} VkPresentInfoKHR;

VkPresentInfoKHR的sType应置为VK_STRUCTURE_TYPE_PRESENT_INFO_KHR,pNext应置为nullptr。在图像

被显示之前,Vulkan将选择性等待一个或者多个信号量来使渲染图像和显示保持同步。需等待的信号量个数

通过waitSemaphoreCount成员传递,pWaitSemaphores成员指向了一个包含所有需要等待的信号量的hanlde的数组。

一次vkQueuePresentKHR()调用会同时向多个交换链中提交多个图像。这很有用,例如,一个应用程序正在向

多个窗口同时渲染。需要呈现的图像个数通过swapchainCount指定,pSwapchains是呈现图像的交换链对象数组。

呈现到每一个交换链的图像不通过VkImage类型的handle被引用,需通过它们在交换链对象中

获取到的交换链图像数组中的索引来引用。对于每一个被呈现图像的交换链,图像的索引通过对应数组pImageIndices

中的元素的索引传递。

每一个单独的通过调用vkQueuePresentKHR()触发的呈现操作可以产生自己的返回码。记住,VkResult中的一些值表示成功,。

pResults是指向了一个大小为swapchainCount的数组。多个VkResult变量将会被呈现操作的结果填充。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: