diff options
author | Allan Sandfeld Jensen <allan.jensen@digia.com> | 2013-08-09 11:15:45 +0200 |
---|---|---|
committer | The Qt Project <gerrit-noreply@qt-project.org> | 2013-08-09 17:36:24 +0200 |
commit | 87780ea2c08c8a46f474f23584c4c8154551e689 (patch) | |
tree | 2f42a272625e4e42ebdf620a11fac4cc58da2a99 | |
parent | eab5d78ef51a9a36414960714853341087bb8e99 (diff) | |
download | qtwebkit-87780ea2c08c8a46f474f23584c4c8154551e689.tar.gz |
[Qt] REGRESSION(r) Two pixel result fail after r153522
https://bugs.webkit.org/show_bug.cgi?id=119392
Reviewed by Jocelyn Turcotte.
Consider scaling transform on the painter to determine final destination size.
Covered by existing tests.
* platform/graphics/qt/ImageQt.cpp:
(WebCore::prescaleImageIfRequired):
(WebCore::BitmapImage::draw):
Change-Id: I631e0925abaf814c95f709c18919f127c8b41503
git-svn-id: http://svn.webkit.org/repository/webkit/trunk@153790 268f45cc-cd09-0410-ab3c-d52691b4dbfc
Reviewed-by: Jocelyn Turcotte <jocelyn.turcotte@digia.com>
-rw-r--r-- | Source/WebCore/platform/graphics/qt/ImageQt.cpp | 77 |
1 files changed, 45 insertions, 32 deletions
diff --git a/Source/WebCore/platform/graphics/qt/ImageQt.cpp b/Source/WebCore/platform/graphics/qt/ImageQt.cpp index 0c66fe5fb..4fb3090fc 100644 --- a/Source/WebCore/platform/graphics/qt/ImageQt.cpp +++ b/Source/WebCore/platform/graphics/qt/ImageQt.cpp @@ -42,7 +42,6 @@ #include <wtf/text/WTFString.h> #include <QCoreApplication> -#include <QDebug> #include <QImage> #include <QImageReader> #include <QPainter> @@ -232,6 +231,49 @@ void BitmapImage::invalidatePlatformData() { } +QPixmap* prescaleImageIfRequired(QPainter* painter, QPixmap* image, QPixmap* buffer, const QRectF& destRect, QRectF* srcRect) +{ + // The quality of down scaling at 0.5x and below in QPainter is not very good + // due to using bilinear sampling, so for high quality scaling we need to + // perform scaling ourselves. + ASSERT(image); + ASSERT(painter); + if (!(painter->renderHints() & QPainter::SmoothPixmapTransform)) + return image; + + QTransform transform = painter->combinedTransform(); + + // Prescaling transforms that does more than scale or translate is not supported. + if (transform.type() > QTransform::TxScale) + return image; + + QRectF transformedDst = transform.mapRect(destRect); + // Only prescale if downscaling to 0.5x or less + if (transformedDst.width() * 2 > srcRect->width() && transformedDst.height() * 2 > srcRect->height()) + return image; + + // This may not work right with subpixel positions, but that can not currently happen. + QRect pixelSrc = srcRect->toRect(); + QSize scaledSize = transformedDst.size().toSize(); + + QString key = QStringLiteral("qtwebkit_prescaled_") + % HexString<qint64>(image->cacheKey()) + % HexString<int>(pixelSrc.x()) % HexString<int>(pixelSrc.y()) + % HexString<int>(pixelSrc.width()) % HexString<int>(pixelSrc.height()) + % HexString<int>(scaledSize.width()) % HexString<int>(scaledSize.height()); + + if (!QPixmapCache::find(key, buffer)) { + if (pixelSrc != image->rect()) + *buffer = image->copy(pixelSrc).scaled(scaledSize, Qt::IgnoreAspectRatio, Qt::SmoothTransformation); + else + *buffer = image->scaled(scaledSize, Qt::IgnoreAspectRatio, Qt::SmoothTransformation); + QPixmapCache::insert(key, *buffer); + } + + *srcRect = QRectF(QPointF(), buffer->size()); + return buffer; +} + // Drawing Routines void BitmapImage::draw(GraphicsContext* ctxt, const FloatRect& dst, const FloatRect& src, ColorSpace styleColorSpace, CompositeOperator op) @@ -247,7 +289,6 @@ void BitmapImage::draw(GraphicsContext* ctxt, const FloatRect& dst, QPixmap* image = nativeImageForCurrentFrame(); if (!image) return; - QPixmap prescaled; if (mayFillWithSolidColor()) { fillWithSolidColor(ctxt, normalizedDst, solidColor(), styleColorSpace, op); @@ -258,36 +299,8 @@ void BitmapImage::draw(GraphicsContext* ctxt, const FloatRect& dst, normalizedSrc = adjustSourceRectForDownSampling(normalizedSrc, image->size()); #endif - QPainter* painter = ctxt->platformContext(); - // The quality of down scaling at 0.5x and below in QPainter is not very good - // due only using bilinear sampling, so for high quality scaling we need to - // perform scaling ourselves. -#if QT_VERSION >= QT_VERSION_CHECK(5, 1, 0) - const float pixelRatio = painter->device()->devicePixelRatio(); -#else - const float pixelRatio = 1; -#endif - if (painter->renderHints() & QPainter::SmoothPixmapTransform - && (normalizedDst.width() * 2 * pixelRatio < normalizedSrc.width() - || normalizedDst.height() * 2 * pixelRatio < normalizedSrc.height())) { - // This may not work right with subpixel positions, but that can not currently happen. - QRect pixelSrc = normalizedSrc.toRect(); - QSize scaledSize(normalizedDst.width() * pixelRatio, normalizedDst.height() * pixelRatio); - QString key = QStringLiteral("qtwebkit_prescaled_") - % HexString<qint64>(image->cacheKey()) - % HexString<int>(pixelSrc.x()) % HexString<int>(pixelSrc.y()) - % HexString<int>(pixelSrc.width()) % HexString<int>(pixelSrc.height()) - % HexString<int>(scaledSize.width()) % HexString<int>(scaledSize.height()); - if (!QPixmapCache::find(key, &prescaled)) { - if (pixelSrc != image->rect()) - prescaled = image->copy(pixelSrc).scaled(scaledSize, Qt::IgnoreAspectRatio, Qt::SmoothTransformation); - else - prescaled = image->scaled(scaledSize, Qt::IgnoreAspectRatio, Qt::SmoothTransformation); - QPixmapCache::insert(key, prescaled); - } - normalizedSrc = QRectF(QPointF(), prescaled.size()); - image = &prescaled; - } + QPixmap prescaledBuffer; + image = prescaleImageIfRequired(ctxt->platformContext(), image, &prescaledBuffer, normalizedDst, &normalizedSrc); CompositeOperator previousOperator = ctxt->compositeOperation(); ctxt->setCompositeOperation(!image->hasAlpha() && op == CompositeSourceOver ? CompositeCopy : op); |