24  : QPaintEngine( QPaintEngine::AllFeatures  )
 
   25  , mPaintDevice( dxfDevice )
 
 
   43  return QPaintEngine::User;
 
 
   55  if ( state.state() & QPaintEngine::DirtyTransform )
 
   56    mTransform = state.transform();
 
   58  if ( state.state() & QPaintEngine::DirtyPen )
 
   61  if ( state.state() & QPaintEngine::DirtyBrush )
 
   62    mBrush = state.brush();
 
   64  if ( state.state() & QPaintEngine::DirtyOpacity )
 
   66    mOpacity = state.opacity();
 
 
   70void QgsDxfPaintEngine::setRing( 
QgsPointSequence &polyline, 
const QPointF *points, 
int pointCount )
 
   73  for ( 
int i = 0; i < pointCount; ++i )
 
   74    polyline.append( toDxfCoordinates( points[i] ) );
 
   80  if ( !mDxf || !mPaintDevice )
 
   85  setRing( polygon.last(), points, pointCount );
 
   87  if ( mode == QPaintEngine::PolylineMode )
 
   89    if ( mPen.style() != Qt::NoPen && mPen.brush().style() != Qt::NoBrush )
 
   90      mDxf->
writePolyline( polygon.at( 0 ), mLayer, QStringLiteral( 
"CONTINUOUS" ), penColor(), currentWidth() );
 
   94    if ( mBrush.style() != Qt::NoBrush )
 
   95      mDxf->
writePolygon( polygon, mLayer, QStringLiteral( 
"SOLID" ), brushColor() );
 
 
  101  const int pathLength = path.elementCount();
 
  102  for ( 
int i = 0; i < pathLength; ++i )
 
  104    const QPainterPath::Element &pathElem = path.elementAt( i );
 
  105    if ( pathElem.type == QPainterPath::MoveToElement )
 
  107      moveTo( pathElem.x, pathElem.y );
 
  109    else if ( pathElem.type == QPainterPath::LineToElement )
 
  111      lineTo( pathElem.x, pathElem.y );
 
  113    else if ( pathElem.type == QPainterPath::CurveToElement )
 
  115      curveTo( pathElem.x, pathElem.y );
 
  117    else if ( pathElem.type == QPainterPath::CurveToDataElement )
 
  119      mCurrentCurve.append( QPointF( pathElem.x, pathElem.y ) );
 
  125  if ( !mPolygon.isEmpty() && mBrush.style() != Qt::NoBrush )
 
  126    mDxf->
writePolygon( mPolygon, mLayer, QStringLiteral( 
"SOLID" ), brushColor() );
 
 
  131void QgsDxfPaintEngine::moveTo( 
double dx, 
double dy )
 
  135  mCurrentPolygon.append( QPointF( dx, dy ) );
 
  138void QgsDxfPaintEngine::lineTo( 
double dx, 
double dy )
 
  141  mCurrentPolygon.append( QPointF( dx, dy ) );
 
  144void QgsDxfPaintEngine::curveTo( 
double dx, 
double dy )
 
  147  if ( !mCurrentPolygon.isEmpty() )
 
  148    mCurrentCurve.append( mCurrentPolygon.last() );
 
  150  mCurrentCurve.append( QPointF( dx, dy ) );
 
  153void QgsDxfPaintEngine::endPolygon()
 
  155  if ( mCurrentPolygon.size() > 1 )
 
  157    if ( mPen.style() != Qt::NoPen )
 
  158      drawPolygon( mCurrentPolygon.constData(), mCurrentPolygon.size(), QPaintEngine::PolylineMode );
 
  161    setRing( mPolygon.last(), mCurrentPolygon.constData(), mCurrentPolygon.size() );
 
  163  mCurrentPolygon.clear();
 
  166void QgsDxfPaintEngine::endCurve()
 
  168  if ( mCurrentCurve.empty() )
 
  171  if ( mCurrentPolygon.empty() )
 
  173    mCurrentCurve.clear();
 
  177  if ( mCurrentCurve.size() >= 3 )
 
  180    for ( 
int i = 1; i <= 20; ++i ) 
 
  182      mCurrentPolygon.append( bezierPoint( mCurrentCurve, t ) );
 
  186  else if ( mCurrentCurve.size() == 2 )
 
  188    mCurrentPolygon.append( mCurrentCurve.at( 1 ) );
 
  190  mCurrentCurve.clear();
 
  195  if ( !mDxf || !mPaintDevice || !lines || mPen.style() == Qt::NoPen )
 
  198  for ( 
int i = 0; i < lineCount; ++i )
 
  200    mDxf->
