QT6 源,十章绘图(15)路径绘制 QPainterPath 篇四:QPainterPath和 QPainterPathStroker 的源代码带注释

(25)

#ifndef QPAINTERPATH_H
#define QPAINTERPATH_H

#include <QtGui/qtguiglobal.h>
#include <QtGui/qtransform.h>
#include <QtCore/qglobal.h>
#include <QtCore/qline.h>
#include <QtCore/qlist.h>
#include <QtCore/qrect.h>
#include <QtCore/qshareddata.h>

QT_BEGIN_NAMESPACE


class QFont;
class QPainterPathPrivate;
struct QPainterPathPrivateDeleter;
class QPainterPathStrokerPrivate;
class QPen;
class QPolygonF;
class QRegion;
class QTransform;
class QVectorPath;

/*
The QPainterPath class provides a container for painting operations,
    enabling graphical shapes to be constructed and reused.

Detailed Description :
绘画路径是由若干图形构建单元(如矩形、椭圆、线条和曲线curve)组成的对象。
这些构建单元可以组合成闭合的子路径,例如一个矩形或一个椭圆。闭合路径具有重合coinside的起点和终点或者。
它们也可以独立存在,作为未闭合的子路径,例如线条和曲线。

-个QPainterPath对象可用于填充、描边和剪裁。
为了为给定的绘图路径生成可填充的描边,应使用QPainterPathStroker类。
与普通的绘图操作相比,绘图路径的主要优势在于复杂的形状只需创建一次;
之后,只需通过调用QPainter:drawPath()函数即可多次绘制这些形状。

QPainterPath提供了一系列函数,可用于获取有关路径及其元素的信息。
此外,通过使用 toReversed()函数,还可以反向排列元素的顺序。
此外,还有多个函数可将此 PainterPath对象转换为多边形表示形式。

Composing a QPainterPath :  弧形arc、 cubic立方体
-个QPainterPath对象可以构建为空路径,带有给定的起点,或者作为另一个QPainterPath对象的副本。
创建后,可以使用“lineTo()、arcTo()、cubicTo()'和`quadTo()'函数向路径中添加线条和曲线。
这些线条和曲线将从`currentPosition()延伸到作为参数传递的位置.

QPainterPath对象的currentPosition()始终是指添加的最后一个子路径的结束位置(或初始起点)。
使用moveTo()函数可以移动currentPosition()而不会添加一个组件。
moveTo()函数默认会开始一个新的子路径,并关闭之前的子路径。

开始新子路径的另一个方法是调用closeSubpath()函数,
该函数通过从currentPosition()添加一条线回到路径的起点来关闭当前路径。
请注意,新路径的初始currentPosition()将是(0,0)。

QPainterPath 类还提供了几个便捷函数,用于向 Painter Path 中添加闭合子路径:
addEllipse()、addPath()、addRect()、addRegion()和addText()。
addPolygon()函数则用于添加未闭合的子路径。
实际上,这些函数都是moveTo()、lineTo()和cubicTo()操作的组合。

此外,可以使用`connectPath()函数在当前路径上添加一条路径。
但请注意,该函数会通过添加一条线来将当前路径的最后一个元素与给定路径的第一个元素连接起来。

以下是一个代码片段,展示了如何使用QPainterPath对象:
    QPainterPath path;
    path.addRect(20, 20, 60, 60);

    path. moveTo( 0,  0);
    path.cubicTo(99,  0,  50, 50,  99, 99);
    path.cubicTo( 0, 99,  50, 50,   0,  0);

    QPainter painter(this);
    painter.fillRect(0, 0, 100, 100, Qt::white);
    painter.setPen(QPen(QColor(79, 106, 25), 1, Qt::SolidLine,
                        Qt::FlatCap, Qt::MiterJoin));
    painter.setBrush(QColor(122, 163, 39));

    painter.drawPath(path);

在构建时,绘画路径最初是空的。
我们首先添加一个矩形,这是一个闭合子路径。
然后我们添加两条贝塞尔曲线,尽管它们单独来看并不闭合,但合在一起形成了一个闭合子路径。
最后,我们绘制整个路径。该路径使用默认填充规则 Qt::OddEvenFill 进行填充。
Qt 提供了两种填充路径的方法:

请参阅 Qt::FillRule 文档以了解规则的定义。
可以使用 fillRule()函数获取当前设置的绘画路径填充规则,并使用 setFillRule()函数进行修改。

QPainterPath Information :
QPainterPath类提供了一系列函数,用于返回有关路径及其元素的信息。
currentPosition()、函数返回所添加的最后一个子路径的端点(或初始起点).
elementAt()、函数可用于检索各个子路径元素,
使用`elementCount()函数可获取元素数量,
而`isEmpty()函数则判断该`QPainterPath'对象是否包含任何元素。

controlPointRect()、函数返回包含此路径中所有点和控制点的矩形。
    与精确的`boundingRect、函数相比,该函数的计算速度显著更快,
`boundingRect()、函数以浮点数精度返回此绘图路径的边界矩形。

最后,QPainterPath提供了contains()函数,可用于确定给定的点或矩形是否位于路径内,
以及intersects()函数,用于确定给定矩形内的任何点是否也位于该路径内。

QPainterPath Conversion :
出于兼容性的考虑,可能需要简化画家路径的表示方式.
QPainterPath提供了toFillPolygon()、toFillPolygons()和toSubpathPolygons()函数,
这些函数可将画家路径转换为多边形。
toFillPolygon()函数返回一个单一的多边形,而后两个函数则返回一个多边形的列表。

toFillPolygons()`和`toSubpathPolygons()、函数被提供,
因为绘制多个小多边形通常比绘制一个大多边形更快,尽管绘制的点总数是相同的。
两者之间的区别在于它们返回的多边形数量:
toSubpathPolygons()、会为每个子路径(无论是否存在相交子路径,即重叠的约束矩形)创建一个多边形
,而`toFillPolygons()、只为重叠的子路径创建一个多边形。

toFillPolygon()、和`toFillPolygons()、函数首先将所有子路径转换为多边形,
然后使用回绕技术确保重叠子路径能够按照正确的填充规则被填充。
请注意,回绕会在多边形中插入额外的线条,因此填充多边形的轮廓与路径的轮廓可能不一致。

Examples :
Qt 提供了 Painter Paths 示例和 Vector Deformation 示例,这些示例位于 Qt 的示例目录中。
《画家路径示例》展示了如何使用画家路径来构建用于渲染的复杂形状,并让用户能够尝试填充和描边操作。
(《矢量变形示例》演示了如何使用QPainterPath来绘制文本。


*/

