diff --git a/src/libkwineffects/kwineglimagetexture.cpp b/src/libkwineffects/kwineglimagetexture.cpp index 97c0c8abd2..fd5e763162 100644 --- a/src/libkwineffects/kwineglimagetexture.cpp +++ b/src/libkwineffects/kwineglimagetexture.cpp @@ -17,12 +17,10 @@ namespace KWin { EGLImageTexture::EGLImageTexture(::EGLDisplay display, EGLImage image, uint textureId, int internalFormat, const QSize &size) - : GLTexture(textureId, internalFormat, size, 1, true) + : GLTexture(textureId, internalFormat, size, 1, true, TextureTransform::MirrorY) , m_image(image) , m_display(display) { - d->m_foreign = false; - setContentTransform(TextureTransform::MirrorY); } EGLImageTexture::~EGLImageTexture() diff --git a/src/libkwineffects/kwingltexture.cpp b/src/libkwineffects/kwingltexture.cpp index 321129fb5f..3845bc821c 100644 --- a/src/libkwineffects/kwingltexture.cpp +++ b/src/libkwineffects/kwingltexture.cpp @@ -88,10 +88,10 @@ GLTexture::GLTexture(GLenum target) d->m_target = target; } -GLTexture::GLTexture(GLuint textureId, GLenum internalFormat, const QSize &size, int levels, bool isImmutable) +GLTexture::GLTexture(GLuint textureId, GLenum internalFormat, const QSize &size, int levels, bool owning, TextureTransforms transform) : GLTexture(GL_TEXTURE_2D) { - d->m_foreign = true; + d->m_owning = owning; d->m_texture = textureId; d->m_scale.setWidth(1.0 / size.width()); d->m_scale.setHeight(1.0 / size.height()); @@ -100,7 +100,7 @@ GLTexture::GLTexture(GLuint textureId, GLenum internalFormat, const QSize &size, d->m_mipLevels = levels; d->m_filter = levels > 1 ? GL_NEAREST_MIPMAP_LINEAR : GL_NEAREST; d->m_internalFormat = internalFormat; - d->m_immutable = isImmutable; + d->m_textureToBufferTransform = transform; d->updateMatrix(); } @@ -128,8 +128,7 @@ GLTexturePrivate::GLTexturePrivate() , m_markedDirty(false) , m_filterChanged(true) , m_wrapModeChanged(false) - , m_immutable(false) - , m_foreign(false) + , m_owning(true) , m_mipLevels(1) , m_unnormalizeActive(0) , m_normalizeActive(0) @@ -138,7 +137,7 @@ GLTexturePrivate::GLTexturePrivate() GLTexturePrivate::~GLTexturePrivate() { - if (m_texture != 0 && !m_foreign) { + if (m_texture != 0 && m_owning) { glDeleteTextures(1, &m_texture); } } @@ -205,7 +204,7 @@ void GLTexture::update(const QImage &image, const QPoint &offset, const QRect &s return; } - Q_ASSERT(!d->m_foreign); + Q_ASSERT(d->m_owning); GLenum glFormat; GLenum type; @@ -417,7 +416,7 @@ GLenum GLTexture::internalFormat() const void GLTexture::clear() { - Q_ASSERT(!d->m_foreign); + Q_ASSERT(d->m_owning); if (!GLTexturePrivate::s_fbo && GLFramebuffer::supported() && GLPlatform::instance()->driver() != Driver_Catalyst) { // fail. -> bug #323065 glGenFramebuffers(1, &GLTexturePrivate::s_fbo); } @@ -601,7 +600,12 @@ QImage GLTexture::toImage() const return ret; } -std::unique_ptr GLTexture::allocate(GLenum internalFormat, const QSize &size, int levels, bool needsMutability) +std::unique_ptr GLTexture::createNonOwningWrapper(GLuint textureId, GLenum internalFormat, const QSize &size) +{ + return std::unique_ptr(new GLTexture(textureId, internalFormat, size, 1, false, TextureTransforms{})); +} + +std::unique_ptr GLTexture::allocate(GLenum internalFormat, const QSize &size, int levels) { GLuint texture = 0; glGenTextures(1, &texture); @@ -611,12 +615,9 @@ std::unique_ptr GLTexture::allocate(GLenum internalFormat, const QSiz } glBindTexture(GL_TEXTURE_2D, texture); - bool immutable = false; - if (!GLPlatform::instance()->isGLES()) { - if (GLTexturePrivate::s_supportsTextureStorage && !needsMutability) { + if (GLTexturePrivate::s_supportsTextureStorage) { glTexStorage2D(GL_TEXTURE_2D, levels, internalFormat, size.width(), size.height()); - immutable = true; } else { glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, levels - 1); glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, size.width(), size.height(), 0, @@ -634,9 +635,7 @@ std::unique_ptr GLTexture::allocate(GLenum internalFormat, const QSiz // internalFormat() won't need to be specialized for GLES2. } glBindTexture(GL_TEXTURE_2D, 0); - auto ret = std::make_unique(texture, internalFormat, size, levels, immutable); - ret->d->m_foreign = false; - return ret; + return std::unique_ptr(new GLTexture(texture, internalFormat, size, levels, true, TextureTransforms{})); } std::unique_ptr GLTexture::upload(const QImage &image) @@ -653,7 +652,6 @@ std::unique_ptr GLTexture::upload(const QImage &image) glBindTexture(GL_TEXTURE_2D, texture); GLenum internalFormat; - bool immutable = false; if (!GLPlatform::instance()->isGLES()) { QImage im; GLenum format; @@ -678,7 +676,6 @@ std::unique_ptr GLTexture::upload(const QImage &image) glTexStorage2D(GL_TEXTURE_2D, 1, internalFormat, im.width(), im.height()); glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, im.width(), im.height(), format, type, im.constBits()); - immutable = true; } else { glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0); glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, im.width(), im.height(), 0, @@ -698,10 +695,7 @@ std::unique_ptr GLTexture::upload(const QImage &image) } } glBindTexture(GL_TEXTURE_2D, 0); - auto ret = std::make_unique(texture, internalFormat, image.size(), 1, immutable); - ret->setContentTransform(TextureTransform::MirrorY); - ret->d->m_foreign = false; - return ret; + return std::unique_ptr(new GLTexture(texture, internalFormat, image.size(), 1, true, TextureTransform::MirrorY)); } std::unique_ptr GLTexture::upload(const QPixmap &pixmap) diff --git a/src/libkwineffects/kwingltexture.h b/src/libkwineffects/kwingltexture.h index 4e4868b868..9570504353 100644 --- a/src/libkwineffects/kwingltexture.h +++ b/src/libkwineffects/kwingltexture.h @@ -56,13 +56,6 @@ public: * for the texture. */ bool create(); - - /** - * Create a GLTexture wrapper around an existing texture. - * Management of the underlying texture remains the responsibility of the caller. - * @since 5.18 - */ - explicit GLTexture(GLuint textureId, GLenum internalFormat, const QSize &size, int levels = 1, bool isImmutable = false); virtual ~GLTexture(); bool isNull() const; @@ -153,11 +146,14 @@ public: */ static bool supportsFormatRG(); - static std::unique_ptr allocate(GLenum internalFormat, const QSize &size, int levels = 1, bool needsMutability = false); + static std::unique_ptr createNonOwningWrapper(GLuint textureId, GLenum internalFormat, const QSize &size); + static std::unique_ptr allocate(GLenum internalFormat, const QSize &size, int levels = 1); static std::unique_ptr upload(const QImage &image); static std::unique_ptr upload(const QPixmap &pixmap); protected: + explicit GLTexture(GLuint textureId, GLenum internalFormat, const QSize &size, int levels, bool owning, TextureTransforms transform); + const std::unique_ptr d; virtual void onDamage(); diff --git a/src/libkwineffects/kwingltexture_p.h b/src/libkwineffects/kwingltexture_p.h index e9834b0b6c..1dcc8ac5ed 100644 --- a/src/libkwineffects/kwingltexture_p.h +++ b/src/libkwineffects/kwingltexture_p.h @@ -49,8 +49,7 @@ public: bool m_markedDirty; bool m_filterChanged; bool m_wrapModeChanged; - bool m_immutable; - bool m_foreign; + bool m_owning; int m_mipLevels; int m_unnormalizeActive; // 0 - no, otherwise refcount diff --git a/src/libkwineffects/kwinoffscreenquickview.cpp b/src/libkwineffects/kwinoffscreenquickview.cpp index 1d78bc2145..339eb3844d 100644 --- a/src/libkwineffects/kwinoffscreenquickview.cpp +++ b/src/libkwineffects/kwinoffscreenquickview.cpp @@ -413,7 +413,7 @@ GLTexture *OffscreenQuickView::bufferAsTexture() return nullptr; } if (!d->m_textureExport) { - d->m_textureExport.reset(new GLTexture(d->m_fbo->texture(), d->m_fbo->format().internalTextureFormat(), d->m_fbo->size())); + d->m_textureExport = GLTexture::createNonOwningWrapper(d->m_fbo->texture(), d->m_fbo->format().internalTextureFormat(), d->m_fbo->size()); } } return d->m_textureExport.get(); diff --git a/src/platformsupport/scenes/opengl/basiceglsurfacetexture_internal.cpp b/src/platformsupport/scenes/opengl/basiceglsurfacetexture_internal.cpp index d5689d9f80..e4134a214b 100644 --- a/src/platformsupport/scenes/opengl/basiceglsurfacetexture_internal.cpp +++ b/src/platformsupport/scenes/opengl/basiceglsurfacetexture_internal.cpp @@ -49,7 +49,7 @@ bool BasicEGLSurfaceTextureInternal::updateFromFramebuffer() if (!fbo) { return false; } - m_texture.reset(new GLTexture(fbo->texture(), 0, fbo->size())); + m_texture = GLTexture::createNonOwningWrapper(fbo->texture(), 0, fbo->size()); m_texture->setWrapMode(GL_CLAMP_TO_EDGE); m_texture->setFilter(GL_LINEAR); m_texture->setContentTransform(TextureTransforms());