mirror of
https://github.com/MobileGL-Dev/MobileGL
synced 2026-09-11 21:58:31 +09:00
[Chore] (MG_Backend/DirectVulkan): manage default depth buffer in SwapchainObject
This commit is contained in:
@@ -38,6 +38,40 @@ static const char* string_VkSurfaceTransformFlagBitsKHR(VkSurfaceTransformFlagBi
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
namespace MobileGL::MG_Backend::DirectVulkan {
|
namespace MobileGL::MG_Backend::DirectVulkan {
|
||||||
|
namespace {
|
||||||
|
Bool HasStencilComponent(VkFormat format) {
|
||||||
|
return format == VK_FORMAT_D24_UNORM_S8_UINT || format == VK_FORMAT_D32_SFLOAT_S8_UINT;
|
||||||
|
}
|
||||||
|
|
||||||
|
VkFormat FindSupportedDepthStencilFormat(VkPhysicalDevice physicalDevice) {
|
||||||
|
const VkFormat candidates[] = {VK_FORMAT_D24_UNORM_S8_UINT, VK_FORMAT_D32_SFLOAT_S8_UINT,
|
||||||
|
VK_FORMAT_D32_SFLOAT};
|
||||||
|
for (VkFormat format : candidates) {
|
||||||
|
VkFormatProperties props{};
|
||||||
|
vkGetPhysicalDeviceFormatProperties(physicalDevice, format, &props);
|
||||||
|
if ((props.optimalTilingFeatures & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT) != 0) {
|
||||||
|
return format;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return VK_FORMAT_UNDEFINED;
|
||||||
|
}
|
||||||
|
|
||||||
|
Uint32 FindMemoryType(VkPhysicalDevice physicalDevice, Uint32 typeFilter, VkMemoryPropertyFlags properties) {
|
||||||
|
VkPhysicalDeviceMemoryProperties memProperties{};
|
||||||
|
vkGetPhysicalDeviceMemoryProperties(physicalDevice, &memProperties);
|
||||||
|
|
||||||
|
for (Uint32 i = 0; i < memProperties.memoryTypeCount; i++) {
|
||||||
|
if ((typeFilter & (1 << i)) &&
|
||||||
|
(memProperties.memoryTypes[i].propertyFlags & properties) == properties) {
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
MOBILEGL_ASSERT(false, "Failed to find suitable memory type.");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
} // namespace
|
||||||
|
|
||||||
SwapchainObject::SwapchainCapabilities SwapchainObject::GetSwapchainCapabilities(VkPhysicalDevice physicalDevice,
|
SwapchainObject::SwapchainCapabilities SwapchainObject::GetSwapchainCapabilities(VkPhysicalDevice physicalDevice,
|
||||||
VkSurfaceKHR surface) {
|
VkSurfaceKHR surface) {
|
||||||
SwapchainCapabilities swapchainCapabilities{};
|
SwapchainCapabilities swapchainCapabilities{};
|
||||||
@@ -190,12 +224,104 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
m_imageLayouts.assign(imageCount, VK_IMAGE_LAYOUT_UNDEFINED);
|
m_imageLayouts.assign(imageCount, VK_IMAGE_LAYOUT_UNDEFINED);
|
||||||
|
|
||||||
CreateImageViews(device);
|
CreateImageViews(device);
|
||||||
|
CreateDepthStencilResources(device, physicalDevice);
|
||||||
|
|
||||||
MGLOG_I("Swapchain created, extent = %dx%d, swapchain imageCount = %d", m_extent.width, m_extent.height,
|
MGLOG_I("Swapchain created, extent = %dx%d, swapchain imageCount = %d", m_extent.width, m_extent.height,
|
||||||
imageCount);
|
imageCount);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SwapchainObject::CreateDepthStencilResources(VkDevice device, VkPhysicalDevice physicalDevice) {
|
||||||
|
DestroyDepthStencilResources(device);
|
||||||
|
|
||||||
|
const auto imageCount = static_cast<Uint32>(m_images.size());
|
||||||
|
if (imageCount == 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_depthStencilFormat = FindSupportedDepthStencilFormat(physicalDevice);
|
||||||
|
MOBILEGL_ASSERT(m_depthStencilFormat != VK_FORMAT_UNDEFINED, "No supported depth/stencil format found.");
|
||||||
|
|
||||||
|
m_depthStencilImages.assign(imageCount, VK_NULL_HANDLE);
|
||||||
|
m_depthStencilImageMemories.assign(imageCount, VK_NULL_HANDLE);
|
||||||
|
m_depthStencilImageViews.assign(imageCount, VK_NULL_HANDLE);
|
||||||
|
m_depthStencilImageLayouts.assign(imageCount, VK_IMAGE_LAYOUT_UNDEFINED);
|
||||||
|
|
||||||
|
for (Uint32 i = 0; i < imageCount; ++i) {
|
||||||
|
VkImageCreateInfo imageInfo{};
|
||||||
|
imageInfo.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO;
|
||||||
|
imageInfo.imageType = VK_IMAGE_TYPE_2D;
|
||||||
|
imageInfo.extent.width = m_extent.width;
|
||||||
|
imageInfo.extent.height = m_extent.height;
|
||||||
|
imageInfo.extent.depth = 1;
|
||||||
|
imageInfo.mipLevels = 1;
|
||||||
|
imageInfo.arrayLayers = 1;
|
||||||
|
imageInfo.format = m_depthStencilFormat;
|
||||||
|
imageInfo.tiling = VK_IMAGE_TILING_OPTIMAL;
|
||||||
|
imageInfo.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
|
||||||
|
imageInfo.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
|
||||||
|
imageInfo.samples = VK_SAMPLE_COUNT_1_BIT;
|
||||||
|
imageInfo.sharingMode = VK_SHARING_MODE_EXCLUSIVE;
|
||||||
|
VK_VERIFY(vkCreateImage(device, &imageInfo, nullptr, &m_depthStencilImages[i]), "vkCreateImage(depth)");
|
||||||
|
|
||||||
|
VkMemoryRequirements memRequirements{};
|
||||||
|
vkGetImageMemoryRequirements(device, m_depthStencilImages[i], &memRequirements);
|
||||||
|
|
||||||
|
VkMemoryAllocateInfo allocInfo{};
|
||||||
|
allocInfo.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO;
|
||||||
|
allocInfo.allocationSize = memRequirements.size;
|
||||||
|
allocInfo.memoryTypeIndex =
|
||||||
|
FindMemoryType(physicalDevice, memRequirements.memoryTypeBits, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT);
|
||||||
|
VK_VERIFY(vkAllocateMemory(device, &allocInfo, nullptr, &m_depthStencilImageMemories[i]),
|
||||||
|
"vkAllocateMemory(depth)");
|
||||||
|
VK_VERIFY(vkBindImageMemory(device, m_depthStencilImages[i], m_depthStencilImageMemories[i], 0),
|
||||||
|
"vkBindImageMemory(depth)");
|
||||||
|
|
||||||
|
VkImageViewCreateInfo viewInfo{};
|
||||||
|
viewInfo.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO;
|
||||||
|
viewInfo.image = m_depthStencilImages[i];
|
||||||
|
viewInfo.viewType = VK_IMAGE_VIEW_TYPE_2D;
|
||||||
|
viewInfo.format = m_depthStencilFormat;
|
||||||
|
viewInfo.subresourceRange.aspectMask = VK_IMAGE_ASPECT_DEPTH_BIT;
|
||||||
|
if (HasStencilComponent(m_depthStencilFormat)) {
|
||||||
|
viewInfo.subresourceRange.aspectMask |= VK_IMAGE_ASPECT_STENCIL_BIT;
|
||||||
|
}
|
||||||
|
viewInfo.subresourceRange.baseMipLevel = 0;
|
||||||
|
viewInfo.subresourceRange.levelCount = 1;
|
||||||
|
viewInfo.subresourceRange.baseArrayLayer = 0;
|
||||||
|
viewInfo.subresourceRange.layerCount = 1;
|
||||||
|
VK_VERIFY(vkCreateImageView(device, &viewInfo, nullptr, &m_depthStencilImageViews[i]),
|
||||||
|
"vkCreateImageView(depth)");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void SwapchainObject::DestroyDepthStencilResources(VkDevice device) {
|
||||||
|
for (auto view : m_depthStencilImageViews) {
|
||||||
|
if (view != VK_NULL_HANDLE) {
|
||||||
|
vkDestroyImageView(device, view, nullptr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
m_depthStencilImageViews.clear();
|
||||||
|
|
||||||
|
for (auto image : m_depthStencilImages) {
|
||||||
|
if (image != VK_NULL_HANDLE) {
|
||||||
|
vkDestroyImage(device, image, nullptr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
m_depthStencilImages.clear();
|
||||||
|
|
||||||
|
for (auto memory : m_depthStencilImageMemories) {
|
||||||
|
if (memory != VK_NULL_HANDLE) {
|
||||||
|
vkFreeMemory(device, memory, nullptr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
m_depthStencilImageMemories.clear();
|
||||||
|
m_depthStencilImageLayouts.clear();
|
||||||
|
m_depthStencilFormat = VK_FORMAT_UNDEFINED;
|
||||||
|
}
|
||||||
|
|
||||||
void SwapchainObject::Shutdown(VkDevice device) {
|
void SwapchainObject::Shutdown(VkDevice device) {
|
||||||
|
DestroyDepthStencilResources(device);
|
||||||
|
|
||||||
for (auto imageView : m_imageViews) {
|
for (auto imageView : m_imageViews) {
|
||||||
vkDestroyImageView(device, imageView, nullptr);
|
vkDestroyImageView(device, imageView, nullptr);
|
||||||
}
|
}
|
||||||
@@ -226,6 +352,29 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
m_imageLayouts[index] = layout;
|
m_imageLayouts[index] = layout;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
VkImage SwapchainObject::GetDepthStencilImage(Uint32 index) const {
|
||||||
|
MOBILEGL_ASSERT(index < m_depthStencilImages.size(), "Swapchain depth/stencil image index out of range");
|
||||||
|
return m_depthStencilImages[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
VkImageView SwapchainObject::GetDepthStencilImageView(Uint32 index) const {
|
||||||
|
MOBILEGL_ASSERT(index < m_depthStencilImageViews.size(),
|
||||||
|
"Swapchain depth/stencil image view index out of range");
|
||||||
|
return m_depthStencilImageViews[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
VkImageLayout SwapchainObject::GetDepthStencilImageLayout(Uint32 index) const {
|
||||||
|
MOBILEGL_ASSERT(index < m_depthStencilImageLayouts.size(),
|
||||||
|
"Swapchain depth/stencil image layout index out of range");
|
||||||
|
return m_depthStencilImageLayouts[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
void SwapchainObject::SetDepthStencilImageLayout(Uint32 index, VkImageLayout layout) {
|
||||||
|
MOBILEGL_ASSERT(index < m_depthStencilImageLayouts.size(),
|
||||||
|
"Swapchain depth/stencil image layout index out of range");
|
||||||
|
m_depthStencilImageLayouts[index] = layout;
|
||||||
|
}
|
||||||
|
|
||||||
void SwapchainObject::CreateImageViews(VkDevice device) {
|
void SwapchainObject::CreateImageViews(VkDevice device) {
|
||||||
m_imageViews.resize(m_images.size(), VK_NULL_HANDLE);
|
m_imageViews.resize(m_images.size(), VK_NULL_HANDLE);
|
||||||
for (SizeT i = 0; i < m_imageViews.size(); i++) {
|
for (SizeT i = 0; i < m_imageViews.size(); i++) {
|
||||||
|
|||||||
@@ -38,6 +38,12 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
VkSurfaceTransformFlagBitsKHR GetPreTransform() const { return m_preTransform; }
|
VkSurfaceTransformFlagBitsKHR GetPreTransform() const { return m_preTransform; }
|
||||||
const Vector<VkImage>& GetImages() const { return m_images; }
|
const Vector<VkImage>& GetImages() const { return m_images; }
|
||||||
const Vector<VkImageView>& GetImageViews() const { return m_imageViews; }
|
const Vector<VkImageView>& GetImageViews() const { return m_imageViews; }
|
||||||
|
VkFormat GetDepthStencilFormat() const { return m_depthStencilFormat; }
|
||||||
|
const Vector<VkImageView>& GetDepthStencilImageViews() const { return m_depthStencilImageViews; }
|
||||||
|
VkImage GetDepthStencilImage(Uint32 index) const;
|
||||||
|
VkImageView GetDepthStencilImageView(Uint32 index) const;
|
||||||
|
VkImageLayout GetDepthStencilImageLayout(Uint32 index) const;
|
||||||
|
void SetDepthStencilImageLayout(Uint32 index, VkImageLayout layout);
|
||||||
VkImage GetImage(Uint32 index) const;
|
VkImage GetImage(Uint32 index) const;
|
||||||
VkImageLayout GetImageLayout(Uint32 index) const;
|
VkImageLayout GetImageLayout(Uint32 index) const;
|
||||||
void SetImageLayout(Uint32 index, VkImageLayout layout);
|
void SetImageLayout(Uint32 index, VkImageLayout layout);
|
||||||
@@ -45,6 +51,8 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
void CreateImageViews(VkDevice device);
|
void CreateImageViews(VkDevice device);
|
||||||
|
void CreateDepthStencilResources(VkDevice device, VkPhysicalDevice physicalDevice);
|
||||||
|
void DestroyDepthStencilResources(VkDevice device);
|
||||||
static constexpr VkPresentModeKHR s_desiredPresentModes[] {
|
static constexpr VkPresentModeKHR s_desiredPresentModes[] {
|
||||||
VK_PRESENT_MODE_MAILBOX_KHR,
|
VK_PRESENT_MODE_MAILBOX_KHR,
|
||||||
VK_PRESENT_MODE_IMMEDIATE_KHR,
|
VK_PRESENT_MODE_IMMEDIATE_KHR,
|
||||||
@@ -59,5 +67,11 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
Vector<VkImage> m_images;
|
Vector<VkImage> m_images;
|
||||||
Vector<VkImageView> m_imageViews;
|
Vector<VkImageView> m_imageViews;
|
||||||
Vector<VkImageLayout> m_imageLayouts;
|
Vector<VkImageLayout> m_imageLayouts;
|
||||||
|
|
||||||
|
VkFormat m_depthStencilFormat = VK_FORMAT_UNDEFINED;
|
||||||
|
Vector<VkImage> m_depthStencilImages;
|
||||||
|
Vector<VkDeviceMemory> m_depthStencilImageMemories;
|
||||||
|
Vector<VkImageView> m_depthStencilImageViews;
|
||||||
|
Vector<VkImageLayout> m_depthStencilImageLayouts;
|
||||||
};
|
};
|
||||||
} // namespace MobileGL::MG_Backend::DirectVulkan
|
} // namespace MobileGL::MG_Backend::DirectVulkan
|
||||||
|
|||||||
@@ -382,16 +382,25 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void VulkanRenderer::TransitionDepthStencilImageToAttachment(VkCommandBuffer commandBuffer, Uint32 imageIndex) {
|
void VulkanRenderer::TransitionDepthStencilImageToAttachment(VkCommandBuffer commandBuffer, Uint32 imageIndex) {
|
||||||
if (m_depthStencilImageLayouts.empty()) {
|
if (m_swapchainObject.GetDepthStencilFormat() == VK_FORMAT_UNDEFINED) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Bool ok = VkTextureManager::TransitionImageLayout(commandBuffer, m_depthStencilImages[imageIndex],
|
VkImageAspectFlags aspectMask = VK_IMAGE_ASPECT_DEPTH_BIT;
|
||||||
m_depthStencilImageLayouts[imageIndex], VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
|
const auto depthStencilFormat = m_swapchainObject.GetDepthStencilFormat();
|
||||||
VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT, VK_PIPELINE_STAGE_EARLY_FRAGMENT_TESTS_BIT | VK_PIPELINE_STAGE_LATE_FRAGMENT_TESTS_BIT,
|
if (depthStencilFormat == VK_FORMAT_D24_UNORM_S8_UINT || depthStencilFormat == VK_FORMAT_D32_SFLOAT_S8_UINT) {
|
||||||
0, VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_READ_BIT | VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT,
|
aspectMask |= VK_IMAGE_ASPECT_STENCIL_BIT;
|
||||||
VK_IMAGE_ASPECT_DEPTH_BIT);
|
}
|
||||||
|
|
||||||
|
auto oldLayout = m_swapchainObject.GetDepthStencilImageLayout(imageIndex);
|
||||||
|
Bool ok = VkTextureManager::TransitionImageLayout(
|
||||||
|
commandBuffer, m_swapchainObject.GetDepthStencilImage(imageIndex),
|
||||||
|
oldLayout, VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
|
||||||
|
VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT,
|
||||||
|
VK_PIPELINE_STAGE_EARLY_FRAGMENT_TESTS_BIT | VK_PIPELINE_STAGE_LATE_FRAGMENT_TESTS_BIT, 0,
|
||||||
|
VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_READ_BIT | VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT, aspectMask);
|
||||||
MOBILEGL_ASSERT(ok, "TransitionDepthStencilImageToAttachment failed");
|
MOBILEGL_ASSERT(ok, "TransitionDepthStencilImageToAttachment failed");
|
||||||
|
m_swapchainObject.SetDepthStencilImageLayout(imageIndex, VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL);
|
||||||
}
|
}
|
||||||
|
|
||||||
void VulkanRenderer::EnsureFrameRecordingStarted() {
|
void VulkanRenderer::EnsureFrameRecordingStarted() {
|
||||||
@@ -1695,129 +1704,11 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
m_config.MaxFramesInFlight);
|
m_config.MaxFramesInFlight);
|
||||||
}
|
}
|
||||||
|
|
||||||
Uint32 VulkanRenderer::FindMemoryType(Uint32 typeFilter, VkMemoryPropertyFlags properties) const {
|
|
||||||
VkPhysicalDeviceMemoryProperties memProperties{};
|
|
||||||
vkGetPhysicalDeviceMemoryProperties(m_physicalDevice.handle, &memProperties);
|
|
||||||
|
|
||||||
for (Uint32 i = 0; i < memProperties.memoryTypeCount; i++) {
|
|
||||||
if ((typeFilter & (1 << i)) && (memProperties.memoryTypes[i].propertyFlags & properties) == properties) {
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
MOBILEGL_ASSERT(false, "Failed to find suitable memory type.");
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
Uint64 VulkanRenderer::BuildPendingClearKey(Uint drawFboExternalIndex, Bool targetsDefaultFramebuffer) {
|
Uint64 VulkanRenderer::BuildPendingClearKey(Uint drawFboExternalIndex, Bool targetsDefaultFramebuffer) {
|
||||||
return (static_cast<Uint64>(targetsDefaultFramebuffer ? 1 : 0) << 63) |
|
return (static_cast<Uint64>(targetsDefaultFramebuffer ? 1 : 0) << 63) |
|
||||||
static_cast<Uint64>(drawFboExternalIndex);
|
static_cast<Uint64>(drawFboExternalIndex);
|
||||||
}
|
}
|
||||||
|
|
||||||
Bool VulkanRenderer::HasStencilComponent(VkFormat format) {
|
|
||||||
return format == VK_FORMAT_D24_UNORM_S8_UINT || format == VK_FORMAT_D32_SFLOAT_S8_UINT;
|
|
||||||
}
|
|
||||||
|
|
||||||
VkFormat VulkanRenderer::FindSupportedDepthStencilFormat(VkPhysicalDevice physicalDevice) {
|
|
||||||
const VkFormat candidates[] = {VK_FORMAT_D24_UNORM_S8_UINT, VK_FORMAT_D32_SFLOAT_S8_UINT, VK_FORMAT_D32_SFLOAT};
|
|
||||||
for (VkFormat format : candidates) {
|
|
||||||
VkFormatProperties props{};
|
|
||||||
vkGetPhysicalDeviceFormatProperties(physicalDevice, format, &props);
|
|
||||||
if ((props.optimalTilingFeatures & VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT) != 0) {
|
|
||||||
return format;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return VK_FORMAT_UNDEFINED;
|
|
||||||
}
|
|
||||||
|
|
||||||
void VulkanRenderer::CreateDepthStencilResources() {
|
|
||||||
const auto imageCount = static_cast<Uint32>(m_swapchainObject.GetImageCount());
|
|
||||||
if (imageCount == 0) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
m_depthStencilFormat = FindSupportedDepthStencilFormat(m_physicalDevice.handle);
|
|
||||||
MOBILEGL_ASSERT(m_depthStencilFormat != VK_FORMAT_UNDEFINED, "No supported depth/stencil format found.");
|
|
||||||
|
|
||||||
const auto extent = m_swapchainObject.GetExtent();
|
|
||||||
m_depthStencilImages.assign(imageCount, VK_NULL_HANDLE);
|
|
||||||
m_depthStencilImageMemories.assign(imageCount, VK_NULL_HANDLE);
|
|
||||||
m_depthStencilImageViews.assign(imageCount, VK_NULL_HANDLE);
|
|
||||||
m_depthStencilImageLayouts.assign(imageCount, VK_IMAGE_LAYOUT_UNDEFINED);
|
|
||||||
|
|
||||||
for (Uint32 i = 0; i < imageCount; ++i) {
|
|
||||||
VkImageCreateInfo imageInfo{};
|
|
||||||
imageInfo.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO;
|
|
||||||
imageInfo.imageType = VK_IMAGE_TYPE_2D;
|
|
||||||
imageInfo.extent.width = extent.width;
|
|
||||||
imageInfo.extent.height = extent.height;
|
|
||||||
imageInfo.extent.depth = 1;
|
|
||||||
imageInfo.mipLevels = 1;
|
|
||||||
imageInfo.arrayLayers = 1;
|
|
||||||
imageInfo.format = m_depthStencilFormat;
|
|
||||||
imageInfo.tiling = VK_IMAGE_TILING_OPTIMAL;
|
|
||||||
imageInfo.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
|
|
||||||
imageInfo.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT;
|
|
||||||
imageInfo.samples = VK_SAMPLE_COUNT_1_BIT;
|
|
||||||
imageInfo.sharingMode = VK_SHARING_MODE_EXCLUSIVE;
|
|
||||||
VK_VERIFY(vkCreateImage(m_device, &imageInfo, nullptr, &m_depthStencilImages[i]), "vkCreateImage(depth)");
|
|
||||||
|
|
||||||
VkMemoryRequirements memRequirements{};
|
|
||||||
vkGetImageMemoryRequirements(m_device, m_depthStencilImages[i], &memRequirements);
|
|
||||||
|
|
||||||
VkMemoryAllocateInfo allocInfo{};
|
|
||||||
allocInfo.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO;
|
|
||||||
allocInfo.allocationSize = memRequirements.size;
|
|
||||||
allocInfo.memoryTypeIndex =
|
|
||||||
FindMemoryType(memRequirements.memoryTypeBits, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT);
|
|
||||||
VK_VERIFY(vkAllocateMemory(m_device, &allocInfo, nullptr, &m_depthStencilImageMemories[i]),
|
|
||||||
"vkAllocateMemory(depth)");
|
|
||||||
VK_VERIFY(vkBindImageMemory(m_device, m_depthStencilImages[i], m_depthStencilImageMemories[i], 0),
|
|
||||||
"vkBindImageMemory(depth)");
|
|
||||||
|
|
||||||
VkImageViewCreateInfo viewInfo{};
|
|
||||||
viewInfo.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO;
|
|
||||||
viewInfo.image = m_depthStencilImages[i];
|
|
||||||
viewInfo.viewType = VK_IMAGE_VIEW_TYPE_2D;
|
|
||||||
viewInfo.format = m_depthStencilFormat;
|
|
||||||
viewInfo.subresourceRange.aspectMask = VK_IMAGE_ASPECT_DEPTH_BIT;
|
|
||||||
if (HasStencilComponent(m_depthStencilFormat)) {
|
|
||||||
viewInfo.subresourceRange.aspectMask |= VK_IMAGE_ASPECT_STENCIL_BIT;
|
|
||||||
}
|
|
||||||
viewInfo.subresourceRange.baseMipLevel = 0;
|
|
||||||
viewInfo.subresourceRange.levelCount = 1;
|
|
||||||
viewInfo.subresourceRange.baseArrayLayer = 0;
|
|
||||||
viewInfo.subresourceRange.layerCount = 1;
|
|
||||||
VK_VERIFY(vkCreateImageView(m_device, &viewInfo, nullptr, &m_depthStencilImageViews[i]),
|
|
||||||
"vkCreateImageView(depth)");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void VulkanRenderer::DestroyDepthStencilResources() {
|
|
||||||
for (auto view : m_depthStencilImageViews) {
|
|
||||||
if (view != VK_NULL_HANDLE) {
|
|
||||||
vkDestroyImageView(m_device, view, nullptr);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
m_depthStencilImageViews.clear();
|
|
||||||
|
|
||||||
for (auto image : m_depthStencilImages) {
|
|
||||||
if (image != VK_NULL_HANDLE) {
|
|
||||||
vkDestroyImage(m_device, image, nullptr);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
m_depthStencilImages.clear();
|
|
||||||
|
|
||||||
for (auto memory : m_depthStencilImageMemories) {
|
|
||||||
if (memory != VK_NULL_HANDLE) {
|
|
||||||
vkFreeMemory(m_device, memory, nullptr);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
m_depthStencilImageMemories.clear();
|
|
||||||
m_depthStencilImageLayouts.clear();
|
|
||||||
m_depthStencilFormat = VK_FORMAT_UNDEFINED;
|
|
||||||
}
|
|
||||||
|
|
||||||
void VulkanRenderer::CreateCommandPool() {
|
void VulkanRenderer::CreateCommandPool() {
|
||||||
VkCommandPoolCreateInfo createInfo{VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO};
|
VkCommandPoolCreateInfo createInfo{VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO};
|
||||||
createInfo.flags = VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT;
|
createInfo.flags = VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT;
|
||||||
@@ -2015,8 +1906,6 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void VulkanRenderer::ShutdownSwapchain() {
|
void VulkanRenderer::ShutdownSwapchain() {
|
||||||
DestroyDepthStencilResources();
|
|
||||||
|
|
||||||
MOBILEGL_ASSERT(m_renderPassManager != nullptr, "ShutdownSwapchain: render pass manager is null");
|
MOBILEGL_ASSERT(m_renderPassManager != nullptr, "ShutdownSwapchain: render pass manager is null");
|
||||||
m_renderPassManager->Shutdown();
|
m_renderPassManager->Shutdown();
|
||||||
|
|
||||||
@@ -2040,16 +1929,16 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
VK_VERIFY(m_frameContext.InitializeSwapchainSemaphores(m_device,
|
VK_VERIFY(m_frameContext.InitializeSwapchainSemaphores(m_device,
|
||||||
static_cast<Uint32>(m_swapchainObject.GetImageCount())),
|
static_cast<Uint32>(m_swapchainObject.GetImageCount())),
|
||||||
"RecreateSwapchain, InitializeSwapchainSemaphores");
|
"RecreateSwapchain, InitializeSwapchainSemaphores");
|
||||||
CreateDepthStencilResources();
|
|
||||||
MOBILEGL_ASSERT(m_renderPassManager != nullptr, "RecreateSwapchain: render pass manager is null");
|
MOBILEGL_ASSERT(m_renderPassManager != nullptr, "RecreateSwapchain: render pass manager is null");
|
||||||
VkRenderPassManager::InitInfo renderPassInitInfo{};
|
VkRenderPassManager::InitInfo renderPassInitInfo{};
|
||||||
renderPassInitInfo.device = m_device;
|
renderPassInitInfo.device = m_device;
|
||||||
renderPassInitInfo.colorFormat = m_swapchainObject.GetSurfaceFormat().format;
|
renderPassInitInfo.colorFormat = m_swapchainObject.GetSurfaceFormat().format;
|
||||||
renderPassInitInfo.depthStencilFormat = m_depthStencilFormat;
|
renderPassInitInfo.depthStencilFormat = m_swapchainObject.GetDepthStencilFormat();
|
||||||
Bool ok = m_renderPassManager->Initialize(renderPassInitInfo);
|
Bool ok = m_renderPassManager->Initialize(renderPassInitInfo);
|
||||||
MOBILEGL_ASSERT(ok, "RecreateSwapchain: render pass manager initialization failed");
|
MOBILEGL_ASSERT(ok, "RecreateSwapchain: render pass manager initialization failed");
|
||||||
ok = m_renderPassManager->RecreateDefaultFramebuffers(
|
ok = m_renderPassManager->RecreateDefaultFramebuffers(m_swapchainObject.GetImageViews(),
|
||||||
m_swapchainObject.GetImageViews(), m_depthStencilImageViews, m_swapchainObject.GetExtent());
|
m_swapchainObject.GetDepthStencilImageViews(),
|
||||||
|
m_swapchainObject.GetExtent());
|
||||||
MOBILEGL_ASSERT(ok, "RecreateSwapchain: default framebuffers initialization failed");
|
MOBILEGL_ASSERT(ok, "RecreateSwapchain: default framebuffers initialization failed");
|
||||||
if (m_pipelineFactory) {
|
if (m_pipelineFactory) {
|
||||||
m_pipelineFactory->DestroyAll();
|
m_pipelineFactory->DestroyAll();
|
||||||
|
|||||||
@@ -123,12 +123,6 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
|
|
||||||
VkCommandPool m_commandPool = VK_NULL_HANDLE;
|
VkCommandPool m_commandPool = VK_NULL_HANDLE;
|
||||||
|
|
||||||
VkFormat m_depthStencilFormat = VK_FORMAT_UNDEFINED;
|
|
||||||
Vector<VkImage> m_depthStencilImages;
|
|
||||||
Vector<VkDeviceMemory> m_depthStencilImageMemories;
|
|
||||||
Vector<VkImageView> m_depthStencilImageViews;
|
|
||||||
Vector<VkImageLayout> m_depthStencilImageLayouts;
|
|
||||||
|
|
||||||
Vector<VkBufferObject> m_frameVertexUploadBuffers;
|
Vector<VkBufferObject> m_frameVertexUploadBuffers;
|
||||||
Vector<VkDeviceSize> m_frameVertexUploadHeads;
|
Vector<VkDeviceSize> m_frameVertexUploadHeads;
|
||||||
Vector<VkBufferObject> m_frameIndexUploadBuffers;
|
Vector<VkBufferObject> m_frameIndexUploadBuffers;
|
||||||
@@ -166,8 +160,6 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
void CreateSwapchain();
|
void CreateSwapchain();
|
||||||
void CreateCommandPool();
|
void CreateCommandPool();
|
||||||
void CreateFrameContexts();
|
void CreateFrameContexts();
|
||||||
void CreateDepthStencilResources();
|
|
||||||
void DestroyDepthStencilResources();
|
|
||||||
Bool GetDefaultRenderTargetForCurrentImage(VkRenderPass& outRenderPass, VkFramebuffer& outFramebuffer,
|
Bool GetDefaultRenderTargetForCurrentImage(VkRenderPass& outRenderPass, VkFramebuffer& outFramebuffer,
|
||||||
VkExtent2D& outExtent, VkFormat& outDepthStencilFormat) const;
|
VkExtent2D& outExtent, VkFormat& outDepthStencilFormat) const;
|
||||||
Bool EnsureOffscreenRenderTarget(Uint glFboExternalIndex, const MG_State::GLState::FramebufferObject& glFbo,
|
Bool EnsureOffscreenRenderTarget(Uint glFboExternalIndex, const MG_State::GLState::FramebufferObject& glFbo,
|
||||||
@@ -207,10 +199,7 @@ namespace MobileGL::MG_Backend::DirectVulkan {
|
|||||||
static Bool GetMoreCapablePhysicalDevice(VkPhysicalDevice newVkDevice, VkSurfaceKHR surface,
|
static Bool GetMoreCapablePhysicalDevice(VkPhysicalDevice newVkDevice, VkSurfaceKHR surface,
|
||||||
const PhysicalDevice& compareWithDevice,
|
const PhysicalDevice& compareWithDevice,
|
||||||
PhysicalDevice& outBetterDevice);
|
PhysicalDevice& outBetterDevice);
|
||||||
Uint32 FindMemoryType(Uint32 typeFilter, VkMemoryPropertyFlags properties) const;
|
|
||||||
static Uint64 BuildPendingClearKey(Uint drawFboExternalIndex, Bool targetsDefaultFramebuffer);
|
static Uint64 BuildPendingClearKey(Uint drawFboExternalIndex, Bool targetsDefaultFramebuffer);
|
||||||
static Bool HasStencilComponent(VkFormat format);
|
|
||||||
static VkFormat FindSupportedDepthStencilFormat(VkPhysicalDevice physicalDevice);
|
|
||||||
static constexpr VkDynamicState s_dynamicStates[] = {VK_DYNAMIC_STATE_VIEWPORT, VK_DYNAMIC_STATE_SCISSOR};
|
static constexpr VkDynamicState s_dynamicStates[] = {VK_DYNAMIC_STATE_VIEWPORT, VK_DYNAMIC_STATE_SCISSOR};
|
||||||
static constexpr const char* s_validationLayerNames[] = {"VK_LAYER_KHRONOS_validation"};
|
static constexpr const char* s_validationLayerNames[] = {"VK_LAYER_KHRONOS_validation"};
|
||||||
static constexpr const char* s_deviceExtensionNames[] = {VK_KHR_SWAPCHAIN_EXTENSION_NAME};
|
static constexpr const char* s_deviceExtensionNames[] = {VK_KHR_SWAPCHAIN_EXTENSION_NAME};
|
||||||
|
|||||||
Reference in New Issue
Block a user