Make QPen default to 1-width non-cosmetic.
[profile/ivi/qtbase.git] / src / gui / painting / qpainter.cpp
index 38f4ebd..090faf1 100644 (file)
@@ -1,38 +1,38 @@
 /****************************************************************************
 **
-** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
-** All rights reserved.
-** Contact: Nokia Corporation (qt-info@nokia.com)
+** Copyright (C) 2012 Digia Plc and/or its subsidiary(-ies).
+** Contact: http://www.qt-project.org/legal
 **
 ** This file is part of the QtGui module of the Qt Toolkit.
 **
 ** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and Digia.  For licensing terms and
+** conditions see http://qt.digia.com/licensing.  For further information
+** use the contact form at http://qt.digia.com/contact-us.
+**
 ** GNU Lesser General Public License Usage
-** This file may be used under the terms of the GNU Lesser General Public
-** License version 2.1 as published by the Free Software Foundation and
-** appearing in the file LICENSE.LGPL included in the packaging of this
-** file. Please review the following information to ensure the GNU Lesser
-** General Public License version 2.1 requirements will be met:
-** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file.  Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
 **
-** In addition, as a special exception, Nokia gives you certain additional
-** rights. These rights are described in the Nokia Qt LGPL Exception
+** In addition, as a special exception, Digia gives you certain additional
+** rights.  These rights are described in the Digia Qt LGPL Exception
 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
 **
 ** GNU General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU General
-** Public License version 3.0 as published by the Free Software Foundation
-** and appearing in the file LICENSE.GPL included in the packaging of this
-** file. Please review the following information to ensure the GNU General
-** Public License version 3.0 requirements will be met:
-** http://www.gnu.org/copyleft/gpl.html.
-**
-** Other Usage
-** Alternatively, this file may be used in accordance with the terms and
-** conditions contained in a signed written agreement between you and Nokia.
-**
-**
-**
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3.0 as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL included in the
+** packaging of this file.  Please review the following information to
+** ensure the GNU General Public License version 3.0 requirements will be
+** met: http://www.gnu.org/copyleft/gpl.html.
 **
 **
 ** $QT_END_LICENSE$
@@ -61,6 +61,8 @@
 #include "qstatictext.h"
 #include "qglyphrun.h"
 
+#include <qpa/qplatformtheme.h>
+
 #include <private/qfontengine_p.h>
 #include <private/qpaintengine_p.h>
 #include <private/qemulationpaintengine_p.h>
@@ -90,7 +92,7 @@ void qt_format_text(const QFont &font,
                     const QRectF &_r, int tf, const QTextOption *option, const QString& str, QRectF *brect,
                     int tabstops, int* tabarray, int tabarraylen,
                     QPainter *painter);
-static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const QFontEngine *fe,
+static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const QFontEngine *fe, QTextEngine *textEngine,
                                    QTextCharFormat::UnderlineStyle underlineStyle,
                                    QTextItem::RenderFlags flags, qreal width,
                                    const QTextCharFormat &charFormat);
@@ -895,26 +897,8 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     if (!newState) {
         engine->state = newState;
-
     } else if (newState->state() || engine->state!=newState) {
-        bool setNonCosmeticPen = (newState->renderHints & QPainter::NonCosmeticDefaultPen)
-                                 && newState->pen.widthF() == 0;
-        if (setNonCosmeticPen) {
-            // Override the default pen's cosmetic state if the
-            // NonCosmeticDefaultPen render hint is used.
-            QPen oldPen = newState->pen;
-            newState->pen.setWidth(1);
-            newState->pen.setCosmetic(false);
-            newState->dirtyFlags |= QPaintEngine::DirtyPen;
-
-            updateStateImpl(newState);
-
-            // Restore the state pen back to its default to preserve visible
-            // state.
-            newState->pen = oldPen;
-        } else {
-            updateStateImpl(newState);
-        }
+        updateStateImpl(newState);
     }
 }
 
@@ -924,6 +908,7 @@ void QPainterPrivate::updateState(QPainterState *newState)
     \brief The QPainter class performs low-level painting on widgets and
     other paint devices.
 
+    \inmodule QtGui
     \ingroup painting
 
     \reentrant
@@ -941,7 +926,7 @@ void QPainterPrivate::updateState(QPainterState *newState)
     painter. Then draw. Remember to destroy the QPainter object after
     drawing. For example:
 
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 0
+    \snippet code/src_gui_painting_qpainter.cpp 0
 
     The core functionality of QPainter is drawing, but the class also
     provide several functions that allows you to customize QPainter's
@@ -970,10 +955,7 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \warning When the paintdevice is a widget, QPainter can only be
     used inside a paintEvent() function or in a function called by
-    paintEvent(); that is unless the Qt::WA_PaintOutsidePaintEvent
-    widget attribute is set. On Mac OS X and Windows, you can only
-    paint in a paintEvent() function regardless of this attribute's
-    setting.
+    paintEvent().
 
     \tableofcontents
 
@@ -984,41 +966,41 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \list
 
-    \o font() is the font used for drawing text. If the painter
+    \li font() is the font used for drawing text. If the painter
         isActive(), you can retrieve information about the currently set
         font, and its metrics, using the fontInfo() and fontMetrics()
         functions respectively.
 
-    \o brush() defines the color or pattern that is used for filling
+    \li brush() defines the color or pattern that is used for filling
        shapes.
 
-    \o pen() defines the color or stipple that is used for drawing
+    \li pen() defines the color or stipple that is used for drawing
        lines or boundaries.
 
-    \o backgroundMode() defines whether there is a background() or
+    \li backgroundMode() defines whether there is a background() or
        not, i.e it is either Qt::OpaqueMode or Qt::TransparentMode.
 
-    \o background() only applies when backgroundMode() is \l
+    \li background() only applies when backgroundMode() is \l
        Qt::OpaqueMode and pen() is a stipple. In that case, it
        describes the color of the background pixels in the stipple.
 
-    \o brushOrigin() defines the origin of the tiled brushes, normally
+    \li brushOrigin() defines the origin of the tiled brushes, normally
        the origin of widget's background.
 
-    \o viewport(), window(), worldTransform() make up the painter's coordinate
+    \li viewport(), window(), worldTransform() make up the painter's coordinate
         transformation system. For more information, see the \l
         {Coordinate Transformations} section and the \l {Coordinate
         System} documentation.
 
-    \o hasClipping() tells whether the painter clips at all. (The paint
+    \li hasClipping() tells whether the painter clips at all. (The paint
        device clips, too.) If the painter clips, it clips to clipRegion().
 
-    \o layoutDirection() defines the layout direction used by the
+    \li layoutDirection() defines the layout direction used by the
        painter when drawing text.
 
-    \o worldMatrixEnabled() tells whether world transformation is enabled.
+    \li worldMatrixEnabled() tells whether world transformation is enabled.
 
-    \o viewTransformEnabled() tells whether view transformation is
+    \li viewTransformEnabled() tells whether view transformation is
         enabled.
 
     \endlist
@@ -1052,9 +1034,9 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-basicdrawing.png
-    \o
-    \bold {Basic Drawing Example}
+    \li \inlineimage qpainter-basicdrawing.png
+    \li
+    \b {Basic Drawing Example}
 
     The \l {painting/basicdrawing}{Basic Drawing} example shows how to
     display basic graphics primitives in a variety of styles using the
@@ -1068,8 +1050,8 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \table 100%
     \row
-    \o
-    \bold {Painter Paths example}
+    \li
+    \b {Painter Paths example}
 
     The QPainterPath class provides a container for painting
     operations, enabling graphical shapes to be constructed and
@@ -1078,7 +1060,7 @@ void QPainterPrivate::updateState(QPainterState *newState)
     The \l {painting/painterpaths}{Painter Paths} example shows how
     painter paths can be used to build complex shapes for rendering.
 
-    \o \inlineimage qpainter-painterpaths.png
+    \li \inlineimage qpainter-painterpaths.png
     \endtable
 
     QPainter also provides the fillPath() function which fills the
@@ -1096,13 +1078,13 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \table
     \header
-    \o \l {painting/deform}{Vector Deformation}
-    \o \l {painting/gradients}{Gradients}
-    \o \l {painting/pathstroke}{Path Stroking}
+    \li \l {painting/deform}{Vector Deformation}
+    \li \l {painting/gradients}{Gradients}
+    \li \l {painting/pathstroke}{Path Stroking}
     \row
-    \o \inlineimage qpainter-vectordeformation.png
-    \o \inlineimage qpainter-gradients.png
-    \o \inlineimage qpainter-pathstroking.png
+    \li \inlineimage qpainter-vectordeformation.png
+    \li \inlineimage qpainter-gradients.png
+    \li \inlineimage qpainter-pathstroking.png
     \endtable
 
 
@@ -1136,9 +1118,9 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-concentriccircles.png
-    \o
-    \bold {Concentric Circles Example}
+    \li \inlineimage qpainter-concentriccircles.png
+    \li
+    \b {Concentric Circles Example}
 
     The \l {painting/concentriccircles}{Concentric Circles} example
     shows the improved rendering quality that can be obtained using
@@ -1176,12 +1158,12 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \table
     \header
-    \o  nop \o rotate() \o scale() \o translate()
+    \li  nop \li rotate() \li scale() \li translate()
     \row
-    \o \inlineimage qpainter-clock.png
-    \o \inlineimage qpainter-rotation.png
-    \o \inlineimage qpainter-scale.png
-    \o \inlineimage qpainter-translation.png
+    \li \inlineimage qpainter-clock.png
+    \li \inlineimage qpainter-rotation.png
+    \li \inlineimage qpainter-scale.png
+    \li \inlineimage qpainter-translation.png
     \endtable
 
     The most commonly used transformations are scaling, rotation,
@@ -1200,15 +1182,15 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \table 100%
     \row
-    \o
-    \bold {Affine Transformations Example}
+    \li
+    \b {Affine Transformations Example}
 
     The \l {painting/affine}{Affine Transformations} example shows Qt's
     ability to perform affine transformations on painting
     operations. The demo also allows the user to experiment with the
     transformation operations and see the results immediately.
 
-    \o \inlineimage qpainter-affinetransformations.png
+    \li \inlineimage qpainter-affinetransformations.png
     \endtable
 
     All the tranformation operations operate on the transformation
@@ -1282,10 +1264,10 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-compositiondemo.png
+    \li \inlineimage qpainter-compositiondemo.png
 
-    \o
-    \bold {Composition Modes Example}
+    \li
+    \b {Composition Modes Example}
 
     The \l {painting/composition}{Composition Modes} example, available in
     Qt's examples directory, allows you to experiment with the various
@@ -1333,14 +1315,14 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \list
 
-    \o Raster - This backend implements all rendering in pure software
+    \li Raster - This backend implements all rendering in pure software
     and is always used to render into QImages. For optimal performance
     only use the format types QImage::Format_ARGB32_Premultiplied,
     QImage::Format_RGB32 or QImage::Format_RGB16. Any other format,
     including QImage::Format_ARGB32, has significantly worse
     performance. This engine is used by default for QWidget and QPixmap.
 
-    \o OpenGL 2.0 (ES) - This backend is the primary backend for
+    \li OpenGL 2.0 (ES) - This backend is the primary backend for
     hardware accelerated graphics. It can be run on desktop machines
     and embedded devices supporting the OpenGL 2.0 or OpenGL/ES 2.0
     specification. This includes most graphics chips produced in the
@@ -1348,7 +1330,7 @@ void QPainterPrivate::updateState(QPainterState *newState)
     onto a QOpenGLWidget or by passing \c {-graphicssystem opengl} on the
     command line when the underlying system supports it.
 
-    \o OpenVG - This backend implements the Khronos standard for 2D
+    \li OpenVG - This backend implements the Khronos standard for 2D
     and Vector Graphics. It is primarily for embedded devices with
     hardware support for OpenVG.  The engine can be enabled by
     passing \c {-graphicssystem openvg} on the command line when
@@ -1360,26 +1342,26 @@ void QPainterPrivate::updateState(QPainterState *newState)
 
     \list
 
-    \o Simple transformations, meaning translation and scaling, pluss
+    \li Simple transformations, meaning translation and scaling, pluss
     0, 90, 180, 270 degree rotations.
 
-    \o \c drawPixmap() in combination with simple transformations and
+    \li \c drawPixmap() in combination with simple transformations and
     opacity with non-smooth transformation mode
     (\c QPainter::SmoothPixmapTransform not enabled as a render hint).
 
-    \o Rectangle fills with solid color, two-color linear gradients
+    \li Rectangle fills with solid color, two-color linear gradients
     and simple transforms.
 
-    \o Rectangular clipping with simple transformations and intersect
+    \li Rectangular clipping with simple transformations and intersect
     clip.
 
-    \o Composition Modes \c QPainter::CompositionMode_Source and
+    \li Composition Modes \c QPainter::CompositionMode_Source and
     QPainter::CompositionMode_SourceOver
 
-    \o Rounded rectangle filling using solid color and two-color
+    \li Rounded rectangle filling using solid color and two-color
     linear gradients fills.
 
-    \o 3x3 patched pixmaps, via qDrawBorderPixmap.
+    \li 3x3 patched pixmaps, via qDrawBorderPixmap.
 
     \endlist
 
@@ -1417,9 +1399,13 @@ void QPainterPrivate::updateState(QPainterState *newState)
     indicating that the engine should use fragment programs and offscreen
     rendering for antialiasing.
 
-    \value NonCosmeticDefaultPen The engine should interpret pens with a width
-    of 0 (which otherwise enables QPen::isCosmetic()) as being a non-cosmetic
-    pen with a width of 1.
+    \value NonCosmeticDefaultPen This value is obsolete, the default for QPen
+    is now non-cosmetic.
+
+    \value Qt4CompatiblePainting Compatibility hint telling the engine to use the
+    same X11 based fill rules as in Qt 4, where aliased rendering is offset
+    by slightly less than half a pixel. Also will treat default constructed pens
+    as cosmetic. Potentially useful when porting a Qt 4 application to Qt 5.
 
     \sa renderHints(), setRenderHint(), {QPainter#Rendering
     Quality}{Rendering Quality}, {Concentric Circles Example}
@@ -1449,10 +1435,10 @@ QPainter::QPainter()
     automatically calls end().
 
     Here's an example using begin() and end():
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 1
+    \snippet code/src_gui_painting_qpainter.cpp 1
 
     The same example using this constructor:
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 2
+    \snippet code/src_gui_painting_qpainter.cpp 2
 
     Since the constructor cannot provide feedback when the initialization
     of the painter failed you should rather use begin() and end() to paint
@@ -1526,7 +1512,7 @@ bool QPainter::isActive() const
 
 /*!
     Initializes the painters pen, background and font to the same as
-    the given \a paint device.
+    the given \a device.
 
     \obsolete
 
@@ -1541,7 +1527,7 @@ void QPainter::initFrom(const QPaintDevice *device)
         return;
     }
 
-    device->init(this);
+    device->initPainter(this);
 
     if (d->extended) {
         d->extended->penChanged();
@@ -1670,7 +1656,7 @@ void QPainter::restore()
 
     The errors that can occur are serious problems, such as these:
 
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 3
+    \snippet code/src_gui_painting_qpainter.cpp 3
 
     Note that most of the time, you can use one of the constructors
     instead of begin(), and that end() is automatically done at
@@ -1760,25 +1746,6 @@ bool QPainter::begin(QPaintDevice *pd)
         d->engine->state = d->state;
 
     switch (pd->devType()) {
-#if 0
-        // is this needed any more??
-        case QInternal::Widget:
-        {
-            const QWidget *widget = static_cast<const QWidget *>(pd);
-            Q_ASSERT(widget);
-
-            const bool paintOutsidePaintEvent = widget->testAttribute(Qt::WA_PaintOutsidePaintEvent);
-            const bool inPaintEvent = widget->testAttribute(Qt::WA_WState_InPaintEvent);
-
-            // Adjust offset for alien widgets painting outside the paint event.
-            if (!inPaintEvent && paintOutsidePaintEvent && !widget->internalWinId()
-                && widget->testAttribute(Qt::WA_WState_Created)) {
-                const QPoint offset = widget->mapTo(widget->nativeParentWidget(), QPoint());
-                d->state->redirectionMatrix.translate(offset.x(), offset.y());
-            }
-            break;
-        }
-#endif
         case QInternal::Pixmap:
         {
             QPixmap *pm = static_cast<QPixmap *>(pd);
@@ -1963,14 +1930,14 @@ QPaintEngine *QPainter::paintEngine() const
     2 engine:
 
     \list
-    \i blending is disabled
-    \i the depth, stencil and scissor tests are disabled
-    \i the active texture unit is reset to 0
-    \i the depth mask, depth function and the clear depth are reset to their
+    \li blending is disabled
+    \li the depth, stencil and scissor tests are disabled
+    \li the active texture unit is reset to 0
+    \li the depth mask, depth function and the clear depth are reset to their
     default values
-    \i the stencil mask, stencil operation and stencil function are reset to
+    \li the stencil mask, stencil operation and stencil function are reset to
     their default values
-     \i the current color is reset to solid white
+     \li the current color is reset to solid white
     \endlist
 
     If, for example, the OpenGL polygon mode is changed by the user inside a
@@ -1978,7 +1945,7 @@ QPaintEngine *QPainter::paintEngine() const
     default state by endNativePainting(). Here is an example that shows
     intermixing of painter commands and raw OpenGL commands:
 
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 21
+    \snippet code/src_gui_painting_qpainter.cpp 21
 
     \sa endNativePainting()
 */