Q_GUI_EXPORT QDataStream & operator<<(QDataStream &, const QPainterPath & );
Q_GUI_EXPORT QDataStream & operator>>(QDataStream &,       QPainterPath & );
Q_GUI_EXPORT QDebug        operator<<(QDebug       , const QPainterPath & );

class Q_GUI_EXPORT QPainterPath
{
private:

    inline
    void ensureData       () { if (!d_ptr) ensureData_helper(); }
    void ensureData_helper();
    void detach();
    void setDirty(bool);
    void computeBoundingRect    () const;
    void computeControlPointRect() const;

    QPainterPathPrivate * d_func() const { return d_ptr.data(); }

    friend class QPainterPathStroker;
    friend class QPainterPathStrokerPrivate;
    friend class QTransform;
    friend class QVectorPath;
    friend Q_GUI_EXPORT const QVectorPath & qtVectorPathForPath(const QPainterPath &);

    friend Q_GUI_EXPORT QDataStream & operator<<(QDataStream &, const QPainterPath &);
    friend Q_GUI_EXPORT QDataStream & operator>>(QDataStream &,       QPainterPath &);

    QExplicitlySharedDataPointer<QPainterPathPrivate> d_ptr;

public:

    QPainterPath() noexcept; //构造一个空的QPainterPath对象。
    explicit                 //创建一个PainterPath对象,并将给定的startPoint作为其当前位置。
    QPainterPath(const QPointF      & startPoint);
    QPainterPath(const QPainterPath & other     ); //copy构造函数
    QPainterPath & operator=(const QPainterPath & other); //copy赋值运算符函数
    QT_MOVE_ASSIGNMENT_OPERATOR_IMPL_VIA_PURE_SWAP(QPainterPath) //移动构造函数

