diff options
Diffstat (limited to 'src/gui')
-rw-r--r-- | src/gui/image/qimage_p.h | 6 | ||||
-rw-r--r-- | src/gui/kernel/qopenglwindow.cpp | 6 | ||||
-rw-r--r-- | src/gui/opengl/qopenglframebufferobject.cpp | 4 | ||||
-rw-r--r-- | src/gui/opengl/qopenglpaintengine.cpp | 53 | ||||
-rw-r--r-- | src/gui/opengl/qopenglpaintengine_p.h | 2 | ||||
-rw-r--r-- | src/gui/painting/qdrawhelper.cpp | 7 | ||||
-rw-r--r-- | src/gui/text/qfontengine_ft.cpp | 22 | ||||
-rw-r--r-- | src/gui/text/qfontengine_ft_p.h | 2 |
8 files changed, 61 insertions, 41 deletions
diff --git a/src/gui/image/qimage_p.h b/src/gui/image/qimage_p.h index 26c42b988e..47e68b14a5 100644 --- a/src/gui/image/qimage_p.h +++ b/src/gui/image/qimage_p.h @@ -116,6 +116,9 @@ void qInitImageConversions(); const uchar *qt_get_bitflip_array(); Q_GUI_EXPORT void qGamma_correct_back_to_linear_cs(QImage *image); +#if defined(Q_OS_WINRT) && defined(_M_ARM) // QTBUG-42038 +#pragma optimize("", off) +#endif inline int qt_depthForFormat(QImage::Format format) { int depth = 0; @@ -160,6 +163,9 @@ inline int qt_depthForFormat(QImage::Format format) } return depth; } +#if defined(Q_OS_WINRT) && defined(_M_ARM) +#pragma optimize("", on) +#endif QT_END_NAMESPACE diff --git a/src/gui/kernel/qopenglwindow.cpp b/src/gui/kernel/qopenglwindow.cpp index 158fb248dc..c37974c429 100644 --- a/src/gui/kernel/qopenglwindow.cpp +++ b/src/gui/kernel/qopenglwindow.cpp @@ -38,6 +38,7 @@ #include <QtGui/QOpenGLFunctions> #include <QtGui/private/qopengltextureblitter_p.h> #include <QtGui/private/qopenglextensions_p.h> +#include <QtGui/private/qopenglcontext_p.h> #include <QtGui/QMatrix4x4> #include <QtGui/QOffscreenSurface> @@ -101,6 +102,10 @@ QT_BEGIN_NAMESPACE this way they do not have to redraw the entire window content on each paintGL() call. + Similarly to QOpenGLWidget, QOpenGLWindow supports the Qt::AA_ShareOpenGLContexts + attribute. When enabled, the OpenGL contexts of all QOpenGLWindow instances will share + with each other. This allows accessing each other's shareable OpenGL resources. + For more information on graphics in Qt, see \l {Graphics}. */ @@ -196,6 +201,7 @@ public: if (!context) { context.reset(new QOpenGLContext); + context->setShareContext(qt_gl_global_share_context()); context->setFormat(q->requestedFormat()); if (!context->create()) qWarning("QOpenGLWindow::beginPaint: Failed to create context"); diff --git a/src/gui/opengl/qopenglframebufferobject.cpp b/src/gui/opengl/qopenglframebufferobject.cpp index 124d9d53f6..6351b8a1e3 100644 --- a/src/gui/opengl/qopenglframebufferobject.cpp +++ b/src/gui/opengl/qopenglframebufferobject.cpp @@ -481,11 +481,9 @@ void QOpenGLFramebufferObjectPrivate::init(QOpenGLFramebufferObject *, const QSi GLenum storageFormat = internal_format; // ES requires a sized format. The older desktop extension does not. Correct the format on ES. if (ctx->isOpenGLES() && internal_format == GL_RGBA) { -#ifdef GL_RGBA8_OES if (funcs.hasOpenGLExtension(QOpenGLExtensions::Sized8Formats)) - storageFormat = GL_RGBA8_OES; + storageFormat = GL_RGBA8; else -#endif storageFormat = GL_RGBA4; } diff --git a/src/gui/opengl/qopenglpaintengine.cpp b/src/gui/opengl/qopenglpaintengine.cpp index 299d3da73d..bfc08a5332 100644 --- a/src/gui/opengl/qopenglpaintengine.cpp +++ b/src/gui/opengl/qopenglpaintengine.cpp @@ -107,7 +107,7 @@ QOpenGL2PaintEngineExPrivate::~QOpenGL2PaintEngineExPrivate() } } -void QOpenGL2PaintEngineExPrivate::updateTextureFilter(GLenum target, GLenum wrapMode, bool smoothPixmapTransform, GLuint id) +void QOpenGL2PaintEngineExPrivate::updateTextureFilter(GLenum wrapMode, bool smoothPixmapTransform, GLuint id) { // funcs.glActiveTexture(GL_TEXTURE0 + QT_BRUSH_TEXTURE_UNIT); //### Is it always this texture unit? if (id != GLuint(-1) && id == lastTextureUsed) @@ -115,6 +115,8 @@ void QOpenGL2PaintEngineExPrivate::updateTextureFilter(GLenum target, GLenum wra lastTextureUsed = id; + static const GLenum target = GL_TEXTURE_2D; + if (smoothPixmapTransform) { funcs.glTexParameteri(target, GL_TEXTURE_MAG_FILTER, GL_LINEAR); funcs.glTexParameteri(target, GL_TEXTURE_MIN_FILTER, GL_LINEAR); @@ -122,6 +124,7 @@ void QOpenGL2PaintEngineExPrivate::updateTextureFilter(GLenum target, GLenum wra funcs.glTexParameteri(target, GL_TEXTURE_MAG_FILTER, GL_NEAREST); funcs.glTexParameteri(target, GL_TEXTURE_MIN_FILTER, GL_NEAREST); } + funcs.glTexParameteri(target, GL_TEXTURE_WRAP_S, wrapMode); funcs.glTexParameteri(target, GL_TEXTURE_WRAP_T, wrapMode); } @@ -185,7 +188,7 @@ void QOpenGL2PaintEngineExPrivate::updateBrushTexture() funcs.glActiveTexture(GL_TEXTURE0 + QT_BRUSH_TEXTURE_UNIT); QOpenGLTextureCache::cacheForContext(ctx)->bindTexture(ctx, texImage); - updateTextureFilter(GL_TEXTURE_2D, GL_REPEAT, q->state()->renderHints & QPainter::SmoothPixmapTransform); + updateTextureFilter(GL_REPEAT, q->state()->renderHints & QPainter::SmoothPixmapTransform); } else if (style >= Qt::LinearGradientPattern && style <= Qt::ConicalGradientPattern) { // Gradiant brush: All the gradiants use the same texture @@ -196,15 +199,15 @@ void QOpenGL2PaintEngineExPrivate::updateBrushTexture() // for opacity to the cache. GLuint texId = QOpenGL2GradientCache::cacheForContext(ctx)->getBuffer(*g, 1.0); - funcs.glActiveTexture(GL_TEXTURE0 + QT_BRUSH_TEXTURE_UNIT); - funcs.glBindTexture(GL_TEXTURE_2D, texId); - + GLenum wrapMode = GL_CLAMP_TO_EDGE; if (g->spread() == QGradient::RepeatSpread || g->type() == QGradient::ConicalGradient) - updateTextureFilter(GL_TEXTURE_2D, GL_REPEAT, q->state()->renderHints & QPainter::SmoothPixmapTransform); + wrapMode = GL_REPEAT; else if (g->spread() == QGradient::ReflectSpread) - updateTextureFilter(GL_TEXTURE_2D, GL_MIRRORED_REPEAT, q->state()->renderHints & QPainter::SmoothPixmapTransform); - else - updateTextureFilter(GL_TEXTURE_2D, GL_CLAMP_TO_EDGE, q->state()->renderHints & QPainter::SmoothPixmapTransform); + wrapMode = GL_MIRRORED_REPEAT; + + funcs.glActiveTexture(GL_TEXTURE0 + QT_BRUSH_TEXTURE_UNIT); + funcs.glBindTexture(GL_TEXTURE_2D, texId); + updateTextureFilter(wrapMode, q->state()->renderHints & QPainter::SmoothPixmapTransform); } else if (style == Qt::TexturePattern) { currentBrushImage = currentBrush.textureImage(); @@ -223,7 +226,8 @@ void QOpenGL2PaintEngineExPrivate::updateBrushTexture() funcs.glActiveTexture(GL_TEXTURE0 + QT_BRUSH_TEXTURE_UNIT); QOpenGLTextureCache::cacheForContext(ctx)->bindTexture(ctx, currentBrushImage); - updateTextureFilter(GL_TEXTURE_2D, wrapMode, q->state()->renderHints & QPainter::SmoothPixmapTransform); + updateTextureFilter(wrapMode, q->state()->renderHints & QPainter::SmoothPixmapTransform); + textureInvertedY = false; } brushTextureDirty = false; @@ -1380,16 +1384,14 @@ void QOpenGL2PaintEngineEx::drawPixmap(const QRectF& dest, const QPixmap & pixma d->funcs.glActiveTexture(GL_TEXTURE0 + QT_IMAGE_TEXTURE_UNIT); GLuint id = QOpenGLTextureCache::cacheForContext(ctx)->bindTexture(ctx, pixmap); - - QOpenGLRect srcRect(src.left(), src.top(), src.right(), src.bottom()); + d->updateTextureFilter(GL_CLAMP_TO_EDGE, state()->renderHints & QPainter::SmoothPixmapTransform, id); bool isBitmap = pixmap.isQBitmap(); bool isOpaque = !isBitmap && !pixmap.hasAlpha(); - d->updateTextureFilter(GL_TEXTURE_2D, GL_CLAMP_TO_EDGE, - state()->renderHints & QPainter::SmoothPixmapTransform, id); - d->shaderManager->setSrcPixelType(isBitmap ? QOpenGLEngineShaderManager::PatternSrc : QOpenGLEngineShaderManager::ImageSrc); + + QOpenGLRect srcRect(src.left(), src.top(), src.right(), src.bottom()); d->drawTexture(dest, srcRect, pixmap.size(), isOpaque, isBitmap); } @@ -1442,9 +1444,7 @@ void QOpenGL2PaintEngineEx::drawImage(const QRectF& dest, const QImage& image, c d->funcs.glActiveTexture(GL_TEXTURE0 + QT_IMAGE_TEXTURE_UNIT); GLuint id = QOpenGLTextureCache::cacheForContext(ctx)->bindTexture(ctx, image, bindOption); - - d->updateTextureFilter(GL_TEXTURE_2D, GL_CLAMP_TO_EDGE, - state()->renderHints & QPainter::SmoothPixmapTransform, id); + d->updateTextureFilter(GL_CLAMP_TO_EDGE, state()->renderHints & QPainter::SmoothPixmapTransform, id); d->drawTexture(dest, src, image.size(), !image.hasAlphaChannel()); } @@ -1487,13 +1487,13 @@ bool QOpenGL2PaintEngineEx::drawTexture(const QRectF &dest, GLuint textureId, co d->funcs.glActiveTexture(GL_TEXTURE0 + QT_IMAGE_TEXTURE_UNIT); d->funcs.glBindTexture(GL_TEXTURE_2D, textureId); + d->updateTextureFilter(GL_CLAMP_TO_EDGE, state()->renderHints & QPainter::SmoothPixmapTransform, textureId); - QOpenGLRect srcRect(src.left(), src.bottom(), src.right(), src.top()); - - d->updateTextureFilter(GL_TEXTURE_2D, GL_CLAMP_TO_EDGE, - state()->renderHints & QPainter::SmoothPixmapTransform, textureId); d->shaderManager->setSrcPixelType(QOpenGLEngineShaderManager::ImageSrc); + + QOpenGLRect srcRect(src.left(), src.bottom(), src.right(), src.top()); d->drawTexture(dest, srcRect, size, false); + return true; } @@ -1821,7 +1821,7 @@ void QOpenGL2PaintEngineExPrivate::drawCachedGlyphs(QFontEngine::GlyphFormat gly funcs.glActiveTexture(GL_TEXTURE0 + QT_MASK_TEXTURE_UNIT); funcs.glBindTexture(GL_TEXTURE_2D, cache->texture()); - updateTextureFilter(GL_TEXTURE_2D, GL_REPEAT, false); + updateTextureFilter(GL_REPEAT, false); #if defined(QT_OPENGL_DRAWCACHEDGLYPHS_INDEX_ARRAY_VBO) funcs.glDrawElements(GL_TRIANGLE_STRIP, 6 * numGlyphs, GL_UNSIGNED_SHORT, 0); @@ -1964,16 +1964,15 @@ void QOpenGL2PaintEngineExPrivate::drawPixmapFragments(const QPainter::PixmapFra allOpaque &= (opacity >= 0.99f); } + transferMode(ImageOpacityArrayDrawingMode); + funcs.glActiveTexture(GL_TEXTURE0 + QT_IMAGE_TEXTURE_UNIT); GLuint id = QOpenGLTextureCache::cacheForContext(ctx)->bindTexture(ctx, pixmap); - transferMode(ImageOpacityArrayDrawingMode); + updateTextureFilter(GL_CLAMP_TO_EDGE, q->state()->renderHints & QPainter::SmoothPixmapTransform, id); bool isBitmap = pixmap.isQBitmap(); bool isOpaque = !isBitmap && (!pixmap.hasAlpha() || (hints & QPainter::OpaqueHint)) && allOpaque; - updateTextureFilter(GL_TEXTURE_2D, GL_CLAMP_TO_EDGE, - q->state()->renderHints & QPainter::SmoothPixmapTransform, id); - // Setup for texture drawing currentBrush = noBrush; shaderManager->setSrcPixelType(isBitmap ? QOpenGLEngineShaderManager::PatternSrc diff --git a/src/gui/opengl/qopenglpaintengine_p.h b/src/gui/opengl/qopenglpaintengine_p.h index 47e915eae5..85ecd82b6f 100644 --- a/src/gui/opengl/qopenglpaintengine_p.h +++ b/src/gui/opengl/qopenglpaintengine_p.h @@ -193,7 +193,7 @@ public: void updateBrushUniforms(); void updateMatrix(); void updateCompositionMode(); - void updateTextureFilter(GLenum target, GLenum wrapMode, bool smoothPixmapTransform, GLuint id = GLuint(-1)); + void updateTextureFilter(GLenum wrapMode, bool smoothPixmapTransform, GLuint id = GLuint(-1)); void resetGLState(); diff --git a/src/gui/painting/qdrawhelper.cpp b/src/gui/painting/qdrawhelper.cpp index a991b89f48..bd53952d1b 100644 --- a/src/gui/painting/qdrawhelper.cpp +++ b/src/gui/painting/qdrawhelper.cpp @@ -6288,6 +6288,8 @@ static inline void rgbBlendPixel(quint32 *dst, int coverage, int sr, int sg, int } #if defined(Q_OS_WIN) && !defined(Q_OS_WINCE) +Q_GUI_EXPORT bool qt_needs_a8_gamma_correction = false; + static inline void grayBlendPixel(quint32 *dst, int coverage, int sr, int sg, int sb, const uint *gamma, const uchar *invgamma) { // Do a gammacorrected gray alphablend... @@ -6335,6 +6337,7 @@ static void qt_alphamapblit_argb32(QRasterBuffer *rasterBuffer, int sb = gamma[qBlue(color)]; bool opaque_src = (qAlpha(color) == 255); + bool doGrayBlendPixel = opaque_src && qt_needs_a8_gamma_correction; #endif if (!clip) { @@ -6349,7 +6352,7 @@ static void qt_alphamapblit_argb32(QRasterBuffer *rasterBuffer, dest[i] = c; } else { #if defined(Q_OS_WIN) && !defined(Q_OS_WINCE) - if (QSysInfo::WindowsVersion >= QSysInfo::WV_XP && opaque_src + if (QSysInfo::WindowsVersion >= QSysInfo::WV_XP && doGrayBlendPixel && qAlpha(dest[i]) == 255) { grayBlendPixel(dest+i, coverage, sr, sg, sb, gamma, invgamma); } else @@ -6390,7 +6393,7 @@ static void qt_alphamapblit_argb32(QRasterBuffer *rasterBuffer, dest[xp] = c; } else { #if defined(Q_OS_WIN) && !defined(Q_OS_WINCE) - if (QSysInfo::WindowsVersion >= QSysInfo::WV_XP && opaque_src + if (QSysInfo::WindowsVersion >= QSysInfo::WV_XP && doGrayBlendPixel && qAlpha(dest[xp]) == 255) { grayBlendPixel(dest+xp, coverage, sr, sg, sb, gamma, invgamma); } else diff --git a/src/gui/text/qfontengine_ft.cpp b/src/gui/text/qfontengine_ft.cpp index ef397e532c..4d6c04a262 100644 --- a/src/gui/text/qfontengine_ft.cpp +++ b/src/gui/text/qfontengine_ft.cpp @@ -762,8 +762,10 @@ bool QFontEngineFT::init(FaceId faceId, bool antialias, GlyphFormat format, face->face_flags &= ~FT_FACE_FLAG_SCALABLE; FT_Select_Size(face, i); - metrics.ascender = face->size->metrics.ascender; - metrics.descender = face->size->metrics.descender; + if (face->size->metrics.ascender + face->size->metrics.descender > 0) { + metrics.ascender = face->size->metrics.ascender; + metrics.descender = face->size->metrics.descender; + } FT_Set_Char_Size(face, xsize, ysize, 0, 0); face->face_flags |= FT_FACE_FLAG_SCALABLE; @@ -889,6 +891,13 @@ QFontEngineFT::Glyph *QFontEngineFT::loadGlyph(QGlyphSet *set, uint glyph, // this is an error in the bytecode interpreter, just try to run without it load_flags |= FT_LOAD_FORCE_AUTOHINT; err = FT_Load_Glyph(face, glyph, load_flags); + } else if (err == FT_Err_Execution_Too_Long) { + // This is an error in the bytecode, probably a web font made by someone who + // didn't test bytecode hinting at all so disable for it for all glyphs. + qWarning("load glyph failed due to broken hinting bytecode in font, switching to auto hinting"); + default_load_flags |= FT_LOAD_FORCE_AUTOHINT; + load_flags |= FT_LOAD_FORCE_AUTOHINT; + err = FT_Load_Glyph(face, glyph, load_flags); } if (err != FT_Err_Ok) { qWarning("load glyph failed err=%x face=%p, glyph=%d", err, face, glyph); @@ -1123,7 +1132,7 @@ QFontEngineFT::Glyph *QFontEngineFT::loadGlyph(QGlyphSet *set, uint glyph, while (h--) { uint *dd = (uint *)dst; *dd++ = 0; - for (int x = 0; x < slot->bitmap.width; x++) { + for (int x = 0; x < static_cast<int>(slot->bitmap.width); x++) { uint a = ((src[x >> 3] & (0x80 >> (x & 7))) ? 0xffffff : 0x000000); *dd++ = a; } @@ -1134,7 +1143,7 @@ QFontEngineFT::Glyph *QFontEngineFT::loadGlyph(QGlyphSet *set, uint glyph, } else if (vfactor != 1) { while (h--) { uint *dd = (uint *)dst; - for (int x = 0; x < slot->bitmap.width; x++) { + for (int x = 0; x < static_cast<int>(slot->bitmap.width); x++) { uint a = ((src[x >> 3] & (0x80 >> (x & 7))) ? 0xffffff : 0x000000); *dd++ = a; } @@ -1143,7 +1152,7 @@ QFontEngineFT::Glyph *QFontEngineFT::loadGlyph(QGlyphSet *set, uint glyph, } } else { while (h--) { - for (int x = 0; x < slot->bitmap.width; x++) { + for (int x = 0; x < static_cast<int>(slot->bitmap.width); x++) { unsigned char a = ((src[x >> 3] & (0x80 >> (x & 7))) ? 0xff : 0x00); dst[x] = a; } @@ -1771,8 +1780,7 @@ glyph_metrics_t QFontEngineFT::alphaMapBoundingBox(glyph_t glyph, QFixed subPixe overall.x = TRUNC(left); overall.y = -TRUNC(top); overall.xoff = TRUNC(ROUND(face->glyph->advance.x)); - if (face) - unlockFace(); + unlockFace(); } return overall; } diff --git a/src/gui/text/qfontengine_ft_p.h b/src/gui/text/qfontengine_ft_p.h index 4c29b5a504..02c692cccc 100644 --- a/src/gui/text/qfontengine_ft_p.h +++ b/src/gui/text/qfontengine_ft_p.h @@ -293,7 +293,7 @@ private: protected: QFreetypeFace *freetype; - int default_load_flags; + mutable int default_load_flags; HintStyle default_hint_style; bool antialias; bool transform; |