rhi: vulkan: Fix multisample resolve with multiview
Task-number: QTBUG-114790 Change-Id: I3afccc3f7ae2d05aa9aa0e0943aeadc080016f0e Reviewed-by: Andy Nichols <andy.nichols@qt.io>
This commit is contained in:
parent
003c29511d
commit
2f619c2ddf
@ -2284,16 +2284,40 @@ QRhiColorAttachment::QRhiColorAttachment(QRhiRenderBuffer *renderBuffer)
|
||||
\nullptr if there is none.
|
||||
|
||||
Setting a non-null resolve texture is applicable when the attachment
|
||||
references a multisample, color renderbuffer. (i.e., renderBuffer() is set)
|
||||
The QRhiTexture in the resolveTexture() is then a regular, 2D,
|
||||
non-multisample texture with the same size (but a sample count of 1). The
|
||||
multisample content is automatically resolved into this texture at the end
|
||||
of each render pass.
|
||||
references a multisample texture or renderbuffer. The QRhiTexture in the
|
||||
resolveTexture() is then a non-multisample 2D texture (or texture array)
|
||||
with the same size (but a sample count of 1). The multisample content is
|
||||
automatically resolved into this texture at the end of each render pass.
|
||||
*/
|
||||
|
||||
/*!
|
||||
\fn void QRhiColorAttachment::setResolveTexture(QRhiTexture *tex)
|
||||
|
||||
Sets the resolve texture \a tex.
|
||||
|
||||
\a tex is expected to be a 2D texture or a 2D texture array. In either
|
||||
case, resolving targets a single mip level of a single layer (array
|
||||
element) of \a tex. The mip level and array layer are specified by
|
||||
resolveLevel() and resolveLayer().
|
||||
|
||||
An exception is \l{setMultiViewCount()}{multiview}: when the color
|
||||
attachment is associated with a texture array and multiview is enabled, the
|
||||
resolve texture must also be a texture array with sufficient elements for
|
||||
all views. In this case all elements that correspond to views are resolved
|
||||
automatically; the behavior is similar to the following pseudo-code:
|
||||
\badcode
|
||||
for (i = 0; i < multiViewCount(); ++i)
|
||||
resolve texture's layer() + i into resolveTexture's resolveLayer() + i
|
||||
\endcode
|
||||
|
||||
Setting a non-multisample texture to resolve a multisample texture or
|
||||
renderbuffer automatically at the end of the render pass is often
|
||||
preferable to working with multisample textures (and not setting a resolve
|
||||
texture), because it avoids the need for writing dedicated fragment shaders
|
||||
that work exclusively with multisample textures (\c sampler2DMS, \c
|
||||
texelFetch, etc.), and rather allows using the same shader as one would if
|
||||
the attachment's texture was not multisampled to begin with. This comes at
|
||||
the expense of an additional resource (the non-multisample \a tex).
|
||||
*/
|
||||
|
||||
/*!
|
||||
|
@ -6723,6 +6723,7 @@ bool QVkTextureRenderTarget::create()
|
||||
|
||||
QRHI_RES_RHI(QRhiVulkan);
|
||||
QVarLengthArray<VkImageView, 8> views;
|
||||
uint32_t multiViewCount = 0;
|
||||
|
||||
d.colorAttCount = 0;
|
||||
int attIndex = 0;
|
||||
@ -6735,6 +6736,8 @@ bool QVkTextureRenderTarget::create()
|
||||
Q_ASSERT(texD->flags().testFlag(QRhiTexture::RenderTarget));
|
||||
const bool is1D = texD->flags().testFlag(QRhiTexture::OneDimensional);
|
||||
const bool isMultiView = it->multiViewCount() >= 2;
|
||||
if (isMultiView && multiViewCount == 0)
|
||||
multiViewCount = uint32_t(it->multiViewCount());
|
||||
VkImageViewCreateInfo viewInfo = {};
|
||||
viewInfo.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO;
|
||||
viewInfo.image = texD->image;
|
||||
@ -6795,6 +6798,7 @@ bool QVkTextureRenderTarget::create()
|
||||
|
||||
d.resolveAttCount = 0;
|
||||
attIndex = 0;
|
||||
Q_ASSERT(multiViewCount == 0 || multiViewCount >= 2);
|
||||
for (auto it = m_desc.cbeginColorAttachments(), itEnd = m_desc.cendColorAttachments(); it != itEnd; ++it, ++attIndex) {
|
||||
if (it->resolveTexture()) {
|
||||
QVkTexture *resTexD = QRHI_RES(QVkTexture, it->resolveTexture());
|
||||
@ -6804,7 +6808,8 @@ bool QVkTextureRenderTarget::create()
|
||||
VkImageViewCreateInfo viewInfo = {};
|
||||
viewInfo.sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO;
|
||||
viewInfo.image = resTexD->image;
|
||||
viewInfo.viewType = VK_IMAGE_VIEW_TYPE_2D;
|
||||
viewInfo.viewType = multiViewCount ? VK_IMAGE_VIEW_TYPE_2D_ARRAY
|
||||
: VK_IMAGE_VIEW_TYPE_2D;
|
||||
viewInfo.format = resTexD->vkformat;
|
||||
viewInfo.components.r = VK_COMPONENT_SWIZZLE_R;
|
||||
viewInfo.components.g = VK_COMPONENT_SWIZZLE_G;
|
||||
@ -6814,7 +6819,7 @@ bool QVkTextureRenderTarget::create()
|
||||
viewInfo.subresourceRange.baseMipLevel = uint32_t(it->resolveLevel());
|
||||
viewInfo.subresourceRange.levelCount = 1;
|
||||
viewInfo.subresourceRange.baseArrayLayer = uint32_t(it->resolveLayer());
|
||||
viewInfo.subresourceRange.layerCount = 1;
|
||||
viewInfo.subresourceRange.layerCount = qMax(1u, multiViewCount);
|
||||
VkResult err = rhiD->df->vkCreateImageView(rhiD->dev, &viewInfo, nullptr, &resrtv[attIndex]);
|
||||
if (err != VK_SUCCESS) {
|
||||
qWarning("Failed to create render target resolve image view: %d", err);
|
||||
|
Loading…
Reference in New Issue
Block a user