    ~QPainterPath();

    inline void swap(QPainterPath & other) noexcept { d_ptr.swap(other.d_ptr); }

    void    clear   (); //清除存储的路径元素。这使得路径可以重用之前的内存分配。
    void    reserve (int size);
    //在PainterPath的内部内存中预留给定数量的元素。尝试为至少 size个元素分配内存。
    int     capacity() const; //返回由QPainterPath分配的元素数量。

    QPointF currentPosition() const; //返回路径的当前位置。

    void    closeSubpath();
    //通过绘制一条线到子路径的起点来关闭当前子路径,并自动开始一条新路径。
    //新路径的当前点为(0,0)。  如果子路径不包含任何元素,此函数将不做任何事情。

    /*
    //指定应使用哪种方法来填充路径和多边形。 QPainter绘制多边形时用到这个枚举类。
    enum Qt::FillRule {
        OddEvenFill,  //指定使用奇偶填充规则填充区域。
        //用这个规则,我们通过使用下面的方法来确定一个点是否在形状内。
        //从点到形状外的位置绘制一条水平线,并计算交叉点的数量。
        //如果相交的数目是奇数,则点在形状内。此模式为默认模式。

        WindingFill   //指定该区域使用非零缠绕规则进行填充。
        //根据此规则,我们采用以下方法来确定一个点是否位于该形状内。
        //从该点向外绘制一条水平线,然后确定每条交点处的线方向是向上还是向下。
        //缠绕数是通过汇总每个交点的方向来确定的。如果数值为非零,则该点位于该形状内。
        //在大多数情况下,这种填充模式也可被视为闭合形状的交点填充。
    };
    */

    //经测试发现,默认的填充模式是变化的。根据需要自行测试需要的填充模式。
    Qt::FillRule     fillRule() const; //返回画家路径当前设置的填充规则。
    void          setFillRule(Qt::FillRule fillRule);
    //将绘图路径的填充规则设置为给定的fiRule。Qt提供了两种填充路径的方法。

    bool   isEmpty() const;
    //如果此路径中没有元素,或者唯一元素是一个MoveToElement,则返回true;否则返回false。

    //将当前点移动到给定点 point,隐式地开始一个新的子路径并关闭之前的子路径。
    void    moveTo(const QPointF & point);
    inline
    void    moveTo(qreal x, qreal  y    )
    {       moveTo(QPointF(x, y)); }

    //创建一个移动到位于给定矩形 rect在角度 angle处所占弧线上的点。
    //角度以度为单位指定。可以使用负角度来指定顺时针弧线。
    void arcMoveTo(const QRectF & rect, qreal angle);
    inline  //本函数只是为了移动绘图的起点,并不绘图。
    void arcMoveTo(qreal x, qreal y, qreal w, qreal h, qreal angle)
    {    arcMoveTo(QRectF(x, y, w, h), angle);    }


    //从当前位置向给定端点 endPoint添加一条直线。绘制线条后,当前位置将更新为位于线条的终点。
    void lineTo(const QPointF  & endPoint);
    inline
    void lineTo(qreal x, qreal   y       )
    {    lineTo(QPointF(x, y)); }


    //将给定的矩形 rect作为闭合子路径 closed subpath添加到此路径。
    //该矩形被添加为一组顺时针排列的线条。
    //在矩形被添加后,绘图路径的当前位置位于矩形的左上角。
    void addRect(const QRectF & rect);
    inline
    void addRect(qreal x, qreal y, qreal w, qreal h)
    {    addRect(QRectF(x, y, w, h));   }

