Hello Andrey! thanks for providing the code, somehow i dont get the nice MSAA de…pth result. but it works on color. what am i doing wrong? since im using input attachments as well on next pass.

void VulkanRenderer::createRenderResource()
{
VkMemoryRequirements colorMemoryRequirements{}, colorResolveMemoryRequirements{},
depthMemoryRequirements{}, depthResolveMemoryRequirements{};
VkImageCreateInfo colorImageCI = {
.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
.imageType = VK_IMAGE_TYPE_2D,
.format = VK_FORMAT_R16G16B16A16_SFLOAT,
.extent = { mWidth, mHeight, 1u },
.mipLevels = 1u,
.arrayLayers = 1u,
.samples = mMSAA,
.tiling = VK_IMAGE_TILING_OPTIMAL,
.usage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSIENT_ATTACHMENT_BIT,
.sharingMode = VK_SHARING_MODE_EXCLUSIVE,
.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED
}; vkCreateImage(mDevice, &colorImageCI, nullptr, &mColorImage);
vkGetImageMemoryRequirements(mDevice, mColorImage, &colorMemoryRequirements);
VkImageCreateInfo colorResolveImageCI = {
.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
.imageType = VK_IMAGE_TYPE_2D,
.format = colorImageCI.format,
.extent = { mWidth, mHeight, 1u },
.mipLevels = 1u,
.arrayLayers = 1u,
.samples = VK_SAMPLE_COUNT_1_BIT,
.tiling = VK_IMAGE_TILING_OPTIMAL,
.usage = VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT,
.sharingMode = VK_SHARING_MODE_EXCLUSIVE,
.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED
}; vkCreateImage(mDevice, &colorResolveImageCI, nullptr, &mColorResolveImage);
vkGetImageMemoryRequirements(mDevice, mColorResolveImage, &colorResolveMemoryRequirements);
VkImageCreateInfo depthImageCI = {
.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
.imageType = VK_IMAGE_TYPE_2D,
.format = VK_FORMAT_D24_UNORM_S8_UINT,
.extent = { mWidth, mHeight, 1u },
.mipLevels = 1u,
.arrayLayers = 1u,
.samples = colorImageCI.samples,
.tiling = VK_IMAGE_TILING_OPTIMAL,
.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSIENT_ATTACHMENT_BIT,
.sharingMode = VK_SHARING_MODE_EXCLUSIVE,
.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED
}; vkCreateImage(mDevice, &depthImageCI, nullptr, &mDepthImage);
vkGetImageMemoryRequirements(mDevice, mDepthImage, &depthMemoryRequirements);
VkImageCreateInfo depthResolveImageCI = {
.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO,
.imageType = VK_IMAGE_TYPE_2D,
.format = depthImageCI.format,
.extent = { mWidth, mHeight, 1u },
.mipLevels = 1u,
.arrayLayers = 1u,
.samples = VK_SAMPLE_COUNT_1_BIT,
.tiling = VK_IMAGE_TILING_OPTIMAL,
.usage = VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT | VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT,
.sharingMode = VK_SHARING_MODE_EXCLUSIVE,
.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED
}; vkCreateImage(mDevice, &depthResolveImageCI, nullptr, &mDepthResolveImage);
vkGetImageMemoryRequirements(mDevice, mDepthResolveImage, &depthResolveMemoryRequirements);
VkDeviceSize colorOffset = 0ull;
VkDeviceSize colorResolveOffset = colorOffset + colorMemoryRequirements.size;
colorResolveOffset = (colorResolveOffset + colorResolveMemoryRequirements.alignment - 1) & ~(colorResolveMemoryRequirements.alignment - 1);
VkDeviceSize depthOffset = colorResolveOffset + colorResolveMemoryRequirements.size;
depthOffset = (depthOffset + depthMemoryRequirements.alignment - 1) & ~(depthMemoryRequirements.alignment - 1);
VkDeviceSize depthResolveOffset = depthOffset + depthMemoryRequirements.size;
depthResolveOffset = (depthResolveOffset + depthResolveMemoryRequirements.alignment - 1) & ~(depthResolveMemoryRequirements.alignment - 1);
VkDeviceSize totalSize = depthResolveOffset + depthResolveMemoryRequirements.size;
VkMemoryAllocateInfo memoryAI = {
.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO,
.allocationSize = totalSize,
.memoryTypeIndex = findMemoryType(colorMemoryRequirements.memoryTypeBits &
colorResolveMemoryRequirements.memoryTypeBits &
depthMemoryRequirements.memoryTypeBits &
depthResolveMemoryRequirements.memoryTypeBits,
VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT
)
}; vkAllocateMemory(mDevice, &memoryAI, nullptr, &mRenderMemory);
vkBindImageMemory(mDevice, mColorImage, mRenderMemory, colorOffset);
vkBindImageMemory(mDevice, mColorResolveImage, mRenderMemory, colorResolveOffset);
vkBindImageMemory(mDevice, mDepthImage, mRenderMemory, depthOffset);
vkBindImageMemory(mDevice, mDepthResolveImage, mRenderMemory, depthResolveOffset);
VkImageViewCreateInfo colorImageViewCI = {
.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
.image = mColorImage,
.viewType = VK_IMAGE_VIEW_TYPE_2D,
.format = colorImageCI.format,
.components = { VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY },
.subresourceRange = { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u }
}; vkCreateImageView(mDevice, &colorImageViewCI, nullptr, &mColorImageView);
VkImageViewCreateInfo colorResolveImageViewCI = {
.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
.image = mColorResolveImage,
.viewType = VK_IMAGE_VIEW_TYPE_2D,
.format = colorResolveImageCI.format,
.components = { VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY },
.subresourceRange = { VK_IMAGE_ASPECT_COLOR_BIT, 0u, 1u, 0u, 1u }
}; vkCreateImageView(mDevice, &colorResolveImageViewCI, nullptr, &mColorResolveImageView);
VkImageViewCreateInfo depthImageViewCI = {
.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
.image = mDepthImage,
.viewType = VK_IMAGE_VIEW_TYPE_2D,
.format = depthImageCI.format,
.components = { VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY },
.subresourceRange = { VK_IMAGE_ASPECT_DEPTH_BIT, 0u, 1u, 0u, 1u }
}; vkCreateImageView(mDevice, &depthImageViewCI, nullptr, &mDepthImageView);
VkImageViewCreateInfo depthResolveImageViewCI = {
.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO,
.image = mDepthResolveImage,
.viewType = VK_IMAGE_VIEW_TYPE_2D,
.format = depthResolveImageCI.format,
.components = { VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY, VK_COMPONENT_SWIZZLE_IDENTITY },
.subresourceRange = { VK_IMAGE_ASPECT_DEPTH_BIT, 0u, 1u, 0u, 1u }
}; vkCreateImageView(mDevice, &depthResolveImageViewCI, nullptr, &mDepthResolveImageView);
}
then i create the render pass ->
void VulkanRenderer::createRenderpass()
{
array<VkAttachmentDescription2, 5u> attachmentDescriptions{};
attachmentDescriptions[0u].sType = VK_STRUCTURE_TYPE_ATTACHMENT_DESCRIPTION_2;
attachmentDescriptions[0u].pNext = nullptr;
attachmentDescriptions[0u].flags = 0;
attachmentDescriptions[0u].format = mSwapchainFormat;
attachmentDescriptions[0u].samples = VK_SAMPLE_COUNT_1_BIT;
attachmentDescriptions[0u].loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescriptions[0u].storeOp = VK_ATTACHMENT_STORE_OP_STORE;
attachmentDescriptions[0u].stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescriptions[0u].stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachmentDescriptions[0u].initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
attachmentDescriptions[0u].finalLayout = VK_IMAGE_LAYOUT_PRESENT_SRC_KHR;
attachmentDescriptions[1u].sType = VK_STRUCTURE_TYPE_ATTACHMENT_DESCRIPTION_2;
attachmentDescriptions[1u].pNext = nullptr;
attachmentDescriptions[1u].flags = 0;
attachmentDescriptions[1u].format = VK_FORMAT_R16G16B16A16_SFLOAT;
attachmentDescriptions[1u].samples = mMSAA;
attachmentDescriptions[1u].loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
attachmentDescriptions[1u].storeOp = VK_ATTACHMENT_STORE_OP_STORE;
attachmentDescriptions[1u].stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescriptions[1u].stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachmentDescriptions[1u].initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
attachmentDescriptions[1u].finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
attachmentDescriptions[2u].sType = VK_STRUCTURE_TYPE_ATTACHMENT_DESCRIPTION_2;
attachmentDescriptions[2u].pNext = nullptr;
attachmentDescriptions[2u].flags = 0;
attachmentDescriptions[2u].format = attachmentDescriptions[1u].format;
attachmentDescriptions[2u].samples = VK_SAMPLE_COUNT_1_BIT;
attachmentDescriptions[2u].loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescriptions[2u].storeOp = VK_ATTACHMENT_STORE_OP_STORE;
attachmentDescriptions[2u].stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescriptions[2u].stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachmentDescriptions[2u].initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
attachmentDescriptions[2u].finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL;
attachmentDescriptions[3u].sType = VK_STRUCTURE_TYPE_ATTACHMENT_DESCRIPTION_2;
attachmentDescriptions[3u].pNext = nullptr;
attachmentDescriptions[3u].flags = 0;
attachmentDescriptions[3u].format = VK_FORMAT_D24_UNORM_S8_UINT;
attachmentDescriptions[3u].samples = attachmentDescriptions[1u].samples;
attachmentDescriptions[3u].loadOp = VK_ATTACHMENT_LOAD_OP_CLEAR;
attachmentDescriptions[3u].storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachmentDescriptions[3u].stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescriptions[3u].stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachmentDescriptions[3u].initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
attachmentDescriptions[3u].finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL;
attachmentDescriptions[4u].sType = VK_STRUCTURE_TYPE_ATTACHMENT_DESCRIPTION_2;
attachmentDescriptions[4u].pNext = nullptr;
attachmentDescriptions[4u].flags = 0;
attachmentDescriptions[4u].format = attachmentDescriptions[3u].format;
attachmentDescriptions[4u].samples = VK_SAMPLE_COUNT_1_BIT;
attachmentDescriptions[4u].loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescriptions[4u].storeOp = VK_ATTACHMENT_STORE_OP_STORE;
attachmentDescriptions[4u].stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachmentDescriptions[4u].stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
attachmentDescriptions[4u].initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
attachmentDescriptions[4u].finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL;
array<VkSubpassDescription2, 2u> subpassDescriptions{};
VkAttachmentReference2 colorReference = {
.sType = VK_STRUCTURE_TYPE_ATTACHMENT_REFERENCE_2,
.pNext = nullptr,
.attachment = 1u,
.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT
};
VkAttachmentReference2 colorResolveReference = {
.sType = VK_STRUCTURE_TYPE_ATTACHMENT_REFERENCE_2,
.pNext = nullptr,
.attachment = 2u,
.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT
};
VkAttachmentReference2 depthReference =
{
.sType = VK_STRUCTURE_TYPE_ATTACHMENT_REFERENCE_2,
.pNext = nullptr,
.attachment = 3u,
.layout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
.aspectMask = VK_IMAGE_ASPECT_DEPTH_BIT
};
VkAttachmentReference2 depthResolveReference = {
.sType = VK_STRUCTURE_TYPE_ATTACHMENT_REFERENCE_2,
.pNext = nullptr,
.attachment = 4u,
.layout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
.aspectMask = VK_IMAGE_ASPECT_DEPTH_BIT
};
VkSubpassDescriptionDepthStencilResolve vkSubpassDescriptionDepthStencilResolve = {
.sType = VK_STRUCTURE_TYPE_SUBPASS_DESCRIPTION_DEPTH_STENCIL_RESOLVE,
.pNext = nullptr,
.depthResolveMode = VK_RESOLVE_MODE_SAMPLE_ZERO_BIT,
.stencilResolveMode = VK_RESOLVE_MODE_SAMPLE_ZERO_BIT,
.pDepthStencilResolveAttachment = &depthResolveReference
};
subpassDescriptions[0u].sType = VK_STRUCTURE_TYPE_SUBPASS_DESCRIPTION_2;
subpassDescriptions[0u].pNext = &vkSubpassDescriptionDepthStencilResolve;
subpassDescriptions[0u].flags = 0;
subpassDescriptions[0u].pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS;
subpassDescriptions[0u].viewMask = 0u;
subpassDescriptions[0u].inputAttachmentCount = 0u;
subpassDescriptions[0u].pInputAttachments = nullptr;
subpassDescriptions[0u].colorAttachmentCount = 1u;
subpassDescriptions[0u].pColorAttachments = &colorReference;
subpassDescriptions[0u].pResolveAttachments = &colorResolveReference;
subpassDescriptions[0u].pDepthStencilAttachment = &depthReference;
subpassDescriptions[0u].preserveAttachmentCount = 0u;
subpassDescriptions[0u].pPreserveAttachments = nullptr;
VkAttachmentReference2 inputReferences[2] =
{
{
.sType = VK_STRUCTURE_TYPE_ATTACHMENT_REFERENCE_2,
.pNext = nullptr,
.attachment = 2u,
.layout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL,
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT
},
{
.sType = VK_STRUCTURE_TYPE_ATTACHMENT_REFERENCE_2,
.pNext = nullptr,
.attachment = 4u,
.layout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL,
.aspectMask = VK_IMAGE_ASPECT_DEPTH_BIT
},
};
VkAttachmentReference2 swapChainReference = {
.sType = VK_STRUCTURE_TYPE_ATTACHMENT_REFERENCE_2,
.pNext = nullptr,
.attachment = 0u,
.layout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
.aspectMask = VK_IMAGE_ASPECT_COLOR_BIT
};
subpassDescriptions[1u].sType = VK_STRUCTURE_TYPE_SUBPASS_DESCRIPTION_2;
subpassDescriptions[1u].pNext = nullptr;
subpassDescriptions[1u].flags = 0;
subpassDescriptions[1u].pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS;
subpassDescriptions[1u].viewMask = 0u;
subpassDescriptions[1u].inputAttachmentCount = 2u;
subpassDescriptions[1u].pInputAttachments = inputReferences;
subpassDescriptions[1u].colorAttachmentCount = 1u;
subpassDescriptions[1u].pColorAttachments = &swapChainReference;
subpassDescriptions[1u].pResolveAttachments = nullptr;
subpassDescriptions[1u].pDepthStencilAttachment = nullptr;
subpassDescriptions[1u].preserveAttachmentCount = 0u;
subpassDescriptions[1u].pPreserveAttachments = nullptr;
array<VkSubpassDependency2, 2u> subpassDependencies{};
subpassDependencies[0u].sType = VK_STRUCTURE_TYPE_SUBPASS_DEPENDENCY_2;
subpassDependencies[0u].pNext = nullptr;
subpassDependencies[0u].srcSubpass = VK_SUBPASS_EXTERNAL;
subpassDependencies[0u].dstSubpass = 0u;
subpassDependencies[0u].srcStageMask = VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT;
subpassDependencies[0u].dstStageMask = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT | VK_PIPELINE_STAGE_EARLY_FRAGMENT_TESTS_BIT;
subpassDependencies[0u].srcAccessMask = VK_ACCESS_MEMORY_READ_BIT;
subpassDependencies[0u].dstAccessMask = VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT | VK_ACCESS_DEPTH_STENCIL_ATTACHMENT_WRITE_BIT;
subpassDependencies[0u].dependencyFlags = VK_DEPENDENCY_BY_REGION_BIT;
subpassDependencies[0u].viewOffset = 0;
subpassDependencies[1u].sType = VK_STRUCTURE_TYPE_SUBPASS_DEPENDENCY_2;
subpassDependencies[1u].pNext = nullptr;
subpassDependencies[1u].srcSubpass = 0u;
subpassDependencies[1u].dstSubpass = 1u;
subpassDependencies[1u].srcStageMask = VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT;
subpassDependencies[1u].dstStageMask = VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT;
subpassDependencies[1u].srcAccessMask = VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT;
subpassDependencies[1u].dstAccessMask = VK_ACCESS_SHADER_READ_BIT;
subpassDependencies[1u].dependencyFlags = VK_DEPENDENCY_BY_REGION_BIT;
subpassDependencies[1u].viewOffset = 0;
VkRenderPassCreateInfo2 renderPassCI = {
.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO_2,
.pNext = nullptr,
.flags = 0,
.attachmentCount = attachmentDescriptions.size(),
.pAttachments = attachmentDescriptions.data(),
.subpassCount = subpassDescriptions.size(),
.pSubpasses = subpassDescriptions.data(),
.dependencyCount = subpassDependencies.size(),
.pDependencies = subpassDependencies.data(),
.correlatedViewMaskCount = 0u,
.pCorrelatedViewMasks = nullptr
}; vkCreateRenderPass2(mDevice, &renderPassCI, nullptr, &mRenderPass);
}
then the framebuffer ->
void VulkanRenderer::createFramebuffer()
{
mFramebuffers.resize(mSwapchainImageViews.size());
for (u32 i = 0u; i < mFramebuffers.size(); ++i)
{
array<VkImageView, 5u> attachments = {
mSwapchainImageViews[i],
mColorImageView,
mColorResolveImageView,
mDepthImageView,
mDepthResolveImageView
};
VkFramebufferCreateInfo framebufferCI = {
.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,
.renderPass = mRenderPass,
.attachmentCount = attachments.size(),
.pAttachments = attachments.data(),
.width = mWidth,
.height = mHeight,
.layers = 1u
}; vkCreateFramebuffer(mDevice, &framebufferCI, nullptr, &mFramebuffers[i]);
}
}
what am i doing wrong? it works great on color but not depth.
is there an unique features that i need to enable first?
im really loss, since no validation layer errors, i check on RenderDoc. here is the proof it doesnt get resolve. it just like copy from one to another?
https://github.com/user-attachments/assets/b505bdd5-c7d2-44e3-a0f7-15813c32b56e