summaryrefslogtreecommitdiffstats
path: root/src/gui/painting/qpaintengine_raster.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/gui/painting/qpaintengine_raster.cpp')
-rw-r--r--src/gui/painting/qpaintengine_raster.cpp157
1 files changed, 48 insertions, 109 deletions
diff --git a/src/gui/painting/qpaintengine_raster.cpp b/src/gui/painting/qpaintengine_raster.cpp
index 5bdf3299c9..40c822076b 100644
--- a/src/gui/painting/qpaintengine_raster.cpp
+++ b/src/gui/painting/qpaintengine_raster.cpp
@@ -555,35 +555,6 @@ bool QRasterPaintEngine::end()
/*!
\internal
*/
-void QRasterPaintEngine::releaseBuffer()
-{
- Q_D(QRasterPaintEngine);
- d->rasterBuffer.reset(new QRasterBuffer);
-}
-
-/*!
- \internal
-*/
-QSize QRasterPaintEngine::size() const
-{
- Q_D(const QRasterPaintEngine);
- return QSize(d->rasterBuffer->width(), d->rasterBuffer->height());
-}
-
-/*!
- \internal
-*/
-#ifndef QT_NO_DEBUG
-void QRasterPaintEngine::saveBuffer(const QString &s) const
-{
- Q_D(const QRasterPaintEngine);
- d->rasterBuffer->bufferImage().save(s, "PNG");
-}
-#endif
-
-/*!
- \internal
-*/
void QRasterPaintEngine::updateMatrix(const QTransform &matrix)
{
QRasterPaintEngineState *s = state();
@@ -871,8 +842,8 @@ void QRasterPaintEngine::updateRasterState()
const QPainter::CompositionMode mode = s->composition_mode;
s->flags.fast_text = (s->penData.type == QSpanData::Solid)
&& s->intOpacity == 256
- && (mode == QPainter::CompositionMode_Source
- || (mode == QPainter::CompositionMode_SourceOver
+ && (mode == QPainter::CompositionMode_SourceOver
+ || (mode == QPainter::CompositionMode_Source
&& s->penData.solidColor.isOpaque()));
}
@@ -927,13 +898,20 @@ void QRasterPaintEngine::renderHintsChanged()
QRasterPaintEngineState *s = state();
#ifdef QT_DEBUG_DRAW
- qDebug() << "QRasterPaintEngine::renderHintsChanged()" << hex << s->renderHints;
+ qDebug() << "QRasterPaintEngine::renderHintsChanged()" << Qt::hex << s->renderHints;
#endif
bool was_aa = s->flags.antialiased;
bool was_bilinear = s->flags.bilinear;
- s->flags.antialiased = bool(s->renderHints & (QPainter::Antialiasing | QPainter::HighQualityAntialiasing));
+ s->flags.antialiased = bool(s->renderHints & QPainter::Antialiasing);
+#if QT_DEPRECATED_SINCE(5, 14)
+QT_WARNING_PUSH
+QT_WARNING_DISABLE_DEPRECATED
+ if (s->renderHints & QPainter::HighQualityAntialiasing)
+ s->flags.antialiased = true;
+QT_WARNING_POP
+#endif
s->flags.bilinear = bool(s->renderHints & QPainter::SmoothPixmapTransform);
s->flags.legacy_rounding = !bool(s->renderHints & QPainter::Antialiasing) && bool(s->renderHints & QPainter::Qt4CompatiblePainting);
@@ -1341,7 +1319,7 @@ void QRasterPaintEngine::clip(const QRect &rect, Qt::ClipOperation op)
QPaintEngineEx::clip(rect, op);
return;
- } else if (!setClipRectInDeviceCoords(s->matrix.mapRect(rect), op)) {
+ } else if (!setClipRectInDeviceCoords(s->matrix.mapRect(QRectF(rect)).toRect(), op)) {
QPaintEngineEx::clip(rect, op);
return;
}
@@ -1774,7 +1752,7 @@ void QRasterPaintEngine::fill(const QVectorPath &path, const QBrush &brush)
QRectF rf = path.controlPointRect();
qDebug() << "QRasterPaintEngine::fill(): "
<< "size=" << path.elementCount()
- << ", hints=" << hex << path.hints()
+ << ", hints=" << Qt::hex << path.hints()
<< rf << brush;
#endif
@@ -2239,7 +2217,7 @@ void QRasterPaintEngine::drawImage(const QPointF &p, const QImage &img)
const QClipData *clip = d->clip();
QPointF pt(p.x() + s->matrix.dx(), p.y() + s->matrix.dy());
- if (d->canUseImageBlitting(d->rasterBuffer->compositionMode, img)) {
+ if (d->canUseImageBlitting(d->rasterBuffer->compositionMode, img, pt, img.rect())) {
if (!clip) {
d->blitImage(pt, img, d->deviceRect);
return;
@@ -2310,7 +2288,12 @@ namespace {
return NoRotation;
}
- inline bool isPixelAligned(const QRectF &rect) {
+ inline bool isPixelAligned(const QPointF &pt)
+ {
+ return QPointF(pt.toPoint()) == pt;
+ }
+ inline bool isPixelAligned(const QRectF &rect)
+ {
return QRectF(rect.toRect()) == rect;
}
}
@@ -2378,17 +2361,12 @@ void QRasterPaintEngine::drawImage(const QRectF &r, const QImage &img, const QRe
const QClipData *clip = d->clip();
- if (s->matrix.type() > QTransform::TxTranslate
+ if (s->matrix.type() == QTransform::TxRotate
&& !stretch_sr
&& (!clip || clip->hasRectClip)
&& s->intOpacity == 256
&& (d->rasterBuffer->compositionMode == QPainter::CompositionMode_SourceOver
- || d->rasterBuffer->compositionMode == QPainter::CompositionMode_Source)
- && d->rasterBuffer->format == img.format()
- && (d->rasterBuffer->format == QImage::Format_RGB16
- || d->rasterBuffer->format == QImage::Format_RGB32
- || (d->rasterBuffer->format == QImage::Format_ARGB32_Premultiplied
- && d->rasterBuffer->compositionMode == QPainter::CompositionMode_Source)))
+ || d->rasterBuffer->compositionMode == QPainter::CompositionMode_Source))
{
RotationType rotationType = qRotationType(s->matrix);
const QPixelLayout::BPP plBpp = qPixelLayouts[d->rasterBuffer->format].bpp;
@@ -2396,9 +2374,7 @@ void QRasterPaintEngine::drawImage(const QRectF &r, const QImage &img, const QRe
if (rotationType != NoRotation && qMemRotateFunctions[plBpp][rotationType] && img.rect().contains(sr.toAlignedRect())) {
QRectF transformedTargetRect = s->matrix.mapRect(r);
- if ((!(s->renderHints & QPainter::SmoothPixmapTransform) && !(s->renderHints & QPainter::Antialiasing))
- || (isPixelAligned(transformedTargetRect) && isPixelAligned(sr)))
- {
+ if (d->canUseImageBlitting(d->rasterBuffer->compositionMode, img, transformedTargetRect.topRight(), sr)) {
QRect clippedTransformedTargetRect = transformedTargetRect.toRect().intersected(clip ? clip->clipRect : d->deviceRect);
if (clippedTransformedTargetRect.isNull())
return;
@@ -2532,8 +2508,8 @@ void QRasterPaintEngine::drawImage(const QRectF &r, const QImage &img, const QRe
fillPath(path, &d->image_filler_xform);
s->matrix = m;
} else {
- if (d->canUseImageBlitting(d->rasterBuffer->compositionMode, img)) {
- QPointF pt(r.x() + s->matrix.dx(), r.y() + s->matrix.dy());
+ QPointF pt(r.x() + s->matrix.dx(), r.y() + s->matrix.dy());
+ if (d->canUseImageBlitting(d->rasterBuffer->compositionMode, img, pt, sr)) {
if (!clip) {
d->blitImage(pt, img, d->deviceRect, sr.toRect());
return;
@@ -2544,7 +2520,6 @@ void QRasterPaintEngine::drawImage(const QRectF &r, const QImage &img, const QRe
} else if (d->canUseFastImageBlending(d->rasterBuffer->compositionMode, img)) {
SrcOverBlendFunc func = qBlendFunctions[d->rasterBuffer->format][img.format()];
if (func) {
- QPointF pt(r.x() + s->matrix.dx(), r.y() + s->matrix.dy());
if (!clip) {
d->drawImage(pt, img, func, d->deviceRect, s->intOpacity, sr.toRect());
return;
@@ -3779,12 +3754,22 @@ bool QRasterPaintEnginePrivate::canUseFastImageBlending(QPainter::CompositionMod
&& !image.hasAlphaChannel()));
}
-bool QRasterPaintEnginePrivate::canUseImageBlitting(QPainter::CompositionMode mode, const QImage &image) const
+bool QRasterPaintEnginePrivate::canUseImageBlitting(QPainter::CompositionMode mode, const QImage &image, const QPointF &pt, const QRectF &sr) const
{
Q_Q(const QRasterPaintEngine);
+
+ if (!(mode == QPainter::CompositionMode_Source
+ || (mode == QPainter::CompositionMode_SourceOver
+ && !image.hasAlphaChannel())))
+ return false;
+
const QRasterPaintEngineState *s = q->state();
+ Q_ASSERT(s->matrix.type() <= QTransform::TxTranslate || s->matrix.type() == QTransform::TxRotate);
- if (!s->flags.fast_images || s->intOpacity != 256 || qt_depthForFormat(rasterBuffer->format) < 8)
+ if (s->intOpacity != 256
+ || image.depth() < 8
+ || ((s->renderHints & (QPainter::SmoothPixmapTransform | QPainter::Antialiasing))
+ && (!isPixelAligned(pt) || !isPixelAligned(sr))))
return false;
QImage::Format dFormat = rasterBuffer->format;
@@ -3792,18 +3777,13 @@ bool QRasterPaintEnginePrivate::canUseImageBlitting(QPainter::CompositionMode mo
// Formats must match or source format must be a subset of destination format
if (dFormat != sFormat && image.pixelFormat().alphaUsage() == QPixelFormat::IgnoresAlpha) {
if ((sFormat == QImage::Format_RGB32 && dFormat == QImage::Format_ARGB32)
- || (sFormat == QImage::Format_RGBX8888 && dFormat == QImage::Format_RGBA8888))
+ || (sFormat == QImage::Format_RGBX8888 && dFormat == QImage::Format_RGBA8888)
+ || (sFormat == QImage::Format_RGBX64 && dFormat == QImage::Format_RGBA64))
sFormat = dFormat;
else
sFormat = qt_maybeAlphaVersionWithSameDepth(sFormat); // this returns premul formats
}
- if (dFormat != sFormat)
- return false;
-
- return s->matrix.type() <= QTransform::TxTranslate
- && (mode == QPainter::CompositionMode_Source
- || (mode == QPainter::CompositionMode_SourceOver
- && !image.hasAlphaChannel()));
+ return (dFormat == sFormat);
}
QImage QRasterBuffer::colorizeBitmap(const QImage &image, const QColor &color)
@@ -3860,11 +3840,6 @@ QImage::Format QRasterBuffer::prepare(QImage *image)
return format;
}
-void QRasterBuffer::resetBuffer(int val)
-{
- memset(m_buffer, val, m_height*bytes_per_line);
-}
-
QClipData::QClipData(int height)
{
clipSpanHeight = height;
@@ -4291,55 +4266,13 @@ static void qt_span_clip(int count, const QSpan *spans, void *userData)
}
}
-#ifndef QT_NO_DEBUG
-QImage QRasterBuffer::bufferImage() const
-{
- QImage image(m_width, m_height, QImage::Format_ARGB32_Premultiplied);
-
- for (int y = 0; y < m_height; ++y) {
- uint *span = (uint *)const_cast<QRasterBuffer *>(this)->scanLine(y);
-
- for (int x=0; x<m_width; ++x) {
- uint argb = span[x];
- image.setPixel(x, y, argb);
- }
- }
- return image;
-}
-#endif
-
-
-void QRasterBuffer::flushToARGBImage(QImage *target) const
-{
- int w = qMin(m_width, target->width());
- int h = qMin(m_height, target->height());
-
- for (int y=0; y<h; ++y) {
- uint *sourceLine = (uint *)const_cast<QRasterBuffer *>(this)->scanLine(y);
- QRgb *dest = (QRgb *) target->scanLine(y);
- for (int x=0; x<w; ++x) {
- QRgb pixel = sourceLine[x];
- int alpha = qAlpha(pixel);
- if (!alpha) {
- dest[x] = 0;
- } else {
- dest[x] = (alpha << 24)
- | ((255*qRed(pixel)/alpha) << 16)
- | ((255*qGreen(pixel)/alpha) << 8)
- | ((255*qBlue(pixel)/alpha) << 0);
- }
- }
- }
-}
-
-
class QGradientCache
{
public:
struct CacheInfo : QSpanData::Pinnable
{
inline CacheInfo(QGradientStops s, int op, QGradient::InterpolationMode mode) :
- stops(qMove(s)), opacity(op), interpolationMode(mode) {}
+ stops(std::move(s)), opacity(op), interpolationMode(mode) {}
QRgba64 buffer64[GRADIENT_STOPTABLE_SIZE];
QRgb buffer32[GRADIENT_STOPTABLE_SIZE];
QGradientStops stops;
@@ -4382,7 +4315,7 @@ protected:
QSharedPointer<const CacheInfo> addCacheElement(quint64 hash_val, const QGradient &gradient, int opacity) {
if (cache.size() == maxCacheSize()) {
// may remove more than 1, but OK
- cache.erase(cache.begin() + QRandomGenerator::global()->bounded(maxCacheSize()));
+ cache.erase(std::next(cache.begin(), QRandomGenerator::global()->bounded(maxCacheSize())));
}
auto cache_entry = QSharedPointer<CacheInfo>::create(gradient.stops(), opacity, gradient.interpolationMode());
generateGradientColorTable(gradient, cache_entry->buffer64, paletteSize(), opacity);
@@ -4626,7 +4559,9 @@ void QSpanData::setup(const QBrush &brush, int alpha, QPainter::CompositionMode
auto cacheInfo = qt_gradient_cache()->getBuffer(*g, alpha);
gradient.colorTable32 = cacheInfo->buffer32;
+#if QT_CONFIG(raster_64bit)
gradient.colorTable64 = cacheInfo->buffer64;
+#endif
cachedGradient = std::move(cacheInfo);
gradient.spread = g->spread();
@@ -4648,7 +4583,9 @@ void QSpanData::setup(const QBrush &brush, int alpha, QPainter::CompositionMode
auto cacheInfo = qt_gradient_cache()->getBuffer(*g, alpha);
gradient.colorTable32 = cacheInfo->buffer32;
+#if QT_CONFIG(raster_64bit)
gradient.colorTable64 = cacheInfo->buffer64;
+#endif
cachedGradient = std::move(cacheInfo);
gradient.spread = g->spread();
@@ -4674,7 +4611,9 @@ void QSpanData::setup(const QBrush &brush, int alpha, QPainter::CompositionMode
auto cacheInfo = qt_gradient_cache()->getBuffer(*g, alpha);
gradient.colorTable32 = cacheInfo->buffer32;
+#if QT_CONFIG(raster_64bit)
gradient.colorTable64 = cacheInfo->buffer64;
+#endif
cachedGradient = std::move(cacheInfo);
gradient.spread = QGradient::RepeatSpread;