    //将给定的矩形rect添加到路径上,使其具有圆角。
    //xRadius 和 yRadius 参数指定定义圆角矩形角的椭圆的半径。
    //当 mode为 Qt::RelativeSize 时,xRadius 和 vRadius分别以矩形宽度和高度的一半的百分比指定,
    //  并且应在 0.0 到 100.0 的范围内。
    void addRoundedRect(const QRectF & rect, qreal xRadius, qreal yRadius,
                        Qt::SizeMode mode = Qt::AbsoluteSize);
    inline
    void addRoundedRect(qreal x, qreal y, qreal w, qreal h,
                        qreal xRadius, qreal yRadius,
                        Qt::SizeMode mode = Qt::AbsoluteSize)
    {    addRoundedRect(QRectF(x, y, w, h), xRadius, yRadius, mode);    }
    /*
    //这个枚举被QPainter::drawRoundedRect()和 QPainterPath::addRoundedRect()函数使用,
    enum Qt::SizeMode {  //以根据指定的边界框的尺寸来指定矩形角落的半径。
        AbsoluteSize,    //使用绝对测量值指定大小。
        RelativeSize     //指定相对于边界矩形的大小,通常使用百分比测量。
    };
    */

    //将给定的多边形添加到路径作为(未闭合)子路径 an (unclosed) subpath。
    //请注意,在添加完多边形后,当前位置将是多边形中的最后一个点。
    //要画一条线回到第一个点,请使用closeSubpath()函数。
    void addPolygon(const QPolygonF & polygon);
    //class QPolygon  : public QList<QPoint > //这些是关于多边形的使用
    //class QPolygonF : public QList<QPointF>
    //QPolygonF(QList<QPointF> & v) : QList<QPointF>(v) { }

    //在指定的边界矩形 boundingRectangle内创建一个椭圆,并将其添加到绘图路径作为闭合子路径。
    //椭圆由顺时针曲线组成,从零度(三点钟位置)开始和结束。终止点在 0 度位置。
    void addEllipse(const QRectF & boundingRectangle);
    inline  // 4 参数模式的参数,被视为描述成矩形边框。
    void addEllipse(qreal x, qreal y, qreal w, qreal h)
    {    addEllipse(QRectF(x, y, w, h));    }
    inline //创建一个位于中心 center的椭圆,其半径为rx和ry,并将其添加到绘图路径中作为闭合子路径。
    void addEllipse(const QPointF & center, qreal rx, qreal ry)
    {    addEllipse(QRectF(center.x() - rx, center.y() - ry, 2 * rx, 2 * ry)); }

    //创建一个弧线,该弧线占据给定的矩形区域 rect,从指定的startAngle开始,
    //  并向逆时针方向扩展 arcLength度。角度以度为单位指定。可以使用负角度来指定顺时针弧线。
    //请注意,如果弧线的起点与当前位置尚未连接,则此函数会将其连接起来。
    //在添加弧线后,当前位置将成为弧线中的最后一个点。
    //要画一条线回到第一个点,请使用“closeSubpath()函数。
    void arcTo(const QRectF & rect, qreal startAngle, qreal arcLength);
    inline
    void arcTo(qreal x, qreal y, qreal w, qreal h, qreal startAngle, qreal arcLength)
    {    arcTo(QRectF(x, y, w, h), startAngle, arcLength);    }

    //在当前位置和给定的终点之间添加一个二次贝塞尔曲线,并使用由 ctrlPt指定的控制点。
    //添加曲线后,当前点更新为在曲线的终点。
    //quadratic 二次的 [kwɒˈdrætɪk] 。  quartic  ['kwɔːtɪk] 四次的方程。
    void quadTo(const QPointF & ctrlPt, const QPointF & endPt);
    inline      //控制点 ctrlPoint 与起点终点均相切
    void quadTo(qreal ctrlPtx, qreal ctrlPty, qreal endPtx, qreal endPty)
    {    quadTo(QPointF(ctrlPtx, ctrlPty), QPointF(endPtx, endPty));    }