@@ -2339,6 +2306,23 @@ void QPainter::setBrushOrigin(const QPointF &p)
     where the source is AND'ed with the inverted destination pixels
     (src AND (NOT dst)).
 
+    \value RasterOp_NotSourceOrDestination Does a bitwise operation
+    where the source is inverted and then OR'ed with the destination
+    ((NOT src) OR dst).
+
+    \value RasterOp_ClearDestination The pixels in the destination are
+    cleared (set to 0) independent of the source.
+
+    \value RasterOp_SetDestination The pixels in the destination are
+    set (set to 1) independent of the source.
+
+    \value RasterOp_NotDestination Does a bitwise operation
+    where the destination pixels are inverted (NOT dst).
+
+    \value RasterOp_SourceOrNotDestination Does a bitwise operation
+    where the source is OR'ed with the inverted destination pixels
+    (src OR (NOT dst)).
+
     \sa compositionMode(), setCompositionMode(), {QPainter#Composition
     Modes}{Composition Modes}, {Image Composition Example}
 */
@@ -2885,15 +2869,15 @@ void QPainter::setClipRegion(const QRegion &r, Qt::ClipOperation op)
     The following functions can transform the coordinate system without using
     a QMatrix:
     \list
-    \i translate()
-    \i scale()
-    \i shear()
-    \i rotate()
+    \li translate()
+    \li scale()
+    \li shear()
+    \li rotate()
     \endlist
 
     They operate on the painter's worldMatrix() and are implemented like this:
 
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 4
+    \snippet code/src_gui_painting_qpainter.cpp 4
 
     Note that when using setWorldMatrix() function you should always have
     \a combine be true when you are drawing into a QPicture. Otherwise
