summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/gui/rhi/qrhi.cpp25
-rw-r--r--src/gui/rhi/qrhi_p.h6
-rw-r--r--src/gui/rhi/qrhi_p_p.h3
-rw-r--r--src/gui/rhi/qrhid3d11.cpp18
-rw-r--r--src/gui/rhi/qrhid3d11_p_p.h6
-rw-r--r--src/gui/rhi/qrhigles2.cpp189
-rw-r--r--src/gui/rhi/qrhigles2_p_p.h6
-rw-r--r--src/gui/rhi/qrhimetal.mm284
-rw-r--r--src/gui/rhi/qrhimetal_p_p.h6
-rw-r--r--src/gui/rhi/qrhinull.cpp10
-rw-r--r--src/gui/rhi/qrhinull_p_p.h6
-rw-r--r--src/gui/rhi/qrhivulkan.cpp17
-rw-r--r--src/gui/rhi/qrhivulkan_p_p.h6
13 files changed, 332 insertions, 250 deletions
diff --git a/src/gui/rhi/qrhi.cpp b/src/gui/rhi/qrhi.cpp
index 1eb26985bf..6a118d20c8 100644
--- a/src/gui/rhi/qrhi.cpp
+++ b/src/gui/rhi/qrhi.cpp
@@ -2123,9 +2123,11 @@ QRhiBuffer::NativeBuffer QRhiBuffer::nativeBuffer()
\internal
*/
QRhiRenderBuffer::QRhiRenderBuffer(QRhiImplementation *rhi, Type type_, const QSize &pixelSize_,
- int sampleCount_, Flags flags_)
+ int sampleCount_, Flags flags_,
+ QRhiTexture::Format backingFormatHint_)
: QRhiResource(rhi),
- m_type(type_), m_pixelSize(pixelSize_), m_sampleCount(sampleCount_), m_flags(flags_)
+ m_type(type_), m_pixelSize(pixelSize_), m_sampleCount(sampleCount_), m_flags(flags_),
+ m_backingFormatHint(backingFormatHint_)
{
}
@@ -5488,14 +5490,29 @@ QRhiBuffer *QRhi::newBuffer(QRhiBuffer::Type type,
\return a new renderbuffer with the specified \a type, \a pixelSize, \a
sampleCount, and \a flags.
+ When \a backingFormatHint is set to a texture format other than
+ QRhiTexture::UnknownFormat, it may be used by the backend to decide what
+ format to use for the storage backing the renderbuffer.
+
+ \note \a backingFormatHint becomes relevant typically when multisampling
+ and floating point texture formats are involved: rendering into a
+ multisample QRhiRenderBuffer and then resolving into a non-RGBA8
+ QRhiTexture implies (with some graphics APIs) that the storage backing the
+ QRhiRenderBuffer uses the matching non-RGBA8 format. That means that
+ passing a format like QRhiTexture::RGBA32F is important, because backends
+ will typically opt for QRhiTexture::RGBA8 by default, which would then
+ break later on due to attempting to set up RGBA8->RGBA32F multisample
+ resolve in the color attachment(s) of the QRhiTextureRenderTarget.
+
\sa QRhiResource::release()
*/
QRhiRenderBuffer *QRhi::newRenderBuffer(QRhiRenderBuffer::Type type,
const QSize &pixelSize,
int sampleCount,
- QRhiRenderBuffer::Flags flags)
+ QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
{
- return d->createRenderBuffer(type, pixelSize, sampleCount, flags);
+ return d->createRenderBuffer(type, pixelSize, sampleCount, flags, backingFormatHint);
}
/*!
diff --git a/src/gui/rhi/qrhi_p.h b/src/gui/rhi/qrhi_p.h
index 5ef415e96c..e63a828bfc 100644
--- a/src/gui/rhi/qrhi_p.h
+++ b/src/gui/rhi/qrhi_p.h
@@ -908,11 +908,12 @@ public:
protected:
QRhiRenderBuffer(QRhiImplementation *rhi, Type type_, const QSize &pixelSize_,
- int sampleCount_, Flags flags_);
+ int sampleCount_, Flags flags_, QRhiTexture::Format backingFormatHint_);
Type m_type;
QSize m_pixelSize;
int m_sampleCount;
Flags m_flags;
+ QRhiTexture::Format m_backingFormatHint;
};
Q_DECLARE_OPERATORS_FOR_FLAGS(QRhiRenderBuffer::Flags)
@@ -1493,7 +1494,8 @@ public:
QRhiRenderBuffer *newRenderBuffer(QRhiRenderBuffer::Type type,
const QSize &pixelSize,
int sampleCount = 1,
- QRhiRenderBuffer::Flags flags = QRhiRenderBuffer::Flags());
+ QRhiRenderBuffer::Flags flags = QRhiRenderBuffer::Flags(),
+ QRhiTexture::Format backingFormatHint = QRhiTexture::UnknownFormat);
QRhiTexture *newTexture(QRhiTexture::Format format,
const QSize &pixelSize,
diff --git a/src/gui/rhi/qrhi_p_p.h b/src/gui/rhi/qrhi_p_p.h
index 4a4c044a29..95f04fbd1b 100644
--- a/src/gui/rhi/qrhi_p_p.h
+++ b/src/gui/rhi/qrhi_p_p.h
@@ -80,7 +80,8 @@ public:
virtual QRhiRenderBuffer *createRenderBuffer(QRhiRenderBuffer::Type type,
const QSize &pixelSize,
int sampleCount,
- QRhiRenderBuffer::Flags flags) = 0;
+ QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint) = 0;
virtual QRhiTexture *createTexture(QRhiTexture::Format format,
const QSize &pixelSize,
int sampleCount,
diff --git a/src/gui/rhi/qrhid3d11.cpp b/src/gui/rhi/qrhid3d11.cpp
index c3c40b4cc4..8336d43ff6 100644
--- a/src/gui/rhi/qrhid3d11.cpp
+++ b/src/gui/rhi/qrhid3d11.cpp
@@ -528,9 +528,10 @@ bool QRhiD3D11::isDeviceLost() const
}
QRhiRenderBuffer *QRhiD3D11::createRenderBuffer(QRhiRenderBuffer::Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
{
- return new QD3D11RenderBuffer(this, type, pixelSize, sampleCount, flags);
+ return new QD3D11RenderBuffer(this, type, pixelSize, sampleCount, flags, backingFormatHint);
}
QRhiTexture *QRhiD3D11::createTexture(QRhiTexture::Format format, const QSize &pixelSize,
@@ -2613,8 +2614,9 @@ ID3D11UnorderedAccessView *QD3D11Buffer::unorderedAccessView()
}
QD3D11RenderBuffer::QD3D11RenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
- : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags)
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
+ : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags, backingFormatHint)
{
}
@@ -2668,7 +2670,8 @@ bool QD3D11RenderBuffer::build()
desc.Usage = D3D11_USAGE_DEFAULT;
if (m_type == Color) {
- dxgiFormat = DXGI_FORMAT_R8G8B8A8_UNORM;
+ dxgiFormat = m_backingFormatHint == QRhiTexture::UnknownFormat ? DXGI_FORMAT_R8G8B8A8_UNORM
+ : toD3DTextureFormat(m_backingFormatHint, {});
desc.Format = dxgiFormat;
desc.BindFlags = D3D11_BIND_RENDER_TARGET;
HRESULT hr = rhiD->dev->CreateTexture2D(&desc, nullptr, &tex);
@@ -2721,7 +2724,10 @@ bool QD3D11RenderBuffer::build()
QRhiTexture::Format QD3D11RenderBuffer::backingFormat() const
{
- return m_type == Color ? QRhiTexture::RGBA8 : QRhiTexture::UnknownFormat;
+ if (m_backingFormatHint != QRhiTexture::UnknownFormat)
+ return m_backingFormatHint;
+ else
+ return m_type == Color ? QRhiTexture::RGBA8 : QRhiTexture::UnknownFormat;
}
QD3D11Texture::QD3D11Texture(QRhiImplementation *rhi, Format format, const QSize &pixelSize,
diff --git a/src/gui/rhi/qrhid3d11_p_p.h b/src/gui/rhi/qrhid3d11_p_p.h
index 33412b8011..2cb59b32b5 100644
--- a/src/gui/rhi/qrhid3d11_p_p.h
+++ b/src/gui/rhi/qrhid3d11_p_p.h
@@ -79,7 +79,8 @@ struct QD3D11Buffer : public QRhiBuffer
struct QD3D11RenderBuffer : public QRhiRenderBuffer
{
QD3D11RenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags);
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint);
~QD3D11RenderBuffer();
void release() override;
bool build() override;
@@ -567,7 +568,8 @@ public:
QRhiRenderBuffer *createRenderBuffer(QRhiRenderBuffer::Type type,
const QSize &pixelSize,
int sampleCount,
- QRhiRenderBuffer::Flags flags) override;
+ QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint) override;
QRhiTexture *createTexture(QRhiTexture::Format format,
const QSize &pixelSize,
int sampleCount,
diff --git a/src/gui/rhi/qrhigles2.cpp b/src/gui/rhi/qrhigles2.cpp
index 1e97d2ed0c..d8c64c7408 100644
--- a/src/gui/rhi/qrhigles2.cpp
+++ b/src/gui/rhi/qrhigles2.cpp
@@ -690,6 +690,87 @@ static inline GLenum toGlCompressedTextureFormat(QRhiTexture::Format format, QRh
}
}
+static inline void toGlTextureFormat(QRhiTexture::Format format, const QRhiGles2::Caps &caps,
+ GLenum *glintformat, GLenum *glsizedintformat,
+ GLenum *glformat, GLenum *gltype)
+{
+ switch (format) {
+ case QRhiTexture::RGBA8:
+ *glintformat = GL_RGBA;
+ *glsizedintformat = caps.rgba8Format ? GL_RGBA8 : GL_RGBA;
+ *glformat = GL_RGBA;
+ *gltype = GL_UNSIGNED_BYTE;
+ break;
+ case QRhiTexture::BGRA8:
+ *glintformat = caps.bgraInternalFormat ? GL_BGRA : GL_RGBA;
+ *glsizedintformat = caps.rgba8Format ? GL_RGBA8 : GL_RGBA;
+ *glformat = GL_BGRA;
+ *gltype = GL_UNSIGNED_BYTE;
+ break;
+ case QRhiTexture::R16:
+ *glintformat = GL_R16;
+ *glsizedintformat = *glintformat;
+ *glformat = GL_RED;
+ *gltype = GL_UNSIGNED_SHORT;
+ break;
+ case QRhiTexture::R8:
+ *glintformat = GL_R8;
+ *glsizedintformat = *glintformat;
+ *glformat = GL_RED;
+ *gltype = GL_UNSIGNED_BYTE;
+ break;
+ case QRhiTexture::RED_OR_ALPHA8:
+ *glintformat = caps.coreProfile ? GL_R8 : GL_ALPHA;
+ *glsizedintformat = *glintformat;
+ *glformat = caps.coreProfile ? GL_RED : GL_ALPHA;
+ *gltype = GL_UNSIGNED_BYTE;
+ break;
+ case QRhiTexture::RGBA16F:
+ *glintformat = GL_RGBA16F;
+ *glsizedintformat = *glintformat;
+ *glformat = GL_RGBA;
+ *gltype = GL_HALF_FLOAT;
+ break;
+ case QRhiTexture::RGBA32F:
+ *glintformat = GL_RGBA32F;
+ *glsizedintformat = *glintformat;
+ *glformat = GL_RGBA;
+ *gltype = GL_FLOAT;
+ break;
+ case QRhiTexture::R16F:
+ *glintformat = GL_R16F;
+ *glsizedintformat = *glintformat;
+ *glformat = GL_RED;
+ *gltype = GL_HALF_FLOAT;
+ break;
+ case QRhiTexture::R32F:
+ *glintformat = GL_R32F;
+ *glsizedintformat = *glintformat;
+ *glformat = GL_RED;
+ *gltype = GL_FLOAT;
+ break;
+ case QRhiTexture::D16:
+ *glintformat = GL_DEPTH_COMPONENT16;
+ *glsizedintformat = *glintformat;
+ *glformat = GL_DEPTH_COMPONENT;
+ *gltype = GL_UNSIGNED_SHORT;
+ break;
+ case QRhiTexture::D32F:
+ *glintformat = GL_DEPTH_COMPONENT32F;
+ *glsizedintformat = *glintformat;
+ *glformat = GL_DEPTH_COMPONENT;
+ *gltype = GL_FLOAT;
+ break;
+ default:
+ Q_UNREACHABLE();
+ *glintformat = GL_RGBA;
+ *glsizedintformat = caps.rgba8Format ? GL_RGBA8 : GL_RGBA;
+ *glformat = GL_RGBA;
+ *gltype = GL_UNSIGNED_BYTE;
+ break;
+ }
+}
+
bool QRhiGles2::isTextureFormatSupported(QRhiTexture::Format format, QRhiTexture::Flags flags) const
{
if (isCompressedFormat(format))
@@ -833,9 +914,10 @@ bool QRhiGles2::isDeviceLost() const
}
QRhiRenderBuffer *QRhiGles2::createRenderBuffer(QRhiRenderBuffer::Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
{
- return new QGles2RenderBuffer(this, type, pixelSize, sampleCount, flags);
+ return new QGles2RenderBuffer(this, type, pixelSize, sampleCount, flags, backingFormatHint);
}
QRhiTexture *QRhiGles2::createTexture(QRhiTexture::Format format, const QSize &pixelSize,
@@ -3435,8 +3517,9 @@ QRhiBuffer::NativeBuffer QGles2Buffer::nativeBuffer()
}
QGles2RenderBuffer::QGles2RenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
- : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags)
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
+ : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags, backingFormatHint)
{
}
@@ -3522,13 +3605,26 @@ bool QGles2RenderBuffer::build()
QRHI_PROF_F(newRenderBuffer(this, false, false, samples));
break;
case QRhiRenderBuffer::Color:
- if (rhiD->caps.msaaRenderBuffer && samples > 1)
- rhiD->f->glRenderbufferStorageMultisample(GL_RENDERBUFFER, samples, GL_RGBA8,
+ {
+ GLenum internalFormat = GL_RGBA4; // ES 2.0
+ if (rhiD->caps.rgba8Format) {
+ internalFormat = GL_RGBA8;
+ if (m_backingFormatHint != QRhiTexture::UnknownFormat) {
+ GLenum glintformat, glformat, gltype;
+ // only care about the sized internal format, the rest is not used here
+ toGlTextureFormat(m_backingFormatHint, rhiD->caps,
+ &glintformat, &internalFormat, &glformat, &gltype);
+ }
+ }
+ if (rhiD->caps.msaaRenderBuffer && samples > 1) {
+ rhiD->f->glRenderbufferStorageMultisample(GL_RENDERBUFFER, samples, internalFormat,
size.width(), size.height());
- else
- rhiD->f->glRenderbufferStorage(GL_RENDERBUFFER, rhiD->caps.rgba8Format ? GL_RGBA8 : GL_RGBA4,
+ } else {
+ rhiD->f->glRenderbufferStorage(GL_RENDERBUFFER, internalFormat,
size.width(), size.height());
+ }
QRHI_PROF_F(newRenderBuffer(this, false, false, samples));
+ }
break;
default:
Q_UNREACHABLE();
@@ -3541,7 +3637,10 @@ bool QGles2RenderBuffer::build()
QRhiTexture::Format QGles2RenderBuffer::backingFormat() const
{
- return m_type == Color ? QRhiTexture::RGBA8 : QRhiTexture::UnknownFormat;
+ if (m_backingFormatHint != QRhiTexture::UnknownFormat)
+ return m_backingFormatHint;
+ else
+ return m_type == Color ? QRhiTexture::RGBA8 : QRhiTexture::UnknownFormat;
}
QGles2Texture::QGles2Texture(QRhiImplementation *rhi, Format format, const QSize &pixelSize,
@@ -3608,76 +3707,8 @@ bool QGles2Texture::prepareBuild(QSize *adjustedSize)
glsizedintformat = glintformat;
glformat = GL_RGBA;
} else {
- switch (m_format) {
- case QRhiTexture::RGBA8:
- glintformat = GL_RGBA;
- glsizedintformat = rhiD->caps.rgba8Format ? GL_RGBA8 : GL_RGBA;
- glformat = GL_RGBA;
- break;
- case QRhiTexture::BGRA8:
- glintformat = rhiD->caps.bgraInternalFormat ? GL_BGRA : GL_RGBA;
- glsizedintformat = rhiD->caps.rgba8Format ? GL_RGBA8 : GL_RGBA;
- glformat = GL_BGRA;
- break;
- case QRhiTexture::R16:
- glintformat = GL_R16;
- glsizedintformat = glintformat;
- glformat = GL_RED;
- gltype = GL_UNSIGNED_SHORT;
- break;
- case QRhiTexture::R8:
- glintformat = GL_R8;
- glsizedintformat = glintformat;
- glformat = GL_RED;
- break;
- case QRhiTexture::RED_OR_ALPHA8:
- glintformat = rhiD->caps.coreProfile ? GL_R8 : GL_ALPHA;
- glsizedintformat = glintformat;
- glformat = rhiD->caps.coreProfile ? GL_RED : GL_ALPHA;
- break;
- case QRhiTexture::RGBA16F:
- glintformat = GL_RGBA16F;
- glsizedintformat = glintformat;
- glformat = GL_RGBA;
- gltype = GL_HALF_FLOAT;
- break;
- case QRhiTexture::RGBA32F:
- glintformat = GL_RGBA32F;
- glsizedintformat = glintformat;
- glformat = GL_RGBA;
- gltype = GL_FLOAT;
- break;
- case QRhiTexture::R16F:
- glintformat = GL_R16F;
- glsizedintformat = glintformat;
- glformat = GL_RED;
- gltype = GL_HALF_FLOAT;
- break;
- case QRhiTexture::R32F:
- glintformat = GL_R32F;
- glsizedintformat = glintformat;
- glformat = GL_RED;
- gltype = GL_FLOAT;
- break;
- case QRhiTexture::D16:
- glintformat = GL_DEPTH_COMPONENT16;
- glsizedintformat = glintformat;
- glformat = GL_DEPTH_COMPONENT;
- gltype = GL_UNSIGNED_SHORT;
- break;
- case QRhiTexture::D32F:
- glintformat = GL_DEPTH_COMPONENT32F;
- glsizedintformat = glintformat;
- glformat = GL_DEPTH_COMPONENT;
- gltype = GL_FLOAT;
- break;
- default:
- Q_UNREACHABLE();
- glintformat = GL_RGBA;
- glsizedintformat = rhiD->caps.rgba8Format ? GL_RGBA8 : GL_RGBA;
- glformat = GL_RGBA;
- break;
- }
+ toGlTextureFormat(m_format, rhiD->caps,
+ &glintformat, &glsizedintformat, &glformat, &gltype);
}
samplerState = QGles2SamplerData();
diff --git a/src/gui/rhi/qrhigles2_p_p.h b/src/gui/rhi/qrhigles2_p_p.h
index ac7b384cb6..e326b661d9 100644
--- a/src/gui/rhi/qrhigles2_p_p.h
+++ b/src/gui/rhi/qrhigles2_p_p.h
@@ -89,7 +89,8 @@ struct QGles2Buffer : public QRhiBuffer
struct QGles2RenderBuffer : public QRhiRenderBuffer
{
QGles2RenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags);
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint);
~QGles2RenderBuffer();
void release() override;
bool build() override;
@@ -694,7 +695,8 @@ public:
QRhiRenderBuffer *createRenderBuffer(QRhiRenderBuffer::Type type,
const QSize &pixelSize,
int sampleCount,
- QRhiRenderBuffer::Flags flags) override;
+ QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint) override;
QRhiTexture *createTexture(QRhiTexture::Format format,
const QSize &pixelSize,
int sampleCount,
diff --git a/src/gui/rhi/qrhimetal.mm b/src/gui/rhi/qrhimetal.mm
index f021e78097..c5afdf63eb 100644
--- a/src/gui/rhi/qrhimetal.mm
+++ b/src/gui/rhi/qrhimetal.mm
@@ -621,9 +621,10 @@ bool QRhiMetal::isDeviceLost() const
}
QRhiRenderBuffer *QRhiMetal::createRenderBuffer(QRhiRenderBuffer::Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
{
- return new QMetalRenderBuffer(this, type, pixelSize, sampleCount, flags);
+ return new QMetalRenderBuffer(this, type, pixelSize, sampleCount, flags, backingFormatHint);
}
QRhiTexture *QRhiMetal::createTexture(QRhiTexture::Format format, const QSize &pixelSize,
@@ -2232,9 +2233,142 @@ QRhiBuffer::NativeBuffer QMetalBuffer::nativeBuffer()
return { { &d->buf[0] }, 1 };
}
+static inline MTLPixelFormat toMetalTextureFormat(QRhiTexture::Format format, QRhiTexture::Flags flags)
+{
+ const bool srgb = flags.testFlag(QRhiTexture::sRGB);
+ switch (format) {
+ case QRhiTexture::RGBA8:
+ return srgb ? MTLPixelFormatRGBA8Unorm_sRGB : MTLPixelFormatRGBA8Unorm;
+ case QRhiTexture::BGRA8:
+ return srgb ? MTLPixelFormatBGRA8Unorm_sRGB : MTLPixelFormatBGRA8Unorm;
+ case QRhiTexture::R8:
+#ifdef Q_OS_MACOS
+ return MTLPixelFormatR8Unorm;
+#else
+ return srgb ? MTLPixelFormatR8Unorm_sRGB : MTLPixelFormatR8Unorm;
+#endif
+ case QRhiTexture::R16:
+ return MTLPixelFormatR16Unorm;
+ case QRhiTexture::RED_OR_ALPHA8:
+ return MTLPixelFormatR8Unorm;
+
+ case QRhiTexture::RGBA16F:
+ return MTLPixelFormatRGBA16Float;
+ case QRhiTexture::RGBA32F:
+ return MTLPixelFormatRGBA32Float;
+ case QRhiTexture::R16F:
+ return MTLPixelFormatR16Float;
+ case QRhiTexture::R32F:
+ return MTLPixelFormatR32Float;
+
+ case QRhiTexture::D16:
+#ifdef Q_OS_MACOS
+ return MTLPixelFormatDepth16Unorm;
+#else
+ return MTLPixelFormatDepth32Float;
+#endif
+ case QRhiTexture::D32F:
+ return MTLPixelFormatDepth32Float;
+
+#ifdef Q_OS_MACOS
+ case QRhiTexture::BC1:
+ return srgb ? MTLPixelFormatBC1_RGBA_sRGB : MTLPixelFormatBC1_RGBA;
+ case QRhiTexture::BC2:
+ return srgb ? MTLPixelFormatBC2_RGBA_sRGB : MTLPixelFormatBC2_RGBA;
+ case QRhiTexture::BC3:
+ return srgb ? MTLPixelFormatBC3_RGBA_sRGB : MTLPixelFormatBC3_RGBA;
+ case QRhiTexture::BC4:
+ return MTLPixelFormatBC4_RUnorm;
+ case QRhiTexture::BC5:
+ qWarning("QRhiMetal does not support BC5");
+ return MTLPixelFormatRGBA8Unorm;
+ case QRhiTexture::BC6H:
+ return MTLPixelFormatBC6H_RGBUfloat;
+ case QRhiTexture::BC7:
+ return srgb ? MTLPixelFormatBC7_RGBAUnorm_sRGB : MTLPixelFormatBC7_RGBAUnorm;
+#else
+ case QRhiTexture::BC1:
+ case QRhiTexture::BC2:
+ case QRhiTexture::BC3:
+ case QRhiTexture::BC4:
+ case QRhiTexture::BC5:
+ case QRhiTexture::BC6H:
+ case QRhiTexture::BC7:
+ qWarning("QRhiMetal: BCx compression not supported on this platform");
+ return MTLPixelFormatRGBA8Unorm;
+#endif
+
+#ifndef Q_OS_MACOS
+ case QRhiTexture::ETC2_RGB8:
+ return srgb ? MTLPixelFormatETC2_RGB8_sRGB : MTLPixelFormatETC2_RGB8;
+ case QRhiTexture::ETC2_RGB8A1:
+ return srgb ? MTLPixelFormatETC2_RGB8A1_sRGB : MTLPixelFormatETC2_RGB8A1;
+ case QRhiTexture::ETC2_RGBA8:
+ return srgb ? MTLPixelFormatEAC_RGBA8_sRGB : MTLPixelFormatEAC_RGBA8;
+
+ case QRhiTexture::ASTC_4x4:
+ return srgb ? MTLPixelFormatASTC_4x4_sRGB : MTLPixelFormatASTC_4x4_LDR;
+ case QRhiTexture::ASTC_5x4:
+ return srgb ? MTLPixelFormatASTC_5x4_sRGB : MTLPixelFormatASTC_5x4_LDR;
+ case QRhiTexture::ASTC_5x5:
+ return srgb ? MTLPixelFormatASTC_5x5_sRGB : MTLPixelFormatASTC_5x5_LDR;
+ case QRhiTexture::ASTC_6x5:
+ return srgb ? MTLPixelFormatASTC_6x5_sRGB : MTLPixelFormatASTC_6x5_LDR;
+ case QRhiTexture::ASTC_6x6:
+ return srgb ? MTLPixelFormatASTC_6x6_sRGB : MTLPixelFormatASTC_6x6_LDR;
+ case QRhiTexture::ASTC_8x5:
+ return srgb ? MTLPixelFormatASTC_8x5_sRGB : MTLPixelFormatASTC_8x5_LDR;
+ case QRhiTexture::ASTC_8x6:
+ return srgb ? MTLPixelFormatASTC_8x6_sRGB : MTLPixelFormatASTC_8x6_LDR;
+ case QRhiTexture::ASTC_8x8:
+ return srgb ? MTLPixelFormatASTC_8x8_sRGB : MTLPixelFormatASTC_8x8_LDR;
+ case QRhiTexture::ASTC_10x5:
+ return srgb ? MTLPixelFormatASTC_10x5_sRGB : MTLPixelFormatASTC_10x5_LDR;
+ case QRhiTexture::ASTC_10x6:
+ return srgb ? MTLPixelFormatASTC_10x6_sRGB : MTLPixelFormatASTC_10x6_LDR;
+ case QRhiTexture::ASTC_10x8:
+ return srgb ? MTLPixelFormatASTC_10x8_sRGB : MTLPixelFormatASTC_10x8_LDR;
+ case QRhiTexture::ASTC_10x10:
+ return srgb ? MTLPixelFormatASTC_10x10_sRGB : MTLPixelFormatASTC_10x10_LDR;
+ case QRhiTexture::ASTC_12x10:
+ return srgb ? MTLPixelFormatASTC_12x10_sRGB : MTLPixelFormatASTC_12x10_LDR;
+ case QRhiTexture::ASTC_12x12:
+ return srgb ? MTLPixelFormatASTC_12x12_sRGB : MTLPixelFormatASTC_12x12_LDR;
+#else
+ case QRhiTexture::ETC2_RGB8:
+ case QRhiTexture::ETC2_RGB8A1:
+ case QRhiTexture::ETC2_RGBA8:
+ qWarning("QRhiMetal: ETC2 compression not supported on this platform");
+ return MTLPixelFormatRGBA8Unorm;
+
+ case QRhiTexture::ASTC_4x4:
+ case QRhiTexture::ASTC_5x4:
+ case QRhiTexture::ASTC_5x5:
+ case QRhiTexture::ASTC_6x5:
+ case QRhiTexture::ASTC_6x6:
+ case QRhiTexture::ASTC_8x5:
+ case QRhiTexture::ASTC_8x6:
+ case QRhiTexture::ASTC_8x8:
+ case QRhiTexture::ASTC_10x5:
+ case QRhiTexture::ASTC_10x6:
+ case QRhiTexture::ASTC_10x8:
+ case QRhiTexture::ASTC_10x10:
+ case QRhiTexture::ASTC_12x10:
+ case QRhiTexture::ASTC_12x12:
+ qWarning("QRhiMetal: ASTC compression not supported on this platform");
+ return MTLPixelFormatRGBA8Unorm;
+#endif
+
+ default:
+ Q_UNREACHABLE();
+ return MTLPixelFormatRGBA8Unorm;
+ }
+}
+
QMetalRenderBuffer::QMetalRenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
- : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags),
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
+ : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags, backingFormatHint),
d(new QMetalRenderBufferData)
{
}
@@ -2300,7 +2434,10 @@ bool QMetalRenderBuffer::build()
break;
case Color:
desc.storageMode = MTLStorageModePrivate;
- d->format = MTLPixelFormatRGBA8Unorm;
+ if (m_backingFormatHint != QRhiTexture::UnknownFormat)
+ d->format = toMetalTextureFormat(m_backingFormatHint, {});
+ else
+ d->format = MTLPixelFormatRGBA8Unorm;
desc.pixelFormat = d->format;
break;
default:
@@ -2325,7 +2462,10 @@ bool QMetalRenderBuffer::build()
QRhiTexture::Format QMetalRenderBuffer::backingFormat() const
{
- return m_type == Color ? QRhiTexture::RGBA8 : QRhiTexture::UnknownFormat;
+ if (m_backingFormatHint != QRhiTexture::UnknownFormat)
+ return m_backingFormatHint;
+ else
+ return m_type == Color ? QRhiTexture::RGBA8 : QRhiTexture::UnknownFormat;
}
QMetalTexture::QMetalTexture(QRhiImplementation *rhi, Format format, const QSize &pixelSize,
@@ -2375,138 +2515,6 @@ void QMetalTexture::release()
rhiD->unregisterResource(this);
}
-static inline MTLPixelFormat toMetalTextureFormat(QRhiTexture::Format format, QRhiTexture::Flags flags)
-{
- const bool srgb = flags.testFlag(QRhiTexture::sRGB);
- switch (format) {
- case QRhiTexture::RGBA8:
- return srgb ? MTLPixelFormatRGBA8Unorm_sRGB : MTLPixelFormatRGBA8Unorm;
- case QRhiTexture::BGRA8:
- return srgb ? MTLPixelFormatBGRA8Unorm_sRGB : MTLPixelFormatBGRA8Unorm;
- case QRhiTexture::R8:
-#ifdef Q_OS_MACOS
- return MTLPixelFormatR8Unorm;
-#else
- return srgb ? MTLPixelFormatR8Unorm_sRGB : MTLPixelFormatR8Unorm;
-#endif
- case QRhiTexture::R16:
- return MTLPixelFormatR16Unorm;
- case QRhiTexture::RED_OR_ALPHA8:
- return MTLPixelFormatR8Unorm;
-
- case QRhiTexture::RGBA16F:
- return MTLPixelFormatRGBA16Float;
- case QRhiTexture::RGBA32F:
- return MTLPixelFormatRGBA32Float;
- case QRhiTexture::R16F:
- return MTLPixelFormatR16Float;
- case QRhiTexture::R32F:
- return MTLPixelFormatR32Float;
-
- case QRhiTexture::D16:
-#ifdef Q_OS_MACOS
- return MTLPixelFormatDepth16Unorm;
-#else
- return MTLPixelFormatDepth32Float;
-#endif
- case QRhiTexture::D32F:
- return MTLPixelFormatDepth32Float;
-
-#ifdef Q_OS_MACOS
- case QRhiTexture::BC1:
- return srgb ? MTLPixelFormatBC1_RGBA_sRGB : MTLPixelFormatBC1_RGBA;
- case QRhiTexture::BC2:
- return srgb ? MTLPixelFormatBC2_RGBA_sRGB : MTLPixelFormatBC2_RGBA;
- case QRhiTexture::BC3:
- return srgb ? MTLPixelFormatBC3_RGBA_sRGB : MTLPixelFormatBC3_RGBA;
- case QRhiTexture::BC4:
- return MTLPixelFormatBC4_RUnorm;
- case QRhiTexture::BC5:
- qWarning("QRhiMetal does not support BC5");
- return MTLPixelFormatRGBA8Unorm;
- case QRhiTexture::BC6H:
- return MTLPixelFormatBC6H_RGBUfloat;
- case QRhiTexture::BC7:
- return srgb ? MTLPixelFormatBC7_RGBAUnorm_sRGB : MTLPixelFormatBC7_RGBAUnorm;
-#else
- case QRhiTexture::BC1:
- case QRhiTexture::BC2:
- case QRhiTexture::BC3:
- case QRhiTexture::BC4:
- case QRhiTexture::BC5:
- case QRhiTexture::BC6H:
- case QRhiTexture::BC7:
- qWarning("QRhiMetal: BCx compression not supported on this platform");
- return MTLPixelFormatRGBA8Unorm;
-#endif
-
-#ifndef Q_OS_MACOS
- case QRhiTexture::ETC2_RGB8:
- return srgb ? MTLPixelFormatETC2_RGB8_sRGB : MTLPixelFormatETC2_RGB8;
- case QRhiTexture::ETC2_RGB8A1:
- return srgb ? MTLPixelFormatETC2_RGB8A1_sRGB : MTLPixelFormatETC2_RGB8A1;
- case QRhiTexture::ETC2_RGBA8:
- return srgb ? MTLPixelFormatEAC_RGBA8_sRGB : MTLPixelFormatEAC_RGBA8;
-
- case QRhiTexture::ASTC_4x4:
- return srgb ? MTLPixelFormatASTC_4x4_sRGB : MTLPixelFormatASTC_4x4_LDR;
- case QRhiTexture::ASTC_5x4:
- return srgb ? MTLPixelFormatASTC_5x4_sRGB : MTLPixelFormatASTC_5x4_LDR;
- case QRhiTexture::ASTC_5x5:
- return srgb ? MTLPixelFormatASTC_5x5_sRGB : MTLPixelFormatASTC_5x5_LDR;
- case QRhiTexture::ASTC_6x5:
- return srgb ? MTLPixelFormatASTC_6x5_sRGB : MTLPixelFormatASTC_6x5_LDR;
- case QRhiTexture::ASTC_6x6:
- return srgb ? MTLPixelFormatASTC_6x6_sRGB : MTLPixelFormatASTC_6x6_LDR;
- case QRhiTexture::ASTC_8x5:
- return srgb ? MTLPixelFormatASTC_8x5_sRGB : MTLPixelFormatASTC_8x5_LDR;
- case QRhiTexture::ASTC_8x6:
- return srgb ? MTLPixelFormatASTC_8x6_sRGB : MTLPixelFormatASTC_8x6_LDR;
- case QRhiTexture::ASTC_8x8:
- return srgb ? MTLPixelFormatASTC_8x8_sRGB : MTLPixelFormatASTC_8x8_LDR;
- case QRhiTexture::ASTC_10x5:
- return srgb ? MTLPixelFormatASTC_10x5_sRGB : MTLPixelFormatASTC_10x5_LDR;
- case QRhiTexture::ASTC_10x6:
- return srgb ? MTLPixelFormatASTC_10x6_sRGB : MTLPixelFormatASTC_10x6_LDR;
- case QRhiTexture::ASTC_10x8:
- return srgb ? MTLPixelFormatASTC_10x8_sRGB : MTLPixelFormatASTC_10x8_LDR;
- case QRhiTexture::ASTC_10x10:
- return srgb ? MTLPixelFormatASTC_10x10_sRGB : MTLPixelFormatASTC_10x10_LDR;
- case QRhiTexture::ASTC_12x10:
- return srgb ? MTLPixelFormatASTC_12x10_sRGB : MTLPixelFormatASTC_12x10_LDR;
- case QRhiTexture::ASTC_12x12:
- return srgb ? MTLPixelFormatASTC_12x12_sRGB : MTLPixelFormatASTC_12x12_LDR;
-#else
- case QRhiTexture::ETC2_RGB8:
- case QRhiTexture::ETC2_RGB8A1:
- case QRhiTexture::ETC2_RGBA8:
- qWarning("QRhiMetal: ETC2 compression not supported on this platform");
- return MTLPixelFormatRGBA8Unorm;
-
- case QRhiTexture::ASTC_4x4:
- case QRhiTexture::ASTC_5x4:
- case QRhiTexture::ASTC_5x5:
- case QRhiTexture::ASTC_6x5:
- case QRhiTexture::ASTC_6x6:
- case QRhiTexture::ASTC_8x5:
- case QRhiTexture::ASTC_8x6:
- case QRhiTexture::ASTC_8x8:
- case QRhiTexture::ASTC_10x5:
- case QRhiTexture::ASTC_10x6:
- case QRhiTexture::ASTC_10x8:
- case QRhiTexture::ASTC_10x10:
- case QRhiTexture::ASTC_12x10:
- case QRhiTexture::ASTC_12x12:
- qWarning("QRhiMetal: ASTC compression not supported on this platform");
- return MTLPixelFormatRGBA8Unorm;
-#endif
-
- default:
- Q_UNREACHABLE();
- return MTLPixelFormatRGBA8Unorm;
- }
-}
-
bool QMetalTexture::prepareBuild(QSize *adjustedSize)
{
if (d->tex)
diff --git a/src/gui/rhi/qrhimetal_p_p.h b/src/gui/rhi/qrhimetal_p_p.h
index cb4b777d88..30f5e8b74e 100644
--- a/src/gui/rhi/qrhimetal_p_p.h
+++ b/src/gui/rhi/qrhimetal_p_p.h
@@ -79,7 +79,8 @@ struct QMetalRenderBufferData;
struct QMetalRenderBuffer : public QRhiRenderBuffer
{
QMetalRenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags);
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint);
~QMetalRenderBuffer();
void release() override;
bool build() override;
@@ -349,7 +350,8 @@ public:
QRhiRenderBuffer *createRenderBuffer(QRhiRenderBuffer::Type type,
const QSize &pixelSize,
int sampleCount,
- QRhiRenderBuffer::Flags flags) override;
+ QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint) override;
QRhiTexture *createTexture(QRhiTexture::Format format,
const QSize &pixelSize,
int sampleCount,
diff --git a/src/gui/rhi/qrhinull.cpp b/src/gui/rhi/qrhinull.cpp
index 7b18c9156b..b1ce9b7599 100644
--- a/src/gui/rhi/qrhinull.cpp
+++ b/src/gui/rhi/qrhinull.cpp
@@ -182,9 +182,10 @@ bool QRhiNull::isDeviceLost() const
}
QRhiRenderBuffer *QRhiNull::createRenderBuffer(QRhiRenderBuffer::Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
{
- return new QNullRenderBuffer(this, type, pixelSize, sampleCount, flags);
+ return new QNullRenderBuffer(this, type, pixelSize, sampleCount, flags, backingFormatHint);
}
QRhiTexture *QRhiNull::createTexture(QRhiTexture::Format format, const QSize &pixelSize,
@@ -564,8 +565,9 @@ bool QNullBuffer::build()
}
QNullRenderBuffer::QNullRenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
- : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags)
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
+ : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags, backingFormatHint)
{
}
diff --git a/src/gui/rhi/qrhinull_p_p.h b/src/gui/rhi/qrhinull_p_p.h
index 0b3d40f1aa..347da4d71c 100644
--- a/src/gui/rhi/qrhinull_p_p.h
+++ b/src/gui/rhi/qrhinull_p_p.h
@@ -66,7 +66,8 @@ struct QNullBuffer : public QRhiBuffer
struct QNullRenderBuffer : public QRhiRenderBuffer
{
QNullRenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags);
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint);
~QNullRenderBuffer();
void release() override;
bool build() override;
@@ -207,7 +208,8 @@ public:
QRhiRenderBuffer *createRenderBuffer(QRhiRenderBuffer::Type type,
const QSize &pixelSize,
int sampleCount,
- QRhiRenderBuffer::Flags flags) override;
+ QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint) override;
QRhiTexture *createTexture(QRhiTexture::Format format,
const QSize &pixelSize,
int sampleCount,
diff --git a/src/gui/rhi/qrhivulkan.cpp b/src/gui/rhi/qrhivulkan.cpp
index 49e634e248..16de7e0aea 100644
--- a/src/gui/rhi/qrhivulkan.cpp
+++ b/src/gui/rhi/qrhivulkan.cpp
@@ -4084,9 +4084,10 @@ bool QRhiVulkan::isDeviceLost() const
}
QRhiRenderBuffer *QRhiVulkan::createRenderBuffer(QRhiRenderBuffer::Type type, const QSize &pixelSize,
- int sampleCount, QRhiRenderBuffer::Flags flags)
+ int sampleCount, QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint)
{
- return new QVkRenderBuffer(this, type, pixelSize, sampleCount, flags);
+ return new QVkRenderBuffer(this, type, pixelSize, sampleCount, flags, backingFormatHint);
}
QRhiTexture *QRhiVulkan::createTexture(QRhiTexture::Format format, const QSize &pixelSize,
@@ -5241,8 +5242,9 @@ QRhiBuffer::NativeBuffer QVkBuffer::nativeBuffer()
}
QVkRenderBuffer::QVkRenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, Flags flags)
- : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags)
+ int sampleCount, Flags flags,
+ QRhiTexture::Format backingFormatHint)
+ : QRhiRenderBuffer(rhi, type, pixelSize, sampleCount, flags, backingFormatHint)
{
}
@@ -5300,7 +5302,7 @@ bool QVkRenderBuffer::build()
case QRhiRenderBuffer::Color:
{
if (!backingTexture) {
- backingTexture = QRHI_RES(QVkTexture, rhiD->createTexture(QRhiTexture::RGBA8,
+ backingTexture = QRHI_RES(QVkTexture, rhiD->createTexture(backingFormat(),
m_pixelSize,
m_sampleCount,
QRhiTexture::RenderTarget | QRhiTexture::UsedAsTransferSource));
@@ -5344,7 +5346,10 @@ bool QVkRenderBuffer::build()
QRhiTexture::Format QVkRenderBuffer::backingFormat() const
{
- return m_type == Color ? QRhiTexture::RGBA8 : QRhiTexture::UnknownFormat;
+ if (m_backingFormatHint != QRhiTexture::UnknownFormat)
+ return m_backingFormatHint;
+ else
+ return m_type == Color ? QRhiTexture::RGBA8 : QRhiTexture::UnknownFormat;
}
QVkTexture::QVkTexture(QRhiImplementation *rhi, Format format, const QSize &pixelSize,
diff --git a/src/gui/rhi/qrhivulkan_p_p.h b/src/gui/rhi/qrhivulkan_p_p.h
index d90b1d1364..1b2e4d0ebb 100644
--- a/src/gui/rhi/qrhivulkan_p_p.h
+++ b/src/gui/rhi/qrhivulkan_p_p.h
@@ -98,7 +98,8 @@ struct QVkTexture;
struct QVkRenderBuffer : public QRhiRenderBuffer
{
QVkRenderBuffer(QRhiImplementation *rhi, Type type, const QSize &pixelSize,
- int sampleCount, Flags flags);
+ int sampleCount, Flags flags,
+ QRhiTexture::Format backingFormatHint);
~QVkRenderBuffer();
void release() override;
bool build() override;
@@ -658,7 +659,8 @@ public:
QRhiRenderBuffer *createRenderBuffer(QRhiRenderBuffer::Type type,
const QSize &pixelSize,
int sampleCount,
- QRhiRenderBuffer::Flags flags) override;
+ QRhiRenderBuffer::Flags flags,
+ QRhiTexture::Format backingFormatHint) override;
QRhiTexture *createTexture(QRhiTexture::Format format,
const QSize &pixelSize,
int sampleCount,