    //在当前位置和给定的终点 endPt之间添加一个三次贝塞尔曲线,使用由 ctrlPt1和 ctrlPt2指定的控制点。
    //添加曲线后,当前位置更新为在曲线的终点。
    void cubicTo(const QPointF & ctrlPt1, const QPointF & ctrlPt2, const QPointF & endPt);
    inline
    void cubicTo(qreal ctrlPt1x, qreal ctrlPt1y, qreal ctrlPt2x, qreal ctrlPt2y,
                qreal endPtx, qreal endPty)
    {    cubicTo(QPointF(ctrlPt1x, ctrlPt1y), QPointF(ctrlPt2x, ctrlPt2y),
                QPointF(endPtx, endPty));
    }

    //将给定的文本 text添加到此路径中,作为由所提供的字体 f创建的一系列闭合子路径。
    //这些子路径被定位,使得文本基线的左端位于指定的点 point处。
    void addText(const QPointF & point, const QFont & f, const QString & text);
    inline
    void addText(qreal x,      qreal y, const QFont & f, const QString & text)
    {    addText(QPointF(x, y), f, text);    }

    //将给定路径 path添加到此路径作为闭合子路径。路径添加。
    void addPath  (const QPainterPath   & path  );

    //将给定区域 QRegion添加到路径中,通过将区域中的每个矩形作为单独的闭合子路径来添加实现。
    void addRegion(const QRegion        & region);

    //将给定路径 path连接到此路径,通过从该路径的最后一个元素添加一条线到给定路径的第一个元素。
    void connectPath(const QPainterPath & path  ); //路径添加并连接。


    void         translate (qreal dx, qreal dy);
    inline                //将路径中的所有元素沿(x,y)方向平移。
    void         translate (const QPointF & offset)
    {            translate (offset.x(), offset.y());  }
    [[nodiscard]]
    QPainterPath translated(qreal dx,     qreal dy) const;
    [[nodiscard]] inline  //返回经过(dx,dy)平移的路径副本。
    QPainterPath translated(const QPointF & offset) const
    {   return   translated(offset.x(), offset.y());  }


    [[nodiscard]] QPainterPath toReversed() const;
    //创建并返回路径的反转副本。
    //元素的顺序被反转了:如果使用moveTo()、lineTo()和cubicTo()函数,
    //  以指定的顺序构建一个QPainterPath对象,
    //那么其反转副本则是通过调用cubicTo()、lineTo()以及moveTo()函数来构建的。

    //返回此绘图路径的边界矩形,作为具有浮点精度的矩形。
    QRectF     boundingRect() const; //路径边界
    QRectF controlPointRect() const; //包含了控制点的大边界
    //返回包含此路径中所有点和控制点的矩形。
    //此函数的计算速度显著快于精确的boundingRect()函数,
    //  且返回的矩形总是boundingRect()函数返回的矩形的超集。

    //使用 QTransform矩阵 matrix将路径转换为多边形,并返回多边形。
    //该多边形是通过首先将所有子路径转换为多边形,
    //  然后使用回绕技术来确保重叠子路径能够按照正确的填充规则进行填充而创建的。
    //请注意,反向转换会在多边形中插入额外的线段,因此填充多边形的轮与路径的轮不匹配。
    QPolygonF           toFillPolygon (const QTransform & matrix = QTransform()) const;
    QList<QPolygonF>    toFillPolygons(const QTransform & matrix = QTransform()) const;
    //将路径转换为使用 QTransform矩阵 matrix的多边形列表,并返回该列表。
    //该函数与`toFillPolygon()'函数的不同之处在于,它创建多个多边形。
    //之所以提供这个函数是因为绘制多个小多边形通常比绘制一个大多边形更快,尽管绘制的点总数是相同的。
    //toFillPolygons()`函数与`toSubpathPolygons()、函数的不同之处在于,
    //它仅会为那些有重叠的边界矩形的子路径创建多边形。
    //与`toFilPolygon()、函数一样,该函数采用回绕技术,以确保重叠子路径能够按照正确的填充规则被填充。
    //请注意,回绕会在多边形中插入额外的线条,因此填充多边形的轮与路径的轮廓可能不一致。
    QList<QPolygonF> toSubpathPolygons(const QTransform & matrix = QTransform()) const;
    //将路径转换为使用 QTransform矩阵 matrix的多边形列表,并返回该列表。
    //该函数会为每个子路径创建一个多边形,而不管是否存在相交子路径(即重叠的边界矩形)。
    //为了确保此类重叠子路径被正确填充,应使用“toFillPolygons()”函数。

