src/gui/painting/qpen.cpp
changeset 0 1918ee327afb
child 3 41300fa6a67c
equal deleted inserted replaced
-1:000000000000 0:1918ee327afb
       
     1 /****************************************************************************
       
     2 **
       
     3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
       
     4 ** All rights reserved.
       
     5 ** Contact: Nokia Corporation (qt-info@nokia.com)
       
     6 **
       
     7 ** This file is part of the QtGui module of the Qt Toolkit.
       
     8 **
       
     9 ** $QT_BEGIN_LICENSE:LGPL$
       
    10 ** No Commercial Usage
       
    11 ** This file contains pre-release code and may not be distributed.
       
    12 ** You may use this file in accordance with the terms and conditions
       
    13 ** contained in the Technology Preview License Agreement accompanying
       
    14 ** this package.
       
    15 **
       
    16 ** GNU Lesser General Public License Usage
       
    17 ** Alternatively, this file may be used under the terms of the GNU Lesser
       
    18 ** General Public License version 2.1 as published by the Free Software
       
    19 ** Foundation and appearing in the file LICENSE.LGPL included in the
       
    20 ** packaging of this file.  Please review the following information to
       
    21 ** ensure the GNU Lesser General Public License version 2.1 requirements
       
    22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
       
    23 **
       
    24 ** In addition, as a special exception, Nokia gives you certain additional
       
    25 ** rights.  These rights are described in the Nokia Qt LGPL Exception
       
    26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
       
    27 **
       
    28 ** If you have questions regarding the use of this file, please contact
       
    29 ** Nokia at qt-info@nokia.com.
       
    30 **
       
    31 **
       
    32 **
       
    33 **
       
    34 **
       
    35 **
       
    36 **
       
    37 **
       
    38 ** $QT_END_LICENSE$
       
    39 **
       
    40 ****************************************************************************/
       
    41 #include "qpen.h"
       
    42 #include "qpen_p.h"
       
    43 #include "qdatastream.h"
       
    44 #include "qvariant.h"
       
    45 #include "qbrush.h"
       
    46 
       
    47 #include <qdebug.h>
       
    48 
       
    49 QT_BEGIN_NAMESPACE
       
    50 
       
    51 typedef QPenPrivate QPenData;
       
    52 
       
    53 /*!
       
    54     \class QPen
       
    55     \ingroup painting
       
    56     \ingroup shared
       
    57 
       
    58 
       
    59     \brief The QPen class defines how a QPainter should draw lines and outlines
       
    60     of shapes.
       
    61 
       
    62     A pen has a style(), width(), brush(), capStyle() and joinStyle().
       
    63 
       
    64     The pen style defines the line type. The brush is used to fill
       
    65     strokes generated with the pen. Use the QBrush class to specify
       
    66     fill styles.  The cap style determines the line end caps that can
       
    67     be drawn using QPainter, while the join style describes how joins
       
    68     between two lines are drawn. The pen width can be specified in
       
    69     both integer (width()) and floating point (widthF()) precision. A
       
    70     line width of zero indicates a cosmetic pen.  This means that the
       
    71     pen width is always drawn one pixel wide, independent of the \l
       
    72     {QPainter#Coordinate Transformations}{transformation} set on the
       
    73     painter.
       
    74 
       
    75     The various settings can easily be modified using the
       
    76     corresponding setStyle(), setWidth(), setBrush(), setCapStyle()
       
    77     and setJoinStyle() functions (note that the painter's pen must be
       
    78     reset when altering the pen's properties).
       
    79 
       
    80     For example:
       
    81 
       
    82     \snippet doc/src/snippets/code/src_gui_painting_qpen.cpp 0
       
    83 
       
    84     which is equivalent to
       
    85 
       
    86     \snippet doc/src/snippets/code/src_gui_painting_qpen.cpp 1
       
    87 
       
    88     The default pen is a solid black brush with 0 width, square
       
    89     cap style (Qt::SquareCap), and  bevel join style (Qt::BevelJoin).
       
    90 
       
    91     In addition QPen provides the color() and setColor()
       
    92     convenience functions to extract and set the color of the pen's
       
    93     brush, respectively. Pens may also be compared and streamed.
       
    94 
       
    95     For more information about painting in general, see \l{The Paint
       
    96     System} documentation.
       
    97 
       
    98     \tableofcontents
       
    99 
       
   100     \section1 Pen Style
       
   101 
       
   102     Qt provides several built-in styles represented by the
       
   103     Qt::PenStyle enum:
       
   104 
       
   105     \table
       
   106     \row
       
   107     \o \inlineimage qpen-solid.png
       
   108     \o \inlineimage qpen-dash.png
       
   109     \o \inlineimage qpen-dot.png
       
   110     \row
       
   111     \o Qt::SolidLine
       
   112     \o Qt::DashLine
       
   113     \o Qt::DotLine
       
   114     \row
       
   115     \o \inlineimage qpen-dashdot.png
       
   116     \o \inlineimage qpen-dashdotdot.png
       
   117     \o \inlineimage qpen-custom.png
       
   118     \row
       
   119     \o Qt::DashDotLine
       
   120     \o Qt::DashDotDotLine
       
   121     \o Qt::CustomDashLine
       
   122     \endtable
       
   123 
       
   124     Simply use the setStyle() function to convert the pen style to
       
   125     either of the built-in styles, except the Qt::CustomDashLine style
       
   126     which we will come back to shortly. Setting the style to Qt::NoPen
       
   127     tells the painter to not draw lines or outlines. The default pen
       
   128     style is Qt::SolidLine.
       
   129 
       
   130     Since Qt 4.1 it is also possible to specify a custom dash pattern
       
   131     using the setDashPattern() function which implicitly converts the
       
   132     style of the pen to Qt::CustomDashLine. The pattern argument, a
       
   133     QVector, must be specified as an even number of \l qreal entries
       
   134     where the entries 1, 3, 5... are the dashes and 2, 4, 6... are the
       
   135     spaces. For example, the custom pattern shown above is created
       
   136     using the following code:
       
   137 
       
   138     \snippet doc/src/snippets/code/src_gui_painting_qpen.cpp 2
       
   139 
       
   140     Note that the dash pattern is specified in units of the pens
       
   141     width, e.g. a dash of length 5 in width 10 is 50 pixels long.
       
   142 
       
   143     The currently set dash pattern can be retrieved using the
       
   144     dashPattern() function. Use the isSolid() function to determine
       
   145     whether the pen has a solid fill, or not.
       
   146 
       
   147     \section1 Cap Style
       
   148 
       
   149     The cap style defines how the end points of lines are drawn using
       
   150     QPainter.  The cap style only apply to wide lines, i.e. when the
       
   151     width is 1 or greater. The Qt::PenCapStyle enum provides the
       
   152     following styles:
       
   153 
       
   154     \table
       
   155     \row
       
   156     \o \inlineimage qpen-square.png
       
   157     \o \inlineimage qpen-flat.png
       
   158     \o \inlineimage qpen-roundcap.png
       
   159     \row
       
   160     \o Qt::SquareCap
       
   161     \o Qt::FlatCap
       
   162     \o Qt::RoundCap
       
   163     \endtable
       
   164 
       
   165     The Qt::SquareCap style is a square line end that covers the end
       
   166     point and extends beyond it by half the line width. The
       
   167     Qt::FlatCap style is a square line end that does not cover the end
       
   168     point of the line. And the Qt::RoundCap style is a rounded line
       
   169     end covering the end point.
       
   170 
       
   171     The default is Qt::SquareCap.
       
   172 
       
   173     Whether or not end points are drawn when the pen width is 0 or 1
       
   174     depends on the cap style. Using Qt::SquareCap or Qt::RoundCap they
       
   175     are drawn, using Qt::FlatCap they are not drawn.
       
   176 
       
   177     \section1 Join Style
       
   178 
       
   179     The join style defines how joins between two connected lines can
       
   180     be drawn using QPainter. The join style only apply to wide lines,
       
   181     i.e. when the width is 1 or greater. The Qt::PenJoinStyle enum
       
   182     provides the following styles:
       
   183 
       
   184     \table
       
   185     \row
       
   186     \o \inlineimage qpen-bevel.png
       
   187     \o \inlineimage qpen-miter.png
       
   188     \o \inlineimage qpen-roundjoin.png
       
   189     \row
       
   190     \o Qt::BevelJoin
       
   191     \o Qt::MiterJoin
       
   192     \o Qt::RoundJoin
       
   193     \endtable
       
   194 
       
   195     The Qt::BevelJoin style fills the triangular notch between the two
       
   196     lines. The Qt::MiterJoin style extends the lines to meet at an
       
   197     angle. And the Qt::RoundJoin style fills a circular arc between
       
   198     the two lines.
       
   199 
       
   200     The default is Qt::BevelJoin.
       
   201 
       
   202     \image qpen-miterlimit.png
       
   203 
       
   204     When the Qt::MiterJoin style is applied, it is possible to use the
       
   205     setMiterLimit() function to specify how far the miter join can
       
   206     extend from the join point. The miterLimit() is used to reduce
       
   207     artifacts between line joins where the lines are close to
       
   208     parallel.
       
   209 
       
   210     The miterLimit() must be specified in units of the pens width,
       
   211     e.g. a miter limit of 5 in width 10 is 50 pixels long. The
       
   212     default miter limit is 2, i.e. twice the pen width in pixels.
       
   213 
       
   214     \table 100%
       
   215     \row
       
   216     \o \inlineimage qpen-demo.png
       
   217     \o \bold {\l {demos/pathstroke}{The Path Stroking Demo}}
       
   218 
       
   219     The Path Stroking demo shows Qt's built-in dash patterns and shows
       
   220     how custom patterns can be used to extend the range of available
       
   221     patterns.
       
   222     \endtable
       
   223 
       
   224     \sa QPainter, QBrush, {demos/pathstroke}{Path Stroking Demo},
       
   225         {Scribble Example}
       
   226 */
       
   227 
       
   228 /*!
       
   229   \internal
       
   230 */
       
   231 inline QPenPrivate::QPenPrivate(const QBrush &_brush, qreal _width, Qt::PenStyle penStyle,
       
   232                                 Qt::PenCapStyle _capStyle, Qt::PenJoinStyle _joinStyle)
       
   233     : dashOffset(0), miterLimit(2),
       
   234       cosmetic(false)
       
   235 {
       
   236     ref = 1;
       
   237     width = _width;
       
   238     brush = _brush;
       
   239     style = penStyle;
       
   240     capStyle = _capStyle;
       
   241     joinStyle = _joinStyle;
       
   242 }
       
   243 
       
   244 static const Qt::PenCapStyle qpen_default_cap = Qt::SquareCap;
       
   245 static const Qt::PenJoinStyle qpen_default_join = Qt::BevelJoin;
       
   246 
       
   247 #ifndef QT_NO_THREAD
       
   248 // Special deleter that only deletes if the ref-count goes to zero
       
   249 template <>
       
   250 class QGlobalStaticDeleter<QPenPrivate>
       
   251 {
       
   252 public:
       
   253     QGlobalStatic<QPenPrivate> &globalStatic;
       
   254     QGlobalStaticDeleter(QGlobalStatic<QPenPrivate> &_globalStatic)
       
   255         : globalStatic(_globalStatic)
       
   256     { }
       
   257 
       
   258     inline ~QGlobalStaticDeleter()
       
   259     {
       
   260         if (!globalStatic.pointer->ref.deref())
       
   261             delete globalStatic.pointer;
       
   262         globalStatic.pointer = 0;
       
   263         globalStatic.destroyed = true;
       
   264     }
       
   265 };
       
   266 #endif
       
   267 
       
   268 Q_GLOBAL_STATIC_WITH_ARGS(QPenData, defaultPenInstance,
       
   269                           (Qt::black, 0, Qt::SolidLine, qpen_default_cap, qpen_default_join))
       
   270 Q_GLOBAL_STATIC_WITH_ARGS(QPenData, nullPenInstance,
       
   271                           (Qt::black, 0, Qt::NoPen, qpen_default_cap, qpen_default_join))
       
   272 
       
   273 /*!
       
   274     Constructs a default black solid line pen with 0 width.
       
   275 */
       
   276 
       
   277 QPen::QPen()
       
   278 {
       
   279     d = defaultPenInstance();
       
   280     d->ref.ref();
       
   281 }
       
   282 
       
   283 /*!
       
   284     Constructs a black pen with 0 width and the given \a style.
       
   285 
       
   286     \sa setStyle()
       
   287 */
       
   288 
       
   289 QPen::QPen(Qt::PenStyle style)
       
   290 {
       
   291     if (style == Qt::NoPen) {
       
   292         d = nullPenInstance();
       
   293         d->ref.ref();
       
   294     } else {
       
   295         d = new QPenData(Qt::black, 0, style, qpen_default_cap, qpen_default_join);
       
   296     }
       
   297 }
       
   298 
       
   299 
       
   300 /*!
       
   301     Constructs a solid line pen with 0 width and the given \a color.
       
   302 
       
   303     \sa setBrush(), setColor()
       
   304 */
       
   305 
       
   306 QPen::QPen(const QColor &color)
       
   307 {
       
   308     d = new QPenData(color, 0, Qt::SolidLine, qpen_default_cap, qpen_default_join);
       
   309 }
       
   310 
       
   311 
       
   312 /*!
       
   313     \fn QPen::QPen(const QBrush &brush, qreal width, Qt::PenStyle style, Qt::PenCapStyle cap, Qt::PenJoinStyle join)
       
   314 
       
   315     Constructs a pen with the specified \a brush, \a width, pen \a style,
       
   316     \a cap style and \a join style.
       
   317 
       
   318     \sa setBrush(), setWidth(), setStyle(),  setCapStyle(), setJoinStyle()
       
   319 */
       
   320 
       
   321 QPen::QPen(const QBrush &brush, qreal width, Qt::PenStyle s, Qt::PenCapStyle c, Qt::PenJoinStyle j)
       
   322 {
       
   323     d = new QPenData(brush, width, s, c, j);
       
   324 }
       
   325 
       
   326 /*!
       
   327     \fn QPen::QPen(const QPen &pen)
       
   328 
       
   329     Constructs a pen that is a copy of the given \a pen.
       
   330 */
       
   331 
       
   332 QPen::QPen(const QPen &p)
       
   333 {
       
   334     d = p.d;
       
   335     d->ref.ref();
       
   336 }
       
   337 
       
   338 
       
   339 /*!
       
   340     Destroys the pen.
       
   341 */
       
   342 
       
   343 QPen::~QPen()
       
   344 {
       
   345     if (!d->ref.deref())
       
   346         delete d;
       
   347 }
       
   348 
       
   349 /*!
       
   350     \fn void QPen::detach()
       
   351     Detaches from shared pen data to make sure that this pen is the
       
   352     only one referring the data.
       
   353 
       
   354     If multiple pens share common data, this pen dereferences the data
       
   355     and gets a copy of the data. Nothing is done if there is just a
       
   356     single reference.
       
   357 */
       
   358 
       
   359 void QPen::detach()
       
   360 {
       
   361     if (d->ref == 1)
       
   362         return;
       
   363 
       
   364     QPenData *x = new QPenData(*static_cast<QPenData *>(d));
       
   365     if (!d->ref.deref())
       
   366         delete d;
       
   367     x->ref = 1;
       
   368     d = x;
       
   369 }
       
   370 
       
   371 
       
   372 /*!
       
   373     \fn QPen &QPen::operator=(const QPen &pen)
       
   374 
       
   375     Assigns the given \a pen to this pen and returns a reference to
       
   376     this pen.
       
   377 */
       
   378 
       
   379 QPen &QPen::operator=(const QPen &p)
       
   380 {
       
   381     qAtomicAssign(d, p.d);
       
   382     return *this;
       
   383 }
       
   384 
       
   385 /*!
       
   386    Returns the pen as a QVariant.
       
   387 */
       
   388 QPen::operator QVariant() const
       
   389 {
       
   390     return QVariant(QVariant::Pen, this);
       
   391 }
       
   392 
       
   393 /*!
       
   394     \fn Qt::PenStyle QPen::style() const
       
   395 
       
   396     Returns the pen style.
       
   397 
       
   398     \sa setStyle(), {QPen#Pen Style}{Pen Style}
       
   399 */
       
   400 Qt::PenStyle QPen::style() const
       
   401 {
       
   402     return d->style;
       
   403 }
       
   404 /*!
       
   405     \fn void QPen::setStyle(Qt::PenStyle style)
       
   406 
       
   407     Sets the pen style to the given \a style.
       
   408 
       
   409     See the \l Qt::PenStyle documentation for a list of the available
       
   410     styles. Since Qt 4.1 it is also possible to specify a custom dash
       
   411     pattern using the setDashPattern() function which implicitly
       
   412     converts the style of the pen to Qt::CustomDashLine.
       
   413 
       
   414     \note This function resets the dash offset to zero.
       
   415 
       
   416     \sa style(), {QPen#Pen Style}{Pen Style}
       
   417 */
       
   418 
       
   419 void QPen::setStyle(Qt::PenStyle s)
       
   420 {
       
   421     if (d->style == s)
       
   422         return;
       
   423     detach();
       
   424     d->style = s;
       
   425     QPenData *dd = static_cast<QPenData *>(d);
       
   426     dd->dashPattern.clear();
       
   427     dd->dashOffset = 0;
       
   428 }
       
   429 
       
   430 /*!
       
   431     Returns the dash pattern of this pen.
       
   432 
       
   433     \sa style(), isSolid()
       
   434  */
       
   435 QVector<qreal> QPen::dashPattern() const
       
   436 {
       
   437     QPenData *dd = static_cast<QPenData *>(d);
       
   438     if (d->style == Qt::SolidLine || d->style == Qt::NoPen) {
       
   439         return QVector<qreal>();
       
   440     } else if (dd->dashPattern.isEmpty()) {
       
   441         const qreal space = 2;
       
   442         const qreal dot = 1;
       
   443         const qreal dash = 4;
       
   444 
       
   445         switch (d->style) {
       
   446         case Qt::DashLine:
       
   447             dd->dashPattern << dash << space;
       
   448             break;
       
   449         case Qt::DotLine:
       
   450             dd->dashPattern << dot << space;
       
   451             break;
       
   452         case Qt::DashDotLine:
       
   453             dd->dashPattern << dash << space << dot << space;
       
   454             break;
       
   455         case Qt::DashDotDotLine:
       
   456             dd->dashPattern << dash << space << dot << space << dot << space;
       
   457             break;
       
   458         default:
       
   459             break;
       
   460         }
       
   461     }
       
   462     return dd->dashPattern;
       
   463 }
       
   464 
       
   465 /*!
       
   466     Sets the dash pattern for this pen to the given \a pattern. This
       
   467     implicitly converts the style of the pen to Qt::CustomDashLine.
       
   468 
       
   469     The pattern must be specified as an even number of positive entries
       
   470     where the entries 1, 3, 5... are the dashes and 2, 4, 6... are the
       
   471     spaces. For example:
       
   472 
       
   473     \table 100%
       
   474     \row
       
   475     \o \inlineimage qpen-custom.png
       
   476     \o
       
   477     \snippet doc/src/snippets/code/src_gui_painting_qpen.cpp 3
       
   478     \endtable
       
   479 
       
   480     The dash pattern is specified in units of the pens width; e.g. a
       
   481     dash of length 5 in width 10 is 50 pixels long. Note that a pen
       
   482     with zero width is equivalent to a cosmetic pen with a width of 1
       
   483     pixel.
       
   484 
       
   485     Each dash is also subject to cap styles so a dash of 1 with square
       
   486     cap set will extend 0.5 pixels out in each direction resulting in
       
   487     a total width of 2.
       
   488 
       
   489     Note that the default cap style is Qt::SquareCap, meaning that a
       
   490     square line end covers the end point and extends beyond it by half
       
   491     the line width.
       
   492 
       
   493     \sa setStyle(), dashPattern(), setCapStyle(), setCosmetic()
       
   494  */
       
   495 void QPen::setDashPattern(const QVector<qreal> &pattern)
       
   496 {
       
   497     if (pattern.isEmpty())
       
   498         return;
       
   499     detach();
       
   500 
       
   501     QPenData *dd = static_cast<QPenData *>(d);
       
   502     dd->dashPattern = pattern;
       
   503     d->style = Qt::CustomDashLine;
       
   504 
       
   505     if ((dd->dashPattern.size() % 2) == 1) {
       
   506         qWarning("QPen::setDashPattern: Pattern not of even length");
       
   507         dd->dashPattern << 1;
       
   508     }
       
   509 }
       
   510 
       
   511 
       
   512 /*!
       
   513     Returns the dash offset for the pen.
       
   514 
       
   515     \sa setDashOffset()
       
   516 */
       
   517 qreal QPen::dashOffset() const
       
   518 {
       
   519     QPenData *dd = static_cast<QPenData *>(d);
       
   520     return dd->dashOffset;
       
   521 }
       
   522 /*!
       
   523     Sets the dash offset (the starting point on the dash pattern) for this pen
       
   524     to the \a offset specified. The offset is measured in terms of the units used
       
   525     to specify the dash pattern.
       
   526 
       
   527     \table
       
   528     \row \o \inlineimage qpen-dashpattern.png
       
   529     \o For example, a pattern where each stroke is four units long, followed by a gap
       
   530     of two units, will begin with the stroke when drawn as a line.
       
   531 
       
   532     However, if the dash offset is set to 4.0, any line drawn will begin with the gap.
       
   533     Values of the offset up to 4.0 will cause part of the stroke to be drawn first,
       
   534     and values of the offset between 4.0 and 6.0 will cause the line to begin with
       
   535     part of the gap.
       
   536     \endtable
       
   537 
       
   538     \note This implicitly converts the style of the pen to Qt::CustomDashLine.
       
   539 */
       
   540 void QPen::setDashOffset(qreal offset)
       
   541 {
       
   542     if (qFuzzyCompare(offset, static_cast<QPenData *>(d)->dashOffset))
       
   543         return;
       
   544     detach();
       
   545     QPenData *dd = static_cast<QPenData *>(d);
       
   546     dd->dashOffset = offset;
       
   547     if (d->style != Qt::CustomDashLine) {
       
   548         dd->dashPattern = dashPattern();
       
   549         d->style = Qt::CustomDashLine;
       
   550     }
       
   551 }
       
   552 
       
   553 /*!
       
   554     Returns the miter limit of the pen. The miter limit is only
       
   555     relevant when the join style is set to Qt::MiterJoin.
       
   556 
       
   557     \sa setMiterLimit(),  {QPen#Join Style}{Join Style}
       
   558 */
       
   559 qreal QPen::miterLimit() const
       
   560 {
       
   561     const QPenData *dd = static_cast<QPenData *>(d);
       
   562     return dd->miterLimit;
       
   563 }
       
   564 
       
   565 /*!
       
   566     Sets the miter limit of this pen to the given \a limit.
       
   567 
       
   568     \image qpen-miterlimit.png
       
   569 
       
   570     The miter limit describes how far a miter join can extend from the
       
   571     join point. This is used to reduce artifacts between line joins
       
   572     where the lines are close to parallel.
       
   573 
       
   574     This value does only have effect when the pen style is set to
       
   575     Qt::MiterJoin. The value is specified in units of the pen's width,
       
   576     e.g. a miter limit of 5 in width 10 is 50 pixels long. The default
       
   577     miter limit is 2, i.e. twice the pen width in pixels.
       
   578 
       
   579     \sa miterLimit(), setJoinStyle(), {QPen#Join Style}{Join Style}
       
   580 */
       
   581 void QPen::setMiterLimit(qreal limit)
       
   582 {
       
   583     detach();
       
   584     QPenData *dd = static_cast<QPenData *>(d);
       
   585     dd->miterLimit = limit;
       
   586 }
       
   587 
       
   588 
       
   589 /*!
       
   590     \fn qreal QPen::width() const
       
   591 
       
   592     Returns the pen width with integer precision.
       
   593 
       
   594     \sa setWidth(), widthF()
       
   595 */
       
   596 
       
   597 int QPen::width() const
       
   598 {
       
   599     return qRound(d->width);
       
   600 }
       
   601 
       
   602 /*!
       
   603     \fn qreal QPen::widthF() const
       
   604 
       
   605     Returns the pen width with floating point precision.
       
   606 
       
   607     \sa setWidthF() width()
       
   608 */
       
   609 qreal QPen::widthF() const
       
   610 {
       
   611     return d->width;
       
   612 }
       
   613 
       
   614 /*!
       
   615     \fn QPen::setWidth(int width)
       
   616 
       
   617     Sets the pen width to the given \a width in pixels with integer
       
   618     precision.
       
   619 
       
   620     A line width of zero indicates a cosmetic pen. This means that the
       
   621     pen width is always drawn one pixel wide, independent of the \l
       
   622     {QPainter#Coordinate Transformations}{transformation} set on the
       
   623     painter.
       
   624 
       
   625     Setting a pen width with a negative value is not supported.
       
   626 
       
   627     \sa setWidthF(), width()
       
   628 */
       
   629 void QPen::setWidth(int width)
       
   630 {
       
   631     if (width < 0)
       
   632         qWarning("QPen::setWidth: Setting a pen width with a negative value is not defined");
       
   633     if ((qreal)width == d->width)
       
   634         return;
       
   635     detach();
       
   636     d->width = width;
       
   637 }
       
   638 
       
   639 /*!
       
   640     Sets the pen width to the given \a width in pixels with floating point
       
   641     precision.
       
   642 
       
   643     A line width of zero indicates a cosmetic pen. This means that the
       
   644     pen width is always drawn one pixel wide, independent of the \l
       
   645     {QPainter#Coordinate Transformations}{transformation} on the
       
   646     painter.
       
   647 
       
   648     Setting a pen width with a negative value is not supported.
       
   649 
       
   650     \sa setWidth() widthF()
       
   651 */
       
   652 
       
   653 void QPen::setWidthF(qreal width)
       
   654 {
       
   655     if (width < 0.f)
       
   656         qWarning("QPen::setWidthF: Setting a pen width with a negative value is not defined");
       
   657     if (qAbs(d->width - width) < 0.00000001f)
       
   658         return;
       
   659     detach();
       
   660     d->width = width;
       
   661 }
       
   662 
       
   663 
       
   664 /*!
       
   665     Returns the pen's cap style.
       
   666 
       
   667     \sa setCapStyle(), {QPen#Cap Style}{Cap Style}
       
   668 */
       
   669 Qt::PenCapStyle QPen::capStyle() const
       
   670 {
       
   671     return d->capStyle;
       
   672 }
       
   673 
       
   674 /*!
       
   675     \fn void QPen::setCapStyle(Qt::PenCapStyle style)
       
   676 
       
   677     Sets the pen's cap style to the given \a style. The default value
       
   678     is Qt::SquareCap.
       
   679 
       
   680     \sa capStyle(), {QPen#Cap Style}{Cap Style}
       
   681 */
       
   682 
       
   683 void QPen::setCapStyle(Qt::PenCapStyle c)
       
   684 {
       
   685     if (d->capStyle == c)
       
   686         return;
       
   687     detach();
       
   688     d->capStyle = c;
       
   689 }
       
   690 
       
   691 /*!
       
   692     Returns the pen's join style.
       
   693 
       
   694     \sa setJoinStyle(),  {QPen#Join Style}{Join Style}
       
   695 */
       
   696 Qt::PenJoinStyle QPen::joinStyle() const
       
   697 {
       
   698     return d->joinStyle;
       
   699 }
       
   700 
       
   701 /*!
       
   702     \fn void QPen::setJoinStyle(Qt::PenJoinStyle style)
       
   703 
       
   704     Sets the pen's join style to the given \a style. The default value
       
   705     is Qt::BevelJoin.
       
   706 
       
   707     \sa joinStyle(), {QPen#Join Style}{Join Style}
       
   708 */
       
   709 
       
   710 void QPen::setJoinStyle(Qt::PenJoinStyle j)
       
   711 {
       
   712     if (d->joinStyle == j)
       
   713         return;
       
   714     detach();
       
   715     d->joinStyle = j;
       
   716 }
       
   717 
       
   718 /*!
       
   719     \fn const QColor &QPen::color() const
       
   720 
       
   721     Returns the color of this pen's brush.
       
   722 
       
   723     \sa brush(), setColor()
       
   724 */
       
   725 QColor QPen::color() const
       
   726 {
       
   727     return d->brush.color();
       
   728 }
       
   729 
       
   730 /*!
       
   731     \fn void QPen::setColor(const QColor &color)
       
   732 
       
   733     Sets the color of this pen's brush to the given \a color.
       
   734 
       
   735     \sa setBrush(), color()
       
   736 */
       
   737 
       
   738 void QPen::setColor(const QColor &c)
       
   739 {
       
   740     detach();
       
   741     d->brush = QBrush(c);
       
   742 }
       
   743 
       
   744 
       
   745 /*!
       
   746     Returns the brush used to fill strokes generated with this pen.
       
   747 */
       
   748 QBrush QPen::brush() const
       
   749 {
       
   750     return d->brush;
       
   751 }
       
   752 
       
   753 /*!
       
   754     Sets the brush used to fill strokes generated with this pen to the given
       
   755     \a brush.
       
   756 
       
   757     \sa brush(), setColor()
       
   758 */
       
   759 void QPen::setBrush(const QBrush &brush)
       
   760 {
       
   761     detach();
       
   762     d->brush = brush;
       
   763 }
       
   764 
       
   765 
       
   766 /*!
       
   767     Returns true if the pen has a solid fill, otherwise false.
       
   768 
       
   769     \sa style(), dashPattern()
       
   770 */
       
   771 bool QPen::isSolid() const
       
   772 {
       
   773     return d->brush.style() == Qt::SolidPattern;
       
   774 }
       
   775 
       
   776 
       
   777 /*!
       
   778     Returns true if the pen is cosmetic; otherwise returns false.
       
   779 
       
   780     Cosmetic pens are used to draw strokes that have a constant width
       
   781     regardless of any transformations applied to the QPainter they are
       
   782     used with. Drawing a shape with a cosmetic pen ensures that its
       
   783     outline will have the same thickness at different scale factors.
       
   784 
       
   785     A zero width pen is cosmetic by default; pens with a non-zero width
       
   786     are non-cosmetic.
       
   787 
       
   788     \sa setCosmetic(), widthF()
       
   789 */
       
   790 
       
   791 bool QPen::isCosmetic() const
       
   792 {
       
   793     QPenData *dd = static_cast<QPenData *>(d);
       
   794     return (dd->cosmetic == true) || d->width == 0;
       
   795 }
       
   796 
       
   797 
       
   798 /*!
       
   799     Sets this pen to cosmetic or non-cosmetic, depending on the value of
       
   800     \a cosmetic.
       
   801 
       
   802     \sa isCosmetic()
       
   803 */
       
   804 
       
   805 void QPen::setCosmetic(bool cosmetic)
       
   806 {
       
   807     detach();
       
   808     QPenData *dd = static_cast<QPenData *>(d);
       
   809     dd->cosmetic = cosmetic;
       
   810 }
       
   811 
       
   812 
       
   813 
       
   814 /*!
       
   815     \fn bool QPen::operator!=(const QPen &pen) const
       
   816 
       
   817     Returns true if the pen is different from the given \a pen;
       
   818     otherwise false. Two pens are different if they have different
       
   819     styles, widths or colors.
       
   820 
       
   821     \sa operator==()
       
   822 */
       
   823 
       
   824 /*!
       
   825     \fn bool QPen::operator==(const QPen &pen) const
       
   826 
       
   827     Returns true if the pen is equal to the given \a pen; otherwise
       
   828     false. Two pens are equal if they have equal styles, widths and
       
   829     colors.
       
   830 
       
   831     \sa operator!=()
       
   832 */
       
   833 
       
   834 bool QPen::operator==(const QPen &p) const
       
   835 {
       
   836     QPenData *dd = static_cast<QPenData *>(d);
       
   837     QPenData *pdd = static_cast<QPenData *>(p.d);
       
   838     return (p.d == d) || (p.d->style == d->style
       
   839                           && p.d->capStyle == d->capStyle
       
   840                           && p.d->joinStyle == d->joinStyle
       
   841                           && p.d->width == d->width
       
   842                           && pdd->miterLimit == dd->miterLimit
       
   843                           && (d->style != Qt::CustomDashLine
       
   844                               || (qFuzzyCompare(pdd->dashOffset, dd->dashOffset) &&
       
   845                                   pdd->dashPattern == dd->dashPattern))
       
   846                           && p.d->brush == d->brush
       
   847                           && pdd->cosmetic == dd->cosmetic);
       
   848 }
       
   849 
       
   850 
       
   851 /*!
       
   852     \fn bool QPen::isDetached()
       
   853 
       
   854     \internal
       
   855 */
       
   856 
       
   857 bool QPen::isDetached()
       
   858 {
       
   859     return d->ref == 1;
       
   860 }
       
   861 
       
   862 
       
   863 /*****************************************************************************
       
   864   QPen stream functions
       
   865  *****************************************************************************/
       
   866 #ifndef QT_NO_DATASTREAM
       
   867 /*!
       
   868     \fn QDataStream &operator<<(QDataStream &stream, const QPen &pen)
       
   869     \relates QPen
       
   870 
       
   871     Writes the given \a pen to the given \a stream and returns a reference to
       
   872     the \a stream.
       
   873 
       
   874     \sa {Format of the QDataStream Operators}
       
   875 */
       
   876 
       
   877 QDataStream &operator<<(QDataStream &s, const QPen &p)
       
   878 {
       
   879     QPenData *dd = static_cast<QPenData *>(p.d);
       
   880     if (s.version() < 3) {
       
   881         s << (quint8)p.style();
       
   882     } else if (s.version() < QDataStream::Qt_4_3) {
       
   883         s << (quint8)(p.style() | p.capStyle() | p.joinStyle());
       
   884     } else {
       
   885         s << (quint16)(p.style() | p.capStyle() | p.joinStyle());
       
   886         s << (bool)(dd->cosmetic);
       
   887     }
       
   888 
       
   889     if (s.version() < 7) {
       
   890         s << (quint8)p.width();
       
   891         s << p.color();
       
   892     } else {
       
   893         s << double(p.widthF());
       
   894         s << p.brush();
       
   895         s << double(p.miterLimit());
       
   896         if (sizeof(qreal) == sizeof(double)) {
       
   897             s << p.dashPattern();
       
   898         } else {
       
   899             // ensure that we write doubles here instead of streaming the pattern
       
   900             // directly; otherwise, platforms that redefine qreal might generate
       
   901             // data that cannot be read on other platforms.
       
   902             QVector<qreal> pattern = p.dashPattern();
       
   903             s << quint32(pattern.size());
       
   904             for (int i = 0; i < pattern.size(); ++i)
       
   905                 s << double(pattern.at(i));
       
   906         }
       
   907         if (s.version() >= 9)
       
   908             s << double(p.dashOffset());
       
   909     }
       
   910     return s;
       
   911 }
       
   912 
       
   913 /*!
       
   914     \fn QDataStream &operator>>(QDataStream &stream, QPen &pen)
       
   915     \relates QPen
       
   916 
       
   917     Reads a pen from the given \a stream into the given \a pen and
       
   918     returns a reference to the \a stream.
       
   919 
       
   920     \sa {Format of the QDataStream Operators}
       
   921 */
       
   922 
       
   923 QDataStream &operator>>(QDataStream &s, QPen &p)
       
   924 {
       
   925     quint16 style;
       
   926     quint8 width8 = 0;
       
   927     double width = 0;
       
   928     QColor color;
       
   929     QBrush brush;
       
   930     double miterLimit = 2;
       
   931     QVector<qreal> dashPattern;
       
   932     double dashOffset = 0;
       
   933     bool cosmetic = false;
       
   934     if (s.version() < QDataStream::Qt_4_3) {
       
   935         quint8 style8;
       
   936         s >> style8;
       
   937         style = style8;
       
   938     } else {
       
   939         s >> style;
       
   940         s >> cosmetic;
       
   941     }
       
   942     if (s.version() < 7) {
       
   943         s >> width8;
       
   944         s >> color;
       
   945         brush = color;
       
   946         width = width8;
       
   947     } else {
       
   948         s >> width;
       
   949         s >> brush;
       
   950         s >> miterLimit;
       
   951         if (sizeof(qreal) == sizeof(double)) {
       
   952             s >> dashPattern;
       
   953         } else {
       
   954             quint32 numDashes;
       
   955             s >> numDashes;
       
   956             double dash;
       
   957             for (quint32 i = 0; i < numDashes; ++i) {
       
   958                 s >> dash;
       
   959                 dashPattern << dash;
       
   960             }
       
   961         }
       
   962         if (s.version() >= 9)
       
   963             s >> dashOffset;
       
   964     }
       
   965 
       
   966     p.detach();
       
   967     QPenData *dd = static_cast<QPenData *>(p.d);
       
   968     dd->width = width;
       
   969     dd->brush = brush;
       
   970     dd->style = Qt::PenStyle(style & Qt::MPenStyle);
       
   971     dd->capStyle = Qt::PenCapStyle(style & Qt::MPenCapStyle);
       
   972     dd->joinStyle = Qt::PenJoinStyle(style & Qt::MPenJoinStyle);
       
   973     dd->dashPattern = dashPattern;
       
   974     dd->miterLimit = miterLimit;
       
   975     dd->dashOffset = dashOffset;
       
   976     dd->cosmetic = cosmetic;
       
   977 
       
   978     return s;
       
   979 }
       
   980 #endif //QT_NO_DATASTREAM
       
   981 
       
   982 #ifndef QT_NO_DEBUG_STREAM
       
   983 QDebug operator<<(QDebug dbg, const QPen &p)
       
   984 {
       
   985 #ifndef Q_BROKEN_DEBUG_STREAM
       
   986     dbg.nospace() << "QPen(" << p.width() << ',' << p.brush()
       
   987                   << ',' << int(p.style()) << ',' << int(p.capStyle())
       
   988                   << ',' << int(p.joinStyle()) << ',' << p.dashPattern()
       
   989                   << ',' << p.dashOffset()
       
   990                   << ',' << p.miterLimit() << ')';
       
   991     return dbg.space();
       
   992 #else
       
   993     qWarning("This compiler doesn't support streaming QPen to QDebug");
       
   994     return dbg;
       
   995     Q_UNUSED(p);
       
   996 #endif
       
   997 }
       
   998 #endif
       
   999 
       
  1000 /*!
       
  1001     \fn DataPtr &QPen::data_ptr()
       
  1002     \internal
       
  1003 */
       
  1004 
       
  1005 /*!
       
  1006     \typedef QPen::DataPtr
       
  1007 
       
  1008     \internal
       
  1009 */
       
  1010 
       
  1011 QT_END_NAMESPACE
       
  1012 
       
  1013 #undef QT_COMPILING_QPEN