@@ -3107,8 +3091,7 @@ bool QPainter::matrixEnabled() const
 /*!
     Scales the coordinate system by (\a{sx}, \a{sy}).
 
-    \sa setWorldTransform() {QPainter#Coordinate Transformations}{Coordinate
-    Transformations}
+    \sa setWorldTransform(), {QPainter#Coordinate Transformations}{Coordinate Transformations}
 */
 
 void QPainter::scale(qreal sx, qreal sy)
@@ -3131,8 +3114,7 @@ void QPainter::scale(qreal sx, qreal sy)
 /*!
     Shears the coordinate system by (\a{sh}, \a{sv}).
 
-    \sa setWorldTransform(), {QPainter#Coordinate Transformations}{Coordinate
-    Transformations}
+    \sa setWorldTransform(), {QPainter#Coordinate Transformations}{Coordinate Transformations}
 */
 
 void QPainter::shear(qreal sh, qreal sv)
@@ -3155,10 +3137,9 @@ void QPainter::shear(qreal sh, qreal sv)
 /*!
     \fn void QPainter::rotate(qreal angle)
 
-    Rotates the coordinate system the given \a angle clockwise.
+    Rotates the coordinate system clockwise. The given \a angle parameter uses degree unit.
 
-    \sa setWorldTransform(), {QPainter#Coordinate Transformations}{Coordinate
-    Transformations}
+    \sa setWorldTransform(), {QPainter#Coordinate Transformations}{Coordinate Transformations}
 */
 
 void QPainter::rotate(qreal a)