    //这个枚举描述了用于在子路径中连接顶点的元素类型。
    //请注意,那些闭合子路径,使用`addEllipse()、addRegion()和`addText()、
    //  addPath()、`addPolygon()、`addRect()这些便捷函数添加的元素,
    //实际上是通过`moveTo()、lineTo()`和cubicTo()函数以一系列独立元素的形式添加到路径中的。
    enum ElementType {
             MoveToElement, //一个新的子路径。另见moveTo()。
             LineToElement, //一条线。另见lineTo()。
            CurveToElement, //一条曲线。另见 cubicTo()和 quadTo()。   //Curve曲线
        CurveToDataElement  //在CurveToElement元素中描述曲线所需的额外数据。
    };

    //The QPainterPath::Element class specifies the position and type of a subpath.
    class Element
    {
    public:
        qreal x;            //该变量存储元素位置的 x坐标。
        qreal y;            //该变量存储元素位置的 y坐标。
        ElementType type;   //此变量持有元素的类型。

        bool isMoveTo () const { return type ==  MoveToElement; }
        bool isLineTo () const { return type ==  LineToElement; }
        bool isCurveTo() const { return type == CurveToElement; }

        operator QPointF () const { return QPointF(x, y); }
        //类型转换运算符函数,得到路径中元素的起点。

        bool operator== (const Element & e) const //判断本元素和形参中元素是否是同一元素。
        {   return qFuzzyCompare(x, e.x) && qFuzzyCompare(y, e.y) && type == e.type; }
        inline
        bool operator!= (const Element & e) const { return !operator==(e); }
    };
    int                       elementCount     () const;      //返回画家路径中的元素数量。
    QPainterPath::Element     elementAt        (int i) const; //返回画家路径中在索引 i处的元素。
    void                   setElementPositionAt(int i, qreal x, qreal y);
    //将索引为index的元素的x和y坐标设置为x和y。

    qreal                   length(         ) const; //返回当前路径的长度。
    qreal          percentAtLength(qreal len) const; //返回指定长度len处的整个路径的百分比。
    //请注意,与类似的其他百分比方法一样,如果路径中存在曲线,则百分比测量与长度之间并非线性相关。
    //当路径中存在曲线时,百分比参数将被映射到Bezier方程的t参数。
    QPointF pointAtPercent        (qreal t  ) const;
    //返回当前路径的t百分比处的点。参数t必须在0到1之间。
    qreal   angleAtPercent        (qreal t  ) const;
    //返回路径在t百分比处的切线角度。参数t必须介于0和1之间。
    //角度的正值表示逆时针方向,负值表示顺时针方向。零度位于三点钟位置。
    qreal   slopeAtPercent        (qreal t  ) const;
    //返回路径在t百分比处的斜率。参数t必须介于0和1之间。


    //如果给定矩形 rect内的任何一点与路径相交,则返回true,否则返回false。
    //如果构成矩形的任何线条与路径的一部分相交,
    //  或者矩形的任何部分与路径所围成的任何区域重叠,就会产生一个交点。
    //该函数遵循当前的填充规则,以确定哪些部分被视为路径内部。
    //测试结论是:对于矩形与路径是一样的,相交或者完全包含,都会使本函返回 true。
    bool         intersects (const QRectF       & rect) const;
    bool         intersects (const QPainterPath & p   ) const;
    //如果当前路径与给定的路径p在任何点相交,则返回true。
    //如果当前路径包含p的任何部分或被p的任何部分包含,也返回 true。
    //对路径进行集合操作时,将把路径视为区域。非闭合路径将被视为隐式闭合。
    [[nodiscard]]
    QPainterPath intersected(const QPainterPath & r   ) const; // A交B(A&B)
    //返回一个路径,该路径是此路径填充区域与p的填充区域的交集。
    //由于 Bezier曲线的交点计算在数值上可能不稳定,因此可能会将 Bezier曲线平展为线段。

