summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLaszlo Agocs <laszlo.agocs@qt.io>2022-01-24 15:28:20 +0100
committerQt Cherry-pick Bot <cherrypick_bot@qt-project.org>2022-01-25 00:55:19 +0000
commit5bbd5e1bfe8a81dc07daa6cbef16264507d91e73 (patch)
tree4c994425927627995871500022d1195ccf9f1ac0
parent40adeb60f4cf0e59eb337c0fd34cbee8bcc629c9 (diff)
rhi: Make sure pixelSize() to a texture rt is always up to date
This is an issue for QQuickWindow in practice, although it is not hit by our current tests. Change-Id: Ia73704c1af6a82b2689ce7b844d3b0eb9a17ec18 Reviewed-by: Christian Strømme <christian.stromme@qt.io> (cherry picked from commit 406bb6ae20471cf9bba6d910256b416792c99322) Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
-rw-r--r--src/gui/rhi/qrhi.cpp12
-rw-r--r--src/gui/rhi/qrhid3d11.cpp3
-rw-r--r--src/gui/rhi/qrhigles2.cpp3
-rw-r--r--src/gui/rhi/qrhimetal.mm3
-rw-r--r--src/gui/rhi/qrhinull.cpp3
-rw-r--r--src/gui/rhi/qrhivulkan.cpp3
-rw-r--r--tests/auto/gui/rhi/qrhi/tst_qrhi.cpp66
7 files changed, 69 insertions, 24 deletions
diff --git a/src/gui/rhi/qrhi.cpp b/src/gui/rhi/qrhi.cpp
index 70525689e9..d8bd4536ae 100644
--- a/src/gui/rhi/qrhi.cpp
+++ b/src/gui/rhi/qrhi.cpp
@@ -2886,6 +2886,18 @@ QRhiResource::Type QRhiRenderTarget::resourceType() const
\fn QSize QRhiRenderTarget::pixelSize() const
\return the size in pixels.
+
+ Valid only after create() has been called successfully. Until then the
+ result is a default-constructed QSize.
+
+ With QRhiTextureRenderTarget the returned size is the size of the
+ associated attachments at the time of create(), in practice the size of the
+ first color attachment, or the depth/stencil buffer if there are no color
+ attachments. If the associated textures or renderbuffers are resized and
+ rebuilt afterwards, then pixelSize() performs an implicit call to create()
+ in order to rebuild the underlying data structures. This implicit check is
+ similar to what QRhiCommandBuffer::beginPass() does, and ensures that the
+ returned size is always up-to-date.
*/
/*!
diff --git a/src/gui/rhi/qrhid3d11.cpp b/src/gui/rhi/qrhid3d11.cpp
index 175015f7fe..54c8b4f477 100644
--- a/src/gui/rhi/qrhid3d11.cpp
+++ b/src/gui/rhi/qrhid3d11.cpp
@@ -3635,6 +3635,9 @@ bool QD3D11TextureRenderTarget::create()
QSize QD3D11TextureRenderTarget::pixelSize() const
{
+ if (!QRhiRenderTargetAttachmentTracker::isUpToDate<QD3D11Texture, QD3D11RenderBuffer>(m_desc, d.currentResIdList))
+ const_cast<QD3D11TextureRenderTarget *>(this)->create();
+
return d.pixelSize;
}
diff --git a/src/gui/rhi/qrhigles2.cpp b/src/gui/rhi/qrhigles2.cpp
index 1e2a1e431f..72eeeb88a5 100644
--- a/src/gui/rhi/qrhigles2.cpp
+++ b/src/gui/rhi/qrhigles2.cpp
@@ -5177,6 +5177,9 @@ bool QGles2TextureRenderTarget::create()
QSize QGles2TextureRenderTarget::pixelSize() const
{
+ if (!QRhiRenderTargetAttachmentTracker::isUpToDate<QGles2Texture, QGles2RenderBuffer>(m_desc, d.currentResIdList))
+ const_cast<QGles2TextureRenderTarget *>(this)->create();
+
return d.pixelSize;
}
diff --git a/src/gui/rhi/qrhimetal.mm b/src/gui/rhi/qrhimetal.mm
index 626eac433b..6ea1f5e645 100644
--- a/src/gui/rhi/qrhimetal.mm
+++ b/src/gui/rhi/qrhimetal.mm
@@ -3192,6 +3192,9 @@ bool QMetalTextureRenderTarget::create()
QSize QMetalTextureRenderTarget::pixelSize() const
{
+ if (!QRhiRenderTargetAttachmentTracker::isUpToDate<QMetalTexture, QMetalRenderBuffer>(m_desc, d->currentResIdList))
+ const_cast<QMetalTextureRenderTarget *>(this)->create();
+
return d->pixelSize;
}
diff --git a/src/gui/rhi/qrhinull.cpp b/src/gui/rhi/qrhinull.cpp
index 6e85e02cc2..c47936e797 100644
--- a/src/gui/rhi/qrhinull.cpp
+++ b/src/gui/rhi/qrhinull.cpp
@@ -888,6 +888,9 @@ bool QNullTextureRenderTarget::create()
QSize QNullTextureRenderTarget::pixelSize() const
{
+ if (!QRhiRenderTargetAttachmentTracker::isUpToDate<QNullTexture, QNullRenderBuffer>(m_desc, d.currentResIdList))
+ const_cast<QNullTextureRenderTarget *>(this)->create();
+
return d.pixelSize;
}
diff --git a/src/gui/rhi/qrhivulkan.cpp b/src/gui/rhi/qrhivulkan.cpp
index e23900069c..0c91021ece 100644
--- a/src/gui/rhi/qrhivulkan.cpp
+++ b/src/gui/rhi/qrhivulkan.cpp
@@ -6585,6 +6585,9 @@ bool QVkTextureRenderTarget::create()
QSize QVkTextureRenderTarget::pixelSize() const
{
+ if (!QRhiRenderTargetAttachmentTracker::isUpToDate<QVkTexture, QVkRenderBuffer>(m_desc, d.currentResIdList))
+ const_cast<QVkTextureRenderTarget *>(this)->create();
+
return d.pixelSize;
}
diff --git a/tests/auto/gui/rhi/qrhi/tst_qrhi.cpp b/tests/auto/gui/rhi/qrhi/tst_qrhi.cpp
index 89c02322dd..51767cd23a 100644
--- a/tests/auto/gui/rhi/qrhi/tst_qrhi.cpp
+++ b/tests/auto/gui/rhi/qrhi/tst_qrhi.cpp
@@ -3783,33 +3783,51 @@ void tst_QRhi::textureRenderTargetAutoRebuild()
if (!rhi)
QSKIP("QRhi could not be created, skipping testing rendering");
- QScopedPointer<QRhiTexture> texture(rhi->newTexture(QRhiTexture::RGBA8, QSize(512, 512), 1, QRhiTexture::RenderTarget));
- QVERIFY(texture->create());
- QScopedPointer<QRhiTextureRenderTarget> rt(rhi->newTextureRenderTarget({ { texture.data() } }));
- QScopedPointer<QRhiRenderPassDescriptor> rp(rt->newCompatibleRenderPassDescriptor());
- rt->setRenderPassDescriptor(rp.data());
- QVERIFY(rt->create());
+ // case 1: beginPass's implicit create()
+ {
+ QScopedPointer<QRhiTexture> texture(rhi->newTexture(QRhiTexture::RGBA8, QSize(512, 512), 1, QRhiTexture::RenderTarget));
+ QVERIFY(texture->create());
+ QScopedPointer<QRhiTextureRenderTarget> rt(rhi->newTextureRenderTarget({ { texture.data() } }));
+ QScopedPointer<QRhiRenderPassDescriptor> rp(rt->newCompatibleRenderPassDescriptor());
+ rt->setRenderPassDescriptor(rp.data());
+ QVERIFY(rt->create());
- QRhiCommandBuffer *cb = nullptr;
- QVERIFY(rhi->beginOffscreenFrame(&cb) == QRhi::FrameOpSuccess);
- QVERIFY(cb);
- cb->beginPass(rt.data(), Qt::red, { 1.0f, 0 });
- cb->endPass();
- rhi->endOffscreenFrame();
+ QRhiCommandBuffer *cb = nullptr;
+ QVERIFY(rhi->beginOffscreenFrame(&cb) == QRhi::FrameOpSuccess);
+ QVERIFY(cb);
+ cb->beginPass(rt.data(), Qt::red, { 1.0f, 0 });
+ cb->endPass();
+ rhi->endOffscreenFrame();
- texture->setPixelSize(QSize(256, 256));
- QVERIFY(texture->create());
- QCOMPARE(texture->pixelSize(), QSize(256, 256));
- // rt still has the old size and knows nothing about texture's underlying native texture resource possibly changing
- QCOMPARE(rt->pixelSize(), QSize(512, 512));
+ texture->setPixelSize(QSize(256, 256));
+ QVERIFY(texture->create());
+ QCOMPARE(texture->pixelSize(), QSize(256, 256));
- QVERIFY(rhi->beginOffscreenFrame(&cb) == QRhi::FrameOpSuccess);
- QVERIFY(cb);
- // no rt->create() but beginPass() does it implicitly for us
- cb->beginPass(rt.data(), Qt::red, { 1.0f, 0 });
- QCOMPARE(rt->pixelSize(), QSize(256, 256));
- cb->endPass();
- rhi->endOffscreenFrame();
+ QVERIFY(rhi->beginOffscreenFrame(&cb) == QRhi::FrameOpSuccess);
+ QVERIFY(cb);
+ // no rt->create() but beginPass() does it implicitly for us
+ cb->beginPass(rt.data(), Qt::red, { 1.0f, 0 });
+ QCOMPARE(rt->pixelSize(), QSize(256, 256));
+ cb->endPass();
+ rhi->endOffscreenFrame();
+ }
+
+ // case 2: pixelSize's implicit create()
+ {
+ QSize sz(512, 512);
+ QScopedPointer<QRhiTexture> texture(rhi->newTexture(QRhiTexture::RGBA8, sz, 1, QRhiTexture::RenderTarget));
+ QVERIFY(texture->create());
+ QScopedPointer<QRhiTextureRenderTarget> rt(rhi->newTextureRenderTarget({ { texture.data() } }));
+ QScopedPointer<QRhiRenderPassDescriptor> rp(rt->newCompatibleRenderPassDescriptor());
+ rt->setRenderPassDescriptor(rp.data());
+ QVERIFY(rt->create());
+ QCOMPARE(rt->pixelSize(), sz);
+
+ sz = QSize(256, 256);
+ texture->setPixelSize(sz);
+ QVERIFY(texture->create());
+ QCOMPARE(rt->pixelSize(), sz);
+ }
}
void tst_QRhi::srbLayoutCompatibility_data()