diff options
author | Allan Sandfeld Jensen <allan.jensen@qt.io> | 2018-05-18 17:03:58 +0200 |
---|---|---|
committer | Allan Sandfeld Jensen <allan.jensen@qt.io> | 2021-05-26 18:00:01 +0200 |
commit | 93cd9130d6d8d30e901dd3b2f2546dbc63754e2e (patch) | |
tree | 3def7382cd1e4edd4ff380587deee775e48a2e4b /src/opengl | |
parent | e51831260a759b58cb089cac089c202a795fc584 (diff) |
Introduce float QImage formats and rendering
Useful for some HDR representations and HDR rendering.
Change-Id: If6e8a661faa3d2afdf17b6ed4d8ff5c5b2aeb30e
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@qt.io>
Reviewed-by: Lars Knoll <lars.knoll@qt.io>
Diffstat (limited to 'src/opengl')
-rw-r--r-- | src/opengl/qopenglframebufferobject.cpp | 44 | ||||
-rw-r--r-- | src/opengl/qopenglpaintengine.cpp | 2 | ||||
-rw-r--r-- | src/opengl/qopengltextureuploader.cpp | 39 |
3 files changed, 85 insertions, 0 deletions
diff --git a/src/opengl/qopenglframebufferobject.cpp b/src/opengl/qopenglframebufferobject.cpp index 78b192b630..aa1c396892 100644 --- a/src/opengl/qopenglframebufferobject.cpp +++ b/src/opengl/qopenglframebufferobject.cpp @@ -152,6 +152,25 @@ QT_BEGIN_NAMESPACE #define GL_DEPTH_STENCIL 0x84F9 #endif +#ifndef GL_HALF_FLOAT +#define GL_HALF_FLOAT 0x140B +#endif + +#ifndef GL_RGBA32F +#define GL_RGBA32F 0x8814 +#endif + +#ifndef GL_RGB32F +#define GL_RGB32F 0x8815 +#endif + +#ifndef GL_RGBA16F +#define GL_RGBA16F 0x881A +#endif + +#ifndef GL_RGB16F +#define GL_RGB16F 0x881B +#endif /*! @@ -554,6 +573,8 @@ void QOpenGLFramebufferObjectPrivate::initTexture(int idx) pixelType = GL_UNSIGNED_INT_2_10_10_10_REV; else if (color.internalFormat == GL_RGB16 || color.internalFormat == GL_RGBA16) pixelType = GL_UNSIGNED_SHORT; + else if (color.internalFormat == GL_RGB16F || color.internalFormat == GL_RGBA16F) + pixelType = GL_HALF_FLOAT; funcs.glTexImage2D(target, 0, color.internalFormat, color.size.width(), color.size.height(), 0, GL_RGBA, pixelType, nullptr); @@ -1379,6 +1400,21 @@ static inline QImage qt_gl_read_framebuffer_rgba16(const QSize &size, bool inclu return img; } +static inline QImage qt_gl_read_framebuffer_rgba16f(const QSize &size, bool include_alpha, QOpenGLContext *context) +{ + // We assume OpenGL (ES) 3.0+ here. + QImage img(size, include_alpha ? QImage::Format_RGBA16FPx4_Premultiplied : QImage::Format_RGBX16FPx4); + context->functions()->glReadPixels(0, 0, size.width(), size.height(), GL_RGBA, GL_HALF_FLOAT, img.bits()); + return img; +} + +static inline QImage qt_gl_read_framebuffer_rgba32f(const QSize &size, bool include_alpha, QOpenGLContext *context) +{ + QImage img(size, include_alpha ? QImage::Format_RGBA32FPx4_Premultiplied : QImage::Format_RGBX32FPx4); + context->functions()->glReadPixels(0, 0, size.width(), size.height(), GL_RGBA, GL_FLOAT, img.bits()); + return img; +} + static QImage qt_gl_read_framebuffer(const QSize &size, GLenum internal_format, bool include_alpha, bool flip) { QOpenGLContext *ctx = QOpenGLContext::currentContext(); @@ -1400,6 +1436,14 @@ static QImage qt_gl_read_framebuffer(const QSize &size, GLenum internal_format, return qt_gl_read_framebuffer_rgba16(size, false, ctx).mirrored(false, flip); case GL_RGBA16: return qt_gl_read_framebuffer_rgba16(size, include_alpha, ctx).mirrored(false, flip); + case GL_RGB16F: + return qt_gl_read_framebuffer_rgba16f(size, false, ctx).mirrored(false, flip); + case GL_RGBA16F: + return qt_gl_read_framebuffer_rgba16f(size, include_alpha, ctx).mirrored(false, flip); + case GL_RGB32F: + return qt_gl_read_framebuffer_rgba32f(size, false, ctx).mirrored(false, flip); + case GL_RGBA32F: + return qt_gl_read_framebuffer_rgba32f(size, include_alpha, ctx).mirrored(false, flip); case GL_RGBA: case GL_RGBA8: default: diff --git a/src/opengl/qopenglpaintengine.cpp b/src/opengl/qopenglpaintengine.cpp index 7da9bf143d..8606a2e7ef 100644 --- a/src/opengl/qopenglpaintengine.cpp +++ b/src/opengl/qopenglpaintengine.cpp @@ -1572,6 +1572,8 @@ void QOpenGL2PaintEngineEx::drawImage(const QRectF& dest, const QImage& image, c case QImage::Format_RGBA8888: case QImage::Format_ARGB32: case QImage::Format_RGBA64: + case QImage::Format_RGBA16FPx4: + case QImage::Format_RGBA32FPx4: d->shaderManager->setSrcPixelType(QOpenGLEngineShaderManager::NonPremultipliedImageSrc); bindOption = { }; break; diff --git a/src/opengl/qopengltextureuploader.cpp b/src/opengl/qopengltextureuploader.cpp index 469ddc56c1..488baf32ad 100644 --- a/src/opengl/qopengltextureuploader.cpp +++ b/src/opengl/qopengltextureuploader.cpp @@ -45,6 +45,10 @@ #include <private/qopenglcontext_p.h> #include <private/qopenglextensions_p.h> +#ifndef GL_HALF_FLOAT +#define GL_HALF_FLOAT 0x140B +#endif + #ifndef GL_RED #define GL_RED 0x1903 #endif @@ -81,6 +85,14 @@ #define GL_UNSIGNED_INT_2_10_10_10_REV 0x8368 #endif +#ifndef GL_RGBA16F +#define GL_RGBA16F 0x881A +#endif + +#ifndef GL_RGBA32F +#define GL_RGBA32F 0x8814 +#endif + #ifndef GL_TEXTURE_SWIZZLE_R #define GL_TEXTURE_SWIZZLE_R 0x8E42 #endif @@ -236,6 +248,25 @@ qsizetype QOpenGLTextureUploader::textureImage(GLenum target, const QImage &imag pixelType = GL_UNSIGNED_SHORT; targetFormat = image.format(); break; + case QImage::Format_RGBX16FPx4: + case QImage::Format_RGBA16FPx4: + case QImage::Format_RGBA16FPx4_Premultiplied: + if (context->format().majorVersion() >= 3) { + externalFormat = GL_RGBA; + internalFormat = GL_RGBA16F; + pixelType = GL_HALF_FLOAT; + targetFormat = image.format(); + } + break; + case QImage::Format_RGBX32FPx4: + case QImage::Format_RGBA32FPx4: + case QImage::Format_RGBA32FPx4_Premultiplied: + externalFormat = internalFormat = GL_RGBA; + if (context->format().majorVersion() >= 3) + internalFormat = GL_RGBA32F; + pixelType = GL_FLOAT; + targetFormat = image.format(); + break; case QImage::Format_Indexed8: if (sRgbBinding) { // Always needs conversion @@ -333,6 +364,10 @@ qsizetype QOpenGLTextureUploader::textureImage(GLenum target, const QImage &imag targetFormat = QImage::Format_RGBA8888_Premultiplied; else if (targetFormat == QImage::Format_RGBA64) targetFormat = QImage::Format_RGBA64_Premultiplied; + else if (targetFormat == QImage::Format_RGBA16FPx4) + targetFormat = QImage::Format_RGBA16FPx4_Premultiplied; + else if (targetFormat == QImage::Format_RGBA32FPx4) + targetFormat = QImage::Format_RGBA32FPx4_Premultiplied; } else { if (targetFormat == QImage::Format_ARGB32_Premultiplied) targetFormat = QImage::Format_ARGB32; @@ -340,6 +375,10 @@ qsizetype QOpenGLTextureUploader::textureImage(GLenum target, const QImage &imag targetFormat = QImage::Format_RGBA8888; else if (targetFormat == QImage::Format_RGBA64_Premultiplied) targetFormat = QImage::Format_RGBA64; + else if (targetFormat == QImage::Format_RGBA16FPx4_Premultiplied) + targetFormat = QImage::Format_RGBA16FPx4; + else if (targetFormat == QImage::Format_RGBA32FPx4_Premultiplied) + targetFormat = QImage::Format_RGBA32FPx4; } if (sRgbBinding) { |