@@ -3182,8 +3163,7 @@ void QPainter::rotate(qreal a)
     Translates the coordinate system by the given \a offset; i.e. the
     given \a offset is added to points.
 
-    \sa setWorldTransform(), {QPainter#Coordinate Transformations}{Coordinate
-    Transformations}
+    \sa setWorldTransform(), {QPainter#Coordinate Transformations}{Coordinate Transformations}
 */
 void QPainter::translate(const QPointF &offset)
 {
@@ -3360,9 +3340,9 @@ void QPainter::fillPath(const QPainterPath &path, const QBrush &brush)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-path.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 5
+    \li \inlineimage qpainter-path.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 5
     \endtable
 
     \sa {painting/painterpaths}{the Painter Paths
@@ -3405,9 +3385,9 @@ void QPainter::drawPath(const QPainterPath &path)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-line.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 6
+    \li \inlineimage qpainter-line.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 6
     \endtable
 
     \sa drawLines(), drawPolyline(), {Coordinate System}
@@ -3452,9 +3432,9 @@ void QPainter::drawPath(const QPainterPath &path)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-rectangle.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 7
+    \li \inlineimage qpainter-rectangle.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 7
     \endtable
 
     \sa drawRects(), drawPolygon(), {Coordinate System}
@@ -3850,13 +3830,10 @@ void QPainter::setPen(const QColor &color)
         return;
     }
 
-    if (d->state->pen.style() == Qt::SolidLine
-        && d->state->pen.widthF() == 0
-        && d->state->pen.isSolid()
-        && d->state->pen.color() == color)
-        return;
+    QPen pen(color.isValid() ? color : QColor(Qt::black));
 
-    QPen pen(color.isValid() ? color : QColor(Qt::black), 0, Qt::SolidLine);
+    if (d->state->pen == pen)
+        return;
 
     d->state->pen = pen;
     if (d->extended)
@@ -3905,7 +3882,7 @@ void QPainter::setPen(const QPen &pen)
 /*!
     \overload
 
-    Sets the painter's pen to have the given \a style, width 0 and
+    Sets the painter's pen to have the given \a style, width 1 and
     black color.
 */
 
@@ -3917,15 +3894,12 @@ void QPainter::setPen(Qt::PenStyle style)
         return;
     }
 
-    if (d->state->pen.style() == style
-        && (style == Qt::NoPen || (d->state->pen.widthF() == 0
-                                   && d->state->pen.isSolid()
-                                   && d->state->pen.color() == QColor(Qt::black))))
+    QPen pen = QPen(style);
+
+    if (d->state->pen == pen)
         return;
 
-    // QPen(Qt::NoPen) is to avoid creating QPenData, including its brush (from the color)
-    // Note that this works well as long as QPen(Qt::NoPen) returns a black, zero-width pen
-    d->state->pen = (style == Qt::NoPen) ? QPen(Qt::NoPen) : QPen(Qt::black, 0, style);
+    d->state->pen = pen;
 
     if (d->extended)
         d->extended->penChanged();
@@ -4121,9 +4095,9 @@ const QFont &QPainter::font() const
 
     \table 100%
     \row
-    \o \inlineimage qpainter-roundrect.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 8
+    \li \inlineimage qpainter-roundrect.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 8
     \endtable
 
     \sa drawRect(), QPen
@@ -4221,9 +4195,9 @@ void QPainter::drawRoundRect(const QRectF &r, int xRnd, int yRnd)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-ellipse.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 9
+    \li \inlineimage qpainter-ellipse.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 9
     \endtable
 
     \sa drawPie(), {Coordinate System}
@@ -4347,9 +4321,9 @@ void QPainter::drawEllipse(const QRect &r)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-arc.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 10
+    \li \inlineimage qpainter-arc.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 10
     \endtable
 
     \sa drawPie(), drawChord(), {Coordinate System}
@@ -4398,8 +4372,7 @@ void QPainter::drawArc(const QRectF &r, int a, int alen)
 /*!
     \fn void QPainter::drawPie(const QRectF &rectangle, int startAngle, int spanAngle)
 
-    Draws a pie defined by the given \a rectangle, \a startAngle and
-    and \a spanAngle.
+    Draws a pie defined by the given \a rectangle, \a startAngle and \a spanAngle.
 
     The pie is filled with the current brush().
 
@@ -4411,9 +4384,9 @@ void QPainter::drawArc(const QRectF &r, int a, int alen)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-pie.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 11
+    \li \inlineimage qpainter-pie.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 11
     \endtable
 
     \sa drawEllipse(), drawChord(), {Coordinate System}
@@ -4480,9 +4453,9 @@ void QPainter::drawPie(const QRectF &r, int a, int alen)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-chord.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 12
+    \li \inlineimage qpainter-chord.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 12
     \endtable
 
     \sa drawArc(), drawPie(), {Coordinate System}
@@ -4696,8 +4669,8 @@ void QPainter::drawLines(const QPoint *pointPairs, int lineCount)
 
     \table 100%
     \row
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 13
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 13
     \endtable
 
     \sa drawLines(), drawPolygon(), {Coordinate System}
@@ -4802,9 +4775,9 @@ void QPainter::drawPolyline(const QPoint *points, int pointCount)
 
     \table 100%
     \row
-    \o \inlineimage qpainter-polygon.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 14
+    \li \inlineimage qpainter-polygon.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 14
     \endtable
 
     The first point is implicitly connected to the last point, and the
@@ -4816,7 +4789,7 @@ void QPainter::drawPolyline(const QPoint *points, int pointCount)
     \l{Qt::FillRule} for a more detailed description of these fill
     rules.
 
-    \sa  drawConvexPolygon(), drawPolyline(), {Coordinate System}
+    \sa drawConvexPolygon(), drawPolyline(), {Coordinate System}
 */
 void QPainter::drawPolygon(const QPointF *points, int pointCount, Qt::FillRule fillRule)
 {
@@ -4915,9 +4888,9 @@ void QPainter::drawPolygon(const QPoint *points, int pointCount, Qt::FillRule fi
 
     \table 100%
     \row
-    \o \inlineimage qpainter-polygon.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 15
+    \li \inlineimage qpainter-polygon.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 15
     \endtable
 
     The first point is implicitly connected to the last point, and the
@@ -5039,8 +5012,8 @@ static inline QPointF roundInDeviceCoordinates(const QPointF &p, const QTransfor
 
     \table 100%
     \row
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 16
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 16
     \endtable
 
     If \a pixmap is a QBitmap it is drawn with the bits that are "set"
@@ -5551,14 +5524,9 @@ void QPainter::drawGlyphRun(const QPointF &position, const QGlyphRun &glyphRun)
     QVarLengthArray<QFixedPoint, 128> fixedPointPositions(count);
 
     QRawFontPrivate *fontD = QRawFontPrivate::get(font);
-    bool supportsTransformations;
-    if (d->extended != 0) {
-        supportsTransformations = d->extended->supportsTransformations(fontD->fontEngine->fontDef.pixelSize,
-                                                                       d->state->matrix);
-    } else {
-        supportsTransformations = d->engine->type() == QPaintEngine::CoreGraphics
-                                  || d->state->matrix.isAffine();
-    }
+    bool supportsTransformations = d->extended
+        ? d->extended->supportsTransformations(fontD->fontEngine, d->state->matrix)
+        : d->engine->type() == QPaintEngine::CoreGraphics || d->state->matrix.isAffine();
 
     for (int i=0; i<count; ++i) {
         QPointF processedPosition = position + glyphPositions[i];
@@ -5621,9 +5589,9 @@ void QPainterPrivate::drawGlyphs(const quint32 *glyphArray, QFixedPoint *positio
         QVarLengthArray<QFixed, 128> advances(glyphCount);
         QVarLengthArray<QGlyphJustification, 128> glyphJustifications(glyphCount);
         QVarLengthArray<HB_GlyphAttributes, 128> glyphAttributes(glyphCount);
-        qMemSet(glyphAttributes.data(), 0, glyphAttributes.size() * sizeof(HB_GlyphAttributes));
-        qMemSet(advances.data(), 0, advances.size() * sizeof(QFixed));
-        qMemSet(glyphJustifications.data(), 0, glyphJustifications.size() * sizeof(QGlyphJustification));
+        memset(glyphAttributes.data(), 0, glyphAttributes.size() * sizeof(HB_GlyphAttributes));
+        memset(advances.data(), 0, advances.size() * sizeof(QFixed));
+        memset(glyphJustifications.data(), 0, glyphJustifications.size() * sizeof(QGlyphJustification));
 
         textItem.glyphs.numGlyphs = glyphCount;
         textItem.glyphs.glyphs = reinterpret_cast<HB_Glyph *>(const_cast<quint32 *>(glyphArray));
@@ -5646,6 +5614,7 @@ void QPainterPrivate::drawGlyphs(const quint32 *glyphArray, QFixedPoint *positio
 
     drawTextItemDecoration(q, QPointF(leftMost.toReal(), baseLine.toReal()),
                            fontEngine,
+                           0, // textEngine
                            (underline
                               ? QTextCharFormat::SingleUnderline
                               : QTextCharFormat::NoUnderline),
@@ -5681,7 +5650,7 @@ void QPainterPrivate::drawGlyphs(const quint32 *glyphArray, QFixedPoint *positio
     Draws the given \a text with the currently defined text direction,
     beginning at the given \a position.
 
-    This function does not handle the newline character (\n), as it cannot
+    This function does not handle the newline character (\\n), as it cannot
     break text into multiple lines, and it cannot display the newline character.
     Use the QPainter::drawText() overload that takes a rectangle instead
     if you want to draw multiple lines of text with the newline character, or
@@ -5690,6 +5659,8 @@ void QPainterPrivate::drawGlyphs(const quint32 *glyphArray, QFixedPoint *positio
     By default, QPainter draws text anti-aliased.
 
     \note The y-position is used as the baseline of the font.
+
+    \sa setFont(), setPen()
 */
 
 void QPainter::drawText(const QPointF &p, const QString &str)
@@ -5739,7 +5710,10 @@ void QPainter::drawStaticText(const QPointF &topLeftPosition, const QStaticText
         return;
     }
 
-    bool supportsTransformations = d->extended->supportsTransformations(staticText_d->font.pixelSize(),
+    QFontEngine *fe = staticText_d->font.d->engineForScript(QUnicodeTables::Common);
+    if (fe->type() == QFontEngine::Multi)
+        fe = static_cast<QFontEngineMulti *>(fe)->engine(0);
+    bool supportsTransformations = d->extended->supportsTransformations(fe,
                                                                         d->state->matrix);
     if (supportsTransformations && !staticText_d->untransformedCoordinates) {
         staticText_d->untransformedCoordinates = true;
@@ -5942,6 +5916,7 @@ void QPainter::drawText(const QRect &r, int flags, const QString &str, QRect *br
 
     \note The y-position is used as the baseline of the font.
 
+    \sa setFont(), setPen()
 */
 
 /*!
@@ -5949,12 +5924,13 @@ void QPainter::drawText(const QRect &r, int flags, const QString &str, QRect *br
     \overload
 
     Draws the given \a text within the provided \a rectangle.
+    The \a rectangle along with alignment \a flags defines the anchors for the \a text.
 
     \table 100%
     \row
-    \o \inlineimage qpainter-text.png
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 17
+    \li \inlineimage qpainter-text.png
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 17
     \endtable
 
     The \a boundingRect (if not null) is set to the what the bounding rectangle
@@ -5962,20 +5938,20 @@ void QPainter::drawText(const QRect &r, int flags, const QString &str, QRect *br
     OR of the following flags:
 
     \list
-    \o Qt::AlignLeft
-    \o Qt::AlignRight
-    \o Qt::AlignHCenter
-    \o Qt::AlignJustify
-    \o Qt::AlignTop
-    \o Qt::AlignBottom
-    \o Qt::AlignVCenter
-    \o Qt::AlignCenter
-    \o Qt::TextDontClip
-    \o Qt::TextSingleLine
-    \o Qt::TextExpandTabs
-    \o Qt::TextShowMnemonic
-    \o Qt::TextWordWrap
-    \o Qt::TextIncludeTrailingSpaces
+    \li Qt::AlignLeft
+    \li Qt::AlignRight
+    \li Qt::AlignHCenter
+    \li Qt::AlignJustify
+    \li Qt::AlignTop
+    \li Qt::AlignBottom
+    \li Qt::AlignVCenter
+    \li Qt::AlignCenter
+    \li Qt::TextDontClip
+    \li Qt::TextSingleLine
+    \li Qt::TextExpandTabs
+    \li Qt::TextShowMnemonic
+    \li Qt::TextWordWrap
+    \li Qt::TextIncludeTrailingSpaces
     \endlist
 
     \sa Qt::AlignmentFlag, Qt::TextFlag, boundingRect(), layoutDirection()
@@ -6014,6 +5990,8 @@ void QPainter::drawText(const QRectF &r, int flags, const QString &str, QRectF *
     By default, QPainter draws text anti-aliased.
 
     \note The y-coordinate of \a rectangle is used as the top of the font.
+
+    \sa setFont(), setPen()
 */
 
 /*!
@@ -6028,6 +6006,7 @@ void QPainter::drawText(const QRectF &r, int flags, const QString &str, QRectF *
 
     \note The y-position is used as the baseline of the font.
 
+    \sa setFont(), setPen()
 */
 
 /*!
@@ -6044,25 +6023,25 @@ void QPainter::drawText(const QRectF &r, int flags, const QString &str, QRectF *
     the following flags:
 
     \list
-    \o Qt::AlignLeft
-    \o Qt::AlignRight
-    \o Qt::AlignHCenter
-    \o Qt::AlignJustify
-    \o Qt::AlignTop
-    \o Qt::AlignBottom
-    \o Qt::AlignVCenter
-    \o Qt::AlignCenter
-    \o Qt::TextSingleLine
-    \o Qt::TextExpandTabs
-    \o Qt::TextShowMnemonic
-    \o Qt::TextWordWrap
+    \li Qt::AlignLeft
+    \li Qt::AlignRight
+    \li Qt::AlignHCenter
+    \li Qt::AlignJustify
+    \li Qt::AlignTop
+    \li Qt::AlignBottom
+    \li Qt::AlignVCenter
+    \li Qt::AlignCenter
+    \li Qt::TextSingleLine
+    \li Qt::TextExpandTabs
+    \li Qt::TextShowMnemonic
+    \li Qt::TextWordWrap
     \endlist
 
     By default, QPainter draws text anti-aliased.
 
     \note The y-position is used as the top of the font.
 
-    \sa Qt::AlignmentFlag, Qt::TextFlag
+    \sa Qt::AlignmentFlag, Qt::TextFlag, setFont(), setPen()
 */
 
 /*!
@@ -6076,6 +6055,8 @@ void QPainter::drawText(const QRectF &r, int flags, const QString &str, QRectF *
     By default, QPainter draws text anti-aliased.
 
     \note The y-coordinate of \a rectangle is used as the top of the font.
+
+    \sa setFont(), setPen()
 */
 void QPainter::drawText(const QRectF &r, const QString &text, const QTextOption &o)
 {
@@ -6135,7 +6116,7 @@ static QPixmap generateWavyPixmap(qreal maxRadius, const QPen &pen)
 {
     const qreal radiusBase = qMax(qreal(1), maxRadius);
 
-    QString key = QLatin1Literal("WaveUnderline-")
+    QString key = QLatin1String("WaveUnderline-")
                   % pen.color().name()
                   % HexString<qreal>(radiusBase);
 
@@ -6182,7 +6163,7 @@ static QPixmap generateWavyPixmap(qreal maxRadius, const QPen &pen)
     return pixmap;
 }
 
-static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const QFontEngine *fe,
+static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const QFontEngine *fe, QTextEngine *textEngine,
                                    QTextCharFormat::UnderlineStyle underlineStyle,
                                    QTextItem::RenderFlags flags, qreal width,
                                    const QTextCharFormat &charFormat)
@@ -6204,11 +6185,12 @@ static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const
     const qreal underlineOffset = fe->underlinePosition().toReal();
     // deliberately ceil the offset to avoid the underline coming too close to
     // the text above it.
-    const qreal aliasedCoordinateDelta = 0.5 - 0.015625;
-    const qreal underlinePos = pos.y() + qCeil(underlineOffset) - aliasedCoordinateDelta;
+    const qreal underlinePos = pos.y() + qCeil(underlineOffset);
 
     if (underlineStyle == QTextCharFormat::SpellCheckUnderline) {
-        underlineStyle = QTextCharFormat::SpellCheckUnderline; // ### Qt5 QTextCharFormat::UnderlineStyle(QApplication::style()->styleHint(QStyle::SH_SpellCheckUnderlineStyle));
+        QPlatformTheme *theme = QGuiApplicationPrivate::platformTheme();
+        if (theme)
+            underlineStyle = QTextCharFormat::UnderlineStyle(theme->themeHint(QPlatformTheme::SpellCheckUnderlineStyle).toInt());
     }
 
     if (underlineStyle == QTextCharFormat::WaveUnderline) {
@@ -6227,15 +6209,17 @@ static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const
         painter->fillRect(pos.x(), 0, qCeil(width), qMin(wave.height(), descent), wave);
         painter->restore();
     } else if (underlineStyle != QTextCharFormat::NoUnderline) {
-        QLineF underLine(line.x1(), underlinePos, line.x2(), underlinePos);
-
         QColor uc = charFormat.underlineColor();
         if (uc.isValid())
             pen.setColor(uc);
 
         pen.setStyle((Qt::PenStyle)(underlineStyle));
         painter->setPen(pen);
-        painter->drawLine(underLine);
+        QLineF underline(line.x1(), underlinePos, line.x2(), underlinePos);
+        if (textEngine)
+            textEngine->addUnderline(painter, underline);
+        else
+            painter->drawLine(underline);
     }
 
     pen.setStyle(Qt::SolidLine);
@@ -6245,14 +6229,20 @@ static void drawTextItemDecoration(QPainter *painter, const QPointF &pos, const
         QLineF strikeOutLine = line;
         strikeOutLine.translate(0., - fe->ascent().toReal() / 3.);
         painter->setPen(pen);
-        painter->drawLine(strikeOutLine);
+        if (textEngine)
+            textEngine->addStrikeOut(painter, strikeOutLine);
+        else
+            painter->drawLine(strikeOutLine);
     }
 
     if (flags & QTextItem::Overline) {
-        QLineF overLine = line;
-        overLine.translate(0., - fe->ascent().toReal());
+        QLineF overline = line;
+        overline.translate(0., - fe->ascent().toReal());
         painter->setPen(pen);
-        painter->drawLine(overLine);
+        if (textEngine)
+            textEngine->addOverline(painter, overline);
+        else
+            painter->drawLine(overline);
     }
 
     painter->setPen(oldPen);
@@ -6277,7 +6267,7 @@ Q_GUI_EXPORT void qt_draw_decoration_for_glyphs(QPainter *painter, const glyph_t
 
         // We don't support glyphs that do not share a common baseline. If this turns out to
         // be a relevant use case, then we need to find clusters of glyphs that share a baseline
-        // and do a drawTextItemDecorations call per cluster.
+        // and do a drawTextItemDecoration call per cluster.
         if (i == 0 || baseLine < positions[i].y)
             baseLine = positions[i].y;
 
@@ -6298,12 +6288,20 @@ Q_GUI_EXPORT void qt_draw_decoration_for_glyphs(QPainter *painter, const glyph_t
 
     drawTextItemDecoration(painter, QPointF(leftMost.toReal(), baseLine.toReal()),
                            fontEngine,
+                           0, // textEngine
                            font.underline() ? QTextCharFormat::SingleUnderline
                                             : QTextCharFormat::NoUnderline, flags,
                            width.toReal(), charFormat);
 }
 
-void QPainter::drawTextItem(const QPointF &p, const QTextItem &_ti)
+void QPainter::drawTextItem(const QPointF &p, const QTextItem &ti)
+{
+    Q_D(QPainter);
+
+    d->drawTextItem(p, ti, static_cast<QTextEngine *>(0));
+}
+
+void QPainterPrivate::drawTextItem(const QPointF &p, const QTextItem &_ti, QTextEngine *textEngine)
 {
 #ifdef QT_DEBUG_DRAW
     if (qt_show_painter_debug_output)
@@ -6311,35 +6309,35 @@ void QPainter::drawTextItem(const QPointF &p, const QTextItem &_ti)
                p.x(), p.y(), qPrintable(_ti.text()));
 #endif
 
-    Q_D(QPainter);
+    Q_Q(QPainter);
 
-    if (!d->engine)
+    if (!engine)
         return;
 
 #ifndef QT_NO_DEBUG
-    qt_painter_thread_test(d->device->devType(),
+    qt_painter_thread_test(device->devType(),
                            "text and fonts",
                            QFontDatabase::supportsThreadedFontRendering());
 #endif
 
     QTextItemInt &ti = const_cast<QTextItemInt &>(static_cast<const QTextItemInt &>(_ti));
 
-    if (!d->extended && d->state->bgMode == Qt::OpaqueMode) {
+    if (!extended && state->bgMode == Qt::OpaqueMode) {
         QRectF rect(p.x(), p.y() - ti.ascent.toReal(), ti.width.toReal(), (ti.ascent + ti.descent + 1).toReal());
-        fillRect(rect, d->state->bgBrush);
+        q->fillRect(rect, state->bgBrush);
     }
 
-    if (pen().style() == Qt::NoPen)
+    if (q->pen().style() == Qt::NoPen)
         return;
 
-    const RenderHints oldRenderHints = d->state->renderHints;
-    if (!d->state->renderHints & QPainter::Antialiasing && d->state->matrix.type() >= QTransform::TxScale) {
+    const QPainter::RenderHints oldRenderHints = state->renderHints;
+    if (!state->renderHints & QPainter::Antialiasing && state->matrix.type() >= QTransform::TxScale) {
         // draw antialias decoration (underline/overline/strikeout) with
         // transformed text
 
         bool aa = true;
-        const QTransform &m = d->state->matrix;
-        if (d->state->matrix.type() < QTransform::TxShear) {
+        const QTransform &m = state->matrix;
+        if (state->matrix.type() < QTransform::TxShear) {
             bool isPlain90DegreeRotation =
                 (qFuzzyIsNull(m.m11())
                  && qFuzzyIsNull(m.m12() - qreal(1))
@@ -6362,11 +6360,11 @@ void QPainter::drawTextItem(const QPointF &p, const QTextItem &_ti)
             aa = !isPlain90DegreeRotation;
         }
         if (aa)
-            setRenderHint(QPainter::Antialiasing, true);
+            q->setRenderHint(QPainter::Antialiasing, true);
     }
 
-    if (!d->extended)
-        d->updateState(d->state);
+    if (!extended)
+        updateState(state);
 
     if (!ti.glyphs.numGlyphs) {
         // nothing to do
@@ -6402,7 +6400,7 @@ void QPainter::drawTextItem(const QPointF &p, const QTextItem &_ti)
             if (rtl)
                 x -= ti2.width.toReal();
 
-            d->engine->drawTextItem(QPointF(x, y), ti2);
+            engine->drawTextItem(QPointF(x, y), ti2);
 
             if (!rtl)
                 x += ti2.width.toReal();
@@ -6429,10 +6427,10 @@ void QPainter::drawTextItem(const QPointF &p, const QTextItem &_ti)
         if (rtl)
             x -= ti2.width.toReal();
 
-        if (d->extended)
-            d->extended->drawTextItem(QPointF(x, y), ti2);
+        if (extended)
+            extended->drawTextItem(QPointF(x, y), ti2);
         else
-            d->engine->drawTextItem(QPointF(x,y), ti2);
+            engine->drawTextItem(QPointF(x,y), ti2);
 
         // reset the high byte for all glyphs
         const int hi = which << 24;
@@ -6440,20 +6438,20 @@ void QPainter::drawTextItem(const QPointF &p, const QTextItem &_ti)
             glyphs.glyphs[i] = hi | glyphs.glyphs[i];
 
     } else {
-        if (d->extended)
-            d->extended->drawTextItem(p, ti);
+        if (extended)
+            extended->drawTextItem(p, ti);
         else
-            d->engine->drawTextItem(p, ti);
+            engine->drawTextItem(p, ti);
     }
-    drawTextItemDecoration(this, p, ti.fontEngine, ti.underlineStyle, ti.flags, ti.width.toReal(),
-                           ti.charFormat);
+    drawTextItemDecoration(q, p, ti.fontEngine, textEngine, ti.underlineStyle,
+                           ti.flags, ti.width.toReal(), ti.charFormat);
 
-    if (d->state->renderHints != oldRenderHints) {
-        d->state->renderHints = oldRenderHints;
-        if (d->extended)
-            d->extended->renderHintsChanged();
+    if (state->renderHints != oldRenderHints) {
+        state->renderHints = oldRenderHints;
+        if (extended)
+            extended->renderHintsChanged();
         else
-            d->state->dirtyFlags |= QPaintEngine::DirtyHints;
+            state->dirtyFlags |= QPaintEngine::DirtyHints;
     }
 }
 
@@ -6472,18 +6470,18 @@ void QPainter::drawTextItem(const QPointF &p, const QTextItem &_ti)
 
     The \a flags argument is a bitwise OR of the following flags:
     \list
-         \o Qt::AlignLeft
-         \o Qt::AlignRight
-         \o Qt::AlignHCenter
-         \o Qt::AlignTop
-         \o Qt::AlignBottom
-         \o Qt::AlignVCenter
-         \o Qt::AlignCenter
-         \o Qt::TextSingleLine
-         \o Qt::TextExpandTabs
-         \o Qt::TextShowMnemonic
-         \o Qt::TextWordWrap
-         \o Qt::TextIncludeTrailingSpaces
+         \li Qt::AlignLeft
+         \li Qt::AlignRight
+         \li Qt::AlignHCenter
+         \li Qt::AlignTop
+         \li Qt::AlignBottom
+         \li Qt::AlignVCenter
+         \li Qt::AlignCenter
+         \li Qt::TextSingleLine
+         \li Qt::TextExpandTabs
+         \li Qt::TextShowMnemonic
+         \li Qt::TextWordWrap
+         \li Qt::TextIncludeTrailingSpaces
     \endlist
     If several of the horizontal or several of the vertical alignment
     flags are set, the resulting alignment is undefined.
@@ -6691,8 +6689,8 @@ void QPainter::drawTiledPixmap(const QRectF &r, const QPixmap &pixmap, const QPo
 
     \table 100%
     \row
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 18
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 18
     \endtable
 
     \sa QPicture::play()
@@ -6735,7 +6733,7 @@ void QPainter::drawPicture(const QPointF &p, const QPicture &picture)
 
     Erases the area inside the given \a rectangle. Equivalent to
     calling
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 19
+    \snippet code/src_gui_painting_qpainter.cpp 19
 
     \sa fillRect()
 */
@@ -7150,7 +7148,7 @@ QRect QPainter::window() const
     The default viewport rectangle is the same as the device's
     rectangle.
 
-    \sa viewport(), viewTransformEnabled() {Coordinate
+    \sa viewport(), viewTransformEnabled(), {Coordinate
     System#Window-Viewport Conversion}{Window-Viewport Conversion}
 */
 
@@ -7258,6 +7256,7 @@ void QPainter::setRedirected(const QPaintDevice *device,
                              const QPoint &offset)
 {
     Q_ASSERT(device != 0);
+    Q_UNUSED(device)
     Q_UNUSED(replacement)
     Q_UNUSED(offset)
     qWarning("QPainter::setRedirected(): ignoring call to deprecated function, use QWidget::render() instead");
@@ -7550,11 +7549,12 @@ start_lengthVariant:
 
         for (int i = 0; i < textLayout.lineCount(); i++) {
             QTextLine line = textLayout.lineAt(i);
+            QTextEngine *eng = textLayout.engine();
+            eng->enableDelayDecorations();
 
             qreal advance = line.horizontalAdvance();
             xoff = 0;
             if (tf & Qt::AlignRight) {
-                QTextEngine *eng = textLayout.engine();
                 xoff = r.width() - advance -
                     eng->leadingSpaceWidth(eng->lines[line.lineNumber()]).toReal();
             }
@@ -7562,6 +7562,7 @@ start_lengthVariant:
                 xoff = (r.width() - advance) / 2;
 
             line.draw(painter, QPointF(r.x() + xoff, r.y() + yoff));
+            eng->drawDecorations(painter);
         }
 
         if (restore) {
@@ -7675,8 +7676,8 @@ void QPainterState::init(QPainter *p) {
 
     \table 100%
     \row
-    \o
-    \snippet doc/src/snippets/code/src_gui_painting_qpainter.cpp 20
+    \li
+    \snippet code/src_gui_painting_qpainter.cpp 20
     \endtable
 
     \sa drawPixmap()
@@ -7769,6 +7770,7 @@ void QPainterState::init(QPainter *p) {
 /*!
     \class QPaintEngineState
     \since 4.1
+    \inmodule QtGui
 
     \brief The QPaintEngineState class provides information about the
     active paint engine's current state.
@@ -7791,21 +7793,21 @@ void QPainterState::init(QPainter *p) {
     \target GetFunction
 
     \table
-    \header \o Property Flag \o Current Property Value
-    \row \o QPaintEngine::DirtyBackground \o backgroundBrush()
-    \row \o QPaintEngine::DirtyBackgroundMode \o backgroundMode()
-    \row \o QPaintEngine::DirtyBrush \o brush()
-    \row \o QPaintEngine::DirtyBrushOrigin \o brushOrigin()
-    \row \o QPaintEngine::DirtyClipRegion \e or QPaintEngine::DirtyClipPath
-         \o clipOperation()
-    \row \o QPaintEngine::DirtyClipPath \o clipPath()
-    \row \o QPaintEngine::DirtyClipRegion \o clipRegion()
-    \row \o QPaintEngine::DirtyCompositionMode \o compositionMode()
-    \row \o QPaintEngine::DirtyFont \o font()
-    \row \o QPaintEngine::DirtyTransform \o transform()
-    \row \o QPaintEngine::DirtyClipEnabled \o isClipEnabled()
-    \row \o QPaintEngine::DirtyPen \o pen()
-    \row \o QPaintEngine::DirtyHints \o renderHints()
+    \header \li Property Flag \li Current Property Value
+    \row \li QPaintEngine::DirtyBackground \li backgroundBrush()
+    \row \li QPaintEngine::DirtyBackgroundMode \li backgroundMode()
+    \row \li QPaintEngine::DirtyBrush \li brush()
+    \row \li QPaintEngine::DirtyBrushOrigin \li brushOrigin()
+    \row \li QPaintEngine::DirtyClipRegion \e or QPaintEngine::DirtyClipPath
+         \li clipOperation()
+    \row \li QPaintEngine::DirtyClipPath \li clipPath()
+    \row \li QPaintEngine::DirtyClipRegion \li clipRegion()
+    \row \li QPaintEngine::DirtyCompositionMode \li compositionMode()
+    \row \li QPaintEngine::DirtyFont \li font()
+    \row \li QPaintEngine::DirtyTransform \li transform()
+    \row \li QPaintEngine::DirtyClipEnabled \li isClipEnabled()
+    \row \li QPaintEngine::DirtyPen \li pen()
+    \row \li QPaintEngine::DirtyHints \li renderHints()
     \endtable
 
     The QPaintEngineState class also provide the painter() function
@@ -8109,7 +8111,7 @@ qreal QPaintEngineState::opacity() const
     If \a combine is true, the specified \a transform is combined with
     the current matrix; otherwise it replaces the current matrix.
 
-    \sa transform() setWorldTransform()
+    \sa transform(), setWorldTransform()
 */
 
 void QPainter::setTransform(const QTransform &transform, bool combine )
@@ -8311,6 +8313,7 @@ void QPainter::drawPixmapFragments(const PixmapFragment *fragments, int fragment
 /*!
     \since 4.7
     \class QPainter::PixmapFragment
+    \inmodule QtGui
 
     \brief This class is used in conjunction with the
     QPainter::drawPixmapFragments() function to specify how a pixmap, or