Revert hacks in text rendering code path
authorEskil Abrahamsen Blomfeldt <eskil.abrahamsen-blomfeldt@nokia.com>
Tue, 23 Oct 2012 11:14:27 +0000 (13:14 +0200)
committerThe Qt Project <gerrit-noreply@qt-project.org>
Thu, 25 Oct 2012 12:10:04 +0000 (14:10 +0200)
There are a lot of hacks here and there in Qt trying to align the
text in a correct way which caused regressions to appear once
the default coordinate system changed. We need to remove these
hacks to get a more consistent and maintainable base. This also
fixes the regression introduced by changing the aliased coordinate
system.

Task-number: QTBUG-27667

Change-Id: I620db2ca23b7ff6c912f3a51e86e7e36bbef81f0
Reviewed-by: Samuel Rødal <samuel.rodal@digia.com>
src/gui/opengl/qopenglpaintengine.cpp
src/gui/painting/qpaintengine_raster.cpp
src/gui/painting/qpainter.cpp
src/gui/text/qtextengine.cpp
src/gui/text/qtextengine_p.h
src/opengl/gl2paintengineex/qpaintengineex_opengl2.cpp

index 8e96720..624eeaf 100644 (file)
@@ -1638,7 +1638,7 @@ void QOpenGL2PaintEngineExPrivate::drawCachedGlyphs(QFontEngineGlyphCache::Type
                 continue;
 
             int x = qFloor(staticTextItem->glyphPositions[i].x) + c.baseLineX - margin;
-            int y = qFloor(staticTextItem->glyphPositions[i].y) - c.baseLineY - margin;
+            int y = qRound(staticTextItem->glyphPositions[i].y) - c.baseLineY - margin;
 
             vertexCoordinates->addQuad(QRectF(x, y, c.w, c.h));
             textureCoordinates->addQuad(QRectF(c.x*dx, c.y*dy, c.w * dx, c.h * dy));
index 1a63ced..fec01af 100644 (file)
@@ -2787,7 +2787,7 @@ bool QRasterPaintEngine::drawCachedGlyphs(int numGlyphs, const glyph_t *glyphs,
 
             alphaPenBlt(alphaMap->bits(), alphaMap->bytesPerLine(), alphaMap->depth(),
                         qFloor(positions[i].x) + offset.x(),
-                        qFloor(positions[i].y) + offset.y(),
+                        qRound(positions[i].y) + offset.y(),
                         alphaMap->width(), alphaMap->height());
 
             fontEngine->unlockAlphaMapForGlyph();
@@ -2818,7 +2818,6 @@ bool QRasterPaintEngine::drawCachedGlyphs(int numGlyphs, const glyph_t *glyphs,
             rightShift = 3; // divide by 8
 
         int margin = fontEngine->glyphMargin(glyphType);
-        const QFixed offs = s->flags.legacy_rounding ? QFixed::fromReal(aliasedCoordinateDelta) : QFixed();
         const uchar *bits = image.bits();
         for (int i=0; i<numGlyphs; ++i) {
 
@@ -2829,7 +2828,7 @@ bool QRasterPaintEngine::drawCachedGlyphs(int numGlyphs, const glyph_t *glyphs,
                 continue;
 
             int x = qFloor(positions[i].x) + c.baseLineX - margin;
-            int y = qFloor(positions[i].y + offs) - c.baseLineY - margin;
+            int y = qRound(positions[i].y) - c.baseLineY - margin;
 
             // printf("drawing [%d %d %d %d] baseline [%d %d], glyph: %d, to: %d %d, pos: %d %d\n",
             //        c.x, c.y,
index 090faf1..7070e57 100644 (file)
@@ -6182,10 +6182,16 @@ static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const
 
     QLineF line(pos.x(), pos.y(), pos.x() + qFloor(width), pos.y());
 
+    bool wasCompatiblePainting = painter->renderHints()
+            & QPainter::Qt4CompatiblePainting;
+
+    if (wasCompatiblePainting)
+        painter->setRenderHint(QPainter::Qt4CompatiblePainting, false);
+
     const qreal underlineOffset = fe->underlinePosition().toReal();
     // deliberately ceil the offset to avoid the underline coming too close to
     // the text above it.
-    const qreal underlinePos = pos.y() + qCeil(underlineOffset);
+    const qreal underlinePos = pos.y() + qCeil(underlineOffset) + 0.5;
 
     if (underlineStyle == QTextCharFormat::SpellCheckUnderline) {
         QPlatformTheme *theme = QGuiApplicationPrivate::platformTheme();
@@ -6247,6 +6253,9 @@ static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const
 
     painter->setPen(oldPen);
     painter->setBrush(oldBrush);
+
+    if (wasCompatiblePainting)
+        painter->setRenderHint(QPainter::Qt4CompatiblePainting);
 }
 
 Q_GUI_EXPORT void qt_draw_decoration_for_glyphs(QPainter *painter, const glyph_t *glyphArray,
@@ -7500,36 +7509,16 @@ start_lengthVariant:
 
     qreal yoff = 0;
     qreal xoff = 0;
-    if (tf & Qt::AlignBottom) {
+    if (tf & Qt::AlignBottom)
         yoff = r.height() - height;
-    } else if (tf & Qt::AlignVCenter) {
+    else if (tf & Qt::AlignVCenter)
         yoff = (r.height() - height)/2;
-        if (painter) {
-            QTransform::TransformationType type = painter->transform().type();
-            if (type <= QTransform::TxScale) {
-                // do the rounding manually to work around inconsistencies
-                // in the paint engines when drawing on floating point offsets
-                const qreal scale = painter->transform().m22();
-                if (scale != 0)
-                    yoff = -qRound(-yoff * scale) / scale;
-            }
-        }
-    }
-    if (tf & Qt::AlignRight) {
+
+    if (tf & Qt::AlignRight)
         xoff = r.width() - width;
-    } else if (tf & Qt::AlignHCenter) {
+    else if (tf & Qt::AlignHCenter)
         xoff = (r.width() - width)/2;
-        if (painter) {
-            QTransform::TransformationType type = painter->transform().type();
-            if (type <= QTransform::TxScale) {
-                // do the rounding manually to work around inconsistencies
-                // in the paint engines when drawing on floating point offsets
-                const qreal scale = painter->transform().m11();
-                if (scale != 0)
-                    xoff = qRound(xoff * scale) / scale;
-            }
-        }
-    }
+
     QRectF bounds = QRectF(r.x() + xoff, r.y() + yoff, width, height);
 
     if (hasMoreLengthVariants && !(tf & Qt::TextLongestVariant) && !r.contains(bounds)) {
index 38fe2f8..025d428 100644 (file)
@@ -3060,8 +3060,7 @@ void QTextEngine::drawItemDecorationList(QPainter *painter, const ItemDecoration
 
     foreach (const ItemDecoration &decoration, decorationList) {
         painter->setPen(decoration.pen);
-        QLineF line(decoration.x1, decoration.y, decoration.x2, decoration.y);
-        painter->drawLine(line);
+        painter->drawLine(QLineF(decoration.x1, decoration.y, decoration.x2, decoration.y));
     }
 }
 
@@ -3069,13 +3068,23 @@ void QTextEngine::drawDecorations(QPainter *painter)
 {
     QPen oldPen = painter->pen();
 
+    bool wasCompatiblePainting = painter->renderHints()
+            & QPainter::Qt4CompatiblePainting;
+
+    if (wasCompatiblePainting)
+        painter->setRenderHint(QPainter::Qt4CompatiblePainting, false);
+
     adjustUnderlines();
     drawItemDecorationList(painter, underlineList);
     drawItemDecorationList(painter, strikeOutList);
     drawItemDecorationList(painter, overlineList);
 
-    painter->setPen(oldPen);
     clearDecorations();
+
+    if (wasCompatiblePainting)
+        painter->setRenderHint(QPainter::Qt4CompatiblePainting);
+
+    painter->setPen(oldPen);
 }
 
 void QTextEngine::clearDecorations()
index 8246722..aff5e1c 100644 (file)
@@ -390,7 +390,7 @@ struct Q_AUTOTEST_EXPORT QScriptLine
     mutable uint gridfitted : 1;
     uint hasTrailingSpaces : 1;
     uint leadingIncluded : 1;
-    QFixed height() const { return (ascent + descent).ceil()
+    QFixed height() const { return ascent + descent
                             + (leadingIncluded?  qMax(QFixed(),leading) : QFixed()); }
     QFixed base() const { return ascent
                           + (leadingIncluded ? qMax(QFixed(),leading) : QFixed()); }
index e542397..7284efa 100644 (file)
@@ -1675,7 +1675,7 @@ void QGL2PaintEngineExPrivate::drawCachedGlyphs(QFontEngineGlyphCache::Type glyp
                 continue;
 
             int x = qFloor(staticTextItem->glyphPositions[i].x) + c.baseLineX - margin;
-            int y = qFloor(staticTextItem->glyphPositions[i].y) - c.baseLineY - margin;
+            int y = qRound(staticTextItem->glyphPositions[i].y) - c.baseLineY - margin;
 
             vertexCoordinates->addQuad(QRectF(x, y, c.w, c.h));
             textureCoordinates->addQuad(QRectF(c.x*dx, c.y*dy, c.w * dx, c.h * dy));