writeLine( toDxfCoordinates( lines[i].p1() ),
 
  201                     toDxfCoordinates( lines[i].p2() ),
 
  202                     mLayer, QStringLiteral( 
"CONTINUOUS" ), penColor(), currentWidth() );
 
 
  206QgsPoint QgsDxfPaintEngine::toDxfCoordinates( QPointF pt )
 const 
  208  if ( !mPaintDevice || !mDxf )
 
  211  const QPointF dxfPt = mPaintDevice->
dxfCoordinates( mTransform.map( pt ) ) + mShift;
 
  212  return QgsPoint( dxfPt.x(), dxfPt.y() );
 
  216double QgsDxfPaintEngine::currentWidth()
 const 
  224QPointF QgsDxfPaintEngine::bezierPoint( 
const QList<QPointF> &controlPolygon, 
double t )
 
  228  const int cPolySize = controlPolygon.size();
 
  231  QList<QPointF>::const_iterator it = controlPolygon.constBegin();
 
  233  for ( ; it != controlPolygon.constEnd(); ++it )
 
  235    bPoly = bernsteinPoly( cPolySize - 1, i, t );
 
  236    x += ( it->x() * bPoly );
 
  237    y += ( it->y() * bPoly );
 
  241  return QPointF( x, y );
 
  244double QgsDxfPaintEngine::bernsteinPoly( 
int n, 
int i, 
double t )
 
  249  return lower( n, i ) * power( t, i ) * power( ( 1 - t ), ( n - i ) );
 
  252int QgsDxfPaintEngine::lower( 
int n, 
int i )
 
  254  if ( i >= 0 && i <= n )
 
  256    return faculty( n ) / ( faculty( i ) * faculty( n - i ) );
 
  264double QgsDxfPaintEngine::power( 
double a, 
int b )
 
  269  const double tmp = a;
 
  270  for ( 
int i = 2; i <= std::abs( b ); i++ )
 
  279int QgsDxfPaintEngine::faculty( 
int n )
 
  287  if ( n == 0 || n == 1 )
 
  290  for ( i = n - 1; i >= 2; i-- )
 
  296QColor QgsDxfPaintEngine::penColor()
 const 
  302  QColor 
c = mPen.color();
 
  303  c.setAlphaF( 
c.alphaF() * mOpacity );
 
  307QColor QgsDxfPaintEngine::brushColor()
 const 
  311    return mBrush.color();
 
  313  QColor 
c = mBrush.color();
 
  314  c.setAlphaF( 
c.alphaF() * mOpacity );
 
Exports QGIS layers to the DXF format.
void writeLine(const QgsPoint &pt1, const QgsPoint &pt2, const QString &layer, const QString &lineStyleName, const QColor &color, double width=-1)
Write line (as a polyline)
void writePolygon(const QgsRingSequence &polygon, const QString &layer, const QString &hatchPattern, const QColor &color)
Draw dxf filled polygon (HATCH)
void writePolyline(const QgsPointSequence &line, const QString &layer, const QString &lineStyleName, const QColor &color, double width=-1)
Draw dxf primitives (LWPOLYLINE)
A paint device for drawing into dxf files.
double widthScaleFactor() const
Returns scale factor for line width.
QPointF dxfCoordinates(QPointF pt) const
Converts a point from device coordinates to dxf coordinates.
void drawPath(const QPainterPath &path) override
bool begin(QPaintDevice *pdev) override
QgsDxfPaintEngine(const QgsDxfPaintDevice *dxfDevice, QgsDxfExport *dxf)
void drawPixmap(const QRectF &r, const QPixmap &pm, const QRectF &sr) override
void updateState(const QPaintEngineState &state) override
void drawLines(const QLineF *lines, int lineCount) override
QPaintEngine::Type type() const override
void drawPolygon(const QPointF *points, int pointCount, PolygonDrawMode mode) override
Point geometry type, with support for z-dimension and m-values.
As part of the API refactoring and improvements which landed in the Processing API was substantially reworked from the x version This was done in order to allow much of the underlying Processing framework to be ported into c
bool qgsDoubleNear(double a, double b, double epsilon=4 *std::numeric_limits< double >::epsilon())
Compare two doubles (but allow some difference)
QVector< QgsPointSequence > QgsRingSequence
QVector< QgsPoint > QgsPointSequence