    //如果给定点 pt在路径内,则返回true;否则返回false。
    bool contains(const QPointF      & pt  ) const;
    bool contains(const QRectF       & rect) const;
    //如果给定的矩形 rect在路径内,则返回true;否则返回false。
    bool contains(const QPainterPath & p   ) const;
    //如果给定路径p包含在当前路径内,则返回true。如果当前路径和p的任意边相交,则返回false。
    //路径上的集合操作将把路径视为区域。非闭合路径将被视为隐式闭合。
    //测试发现路径的包含等价于矩形区域的比较。不是要严格的包含路径元素。


    //返回一个路径,该路径是此路径填充区域和 p的填充区域的并集。
    //对路径执行集操作时,这些路径将被视为区域。非闭合路径将被默认为闭合。
    //由于进行贝塞尔曲线交点的计算存在数值不稳定问题,贝塞尔曲线可能会被简化为线段。
    [[nodiscard]] QPainterPath united    (const QPainterPath & p) const; //A并B(A|B)
    //返回一个路径,该路径是把形参p的填充区域从本路径的填充区域中去掉后的填充区域。
    [[nodiscard]] QPainterPath subtracted(const QPainterPath & p) const; //A-B
    //返回此路径的简化版本。这意味着合并所有相交的子路径,并返回一个不包含相交边缘的路径。
    //连续的平行线也将合并。简化后的路径将始终使用默认填充规则Qt::OddEvenFill。
    [[nodiscard]] QPainterPath simplified() const;

    bool           operator== (const QPainterPath & other) const;
    bool           operator!= (const QPainterPath & other) const;

    QPainterPath   operator&  (const QPainterPath & other) const; //交集
    QPainterPath   operator|  (const QPainterPath & other) const; //并集
    QPainterPath   operator+  (const QPainterPath & other) const; //并集
    QPainterPath   operator-  (const QPainterPath & other) const; //差集
    QPainterPath & operator&= (const QPainterPath & other);
    QPainterPath & operator|= (const QPainterPath & other);
    QPainterPath & operator+= (const QPainterPath & other);
    QPainterPath & operator-= (const QPainterPath & other);


}; //完结 class QPainterPath

Q_DECLARE_SHARED(QPainterPath)
Q_DECLARE_TYPEINFO(QPainterPath::Element, Q_PRIMITIVE_TYPE);


inline QPainterPath operator *(const QPainterPath & p, const QTransform & m)
{ return m.map(p); }


//***************************************************************************
//***************************************************************************
//***************************************************************************

class Q_GUI_EXPORT QPainterPathStroker //本类似乎是为了为路径描边,得到其轮廓
{
    Q_DECLARE_PRIVATE(QPainterPathStroker)

public:
    QPainterPathStroker();
    explicit QPainterPathStroker(const QPen &pen);
    ~QPainterPathStroker();

    void setWidth(qreal width);
    qreal width() const;

    void setCapStyle(Qt::PenCapStyle style);
    Qt::PenCapStyle capStyle() const;

    void setJoinStyle(Qt::PenJoinStyle style);
    Qt::PenJoinStyle joinStyle() const;

    void setMiterLimit(qreal length);
    qreal miterLimit() const;

    void setCurveThreshold(qreal threshold);
    qreal curveThreshold() const;

    void setDashPattern(Qt::PenStyle);
    void setDashPattern(const QList<qreal> &dashPattern);
    QList<qreal> dashPattern() const;

    void setDashOffset(qreal offset);
    qreal dashOffset() const;

    QPainterPath createStroke(const QPainterPath & path) const;

private:
    Q_DISABLE_COPY(QPainterPathStroker)

    friend class QX11PaintEngine;

    QScopedPointer<QPainterPathStrokerPrivate> d_ptr;

}; //完结 class QPainterPathStroker



QT_END_NAMESPACE

#endif // QPAINTERPATH_H

(26)

谢谢

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

zhangzhangkeji

谢谢支持

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值