File indexing completed on 2024-12-08 05:08:32
0001 /*************************************************************************** 0002 * Copyright (C) 1999-2005 Trolltech AS * 0003 * Copyright (C) 2006 David Saxton <david@bluehaze.org> * 0004 * * 0005 * This file may be distributed and/or modified under the terms of the * 0006 * GNU General Public License version 2 as published by the Free * 0007 * Software Foundation * 0008 ***************************************************************************/ 0009 0010 #include "canvasitems.h" 0011 #include "canvas.h" 0012 #include "canvas_private.h" 0013 0014 #include <QBrush> 0015 #include <QPainter> 0016 #include <QPainterPath> 0017 #include <QPen> 0018 #include <QPolygon> 0019 #include <QRect> 0020 0021 #include <ktechlab_debug.h> 0022 0023 static bool isCanvasDebugEnabled() 0024 { 0025 return false; 0026 } 0027 0028 KtlQCanvasItem::KtlQCanvasItem(KtlQCanvas *canvas) 0029 : val(false) 0030 , myx(0) 0031 , myy(0) 0032 , myz(0) 0033 , cnv(canvas) 0034 , ext(nullptr) 0035 , m_bNeedRedraw(true) 0036 , vis(false) 0037 , sel(false) 0038 { 0039 if (isCanvasDebugEnabled()) { 0040 qCDebug(KTL_LOG) << " this=" << this; 0041 } 0042 if (cnv) 0043 cnv->addItem(this); 0044 } 0045 0046 KtlQCanvasItem::~KtlQCanvasItem() 0047 { 0048 if (cnv) 0049 cnv->removeItem(this); 0050 delete ext; 0051 } 0052 0053 KtlQCanvasItemExtra &KtlQCanvasItem::extra() 0054 { 0055 if (!ext) 0056 ext = new KtlQCanvasItemExtra; 0057 return *ext; 0058 } 0059 0060 void KtlQCanvasItem::setZ(double a) 0061 { 0062 if (myz == a) 0063 return; 0064 0065 // remove and then add the item so that z-ordered list in canvas is updated 0066 0067 if (cnv) 0068 cnv->removeItem(this); 0069 0070 myz = a; 0071 changeChunks(); 0072 0073 if (cnv) 0074 cnv->addItem(this); 0075 } 0076 0077 void KtlQCanvasItem::moveBy(const double dx, const double dy) 0078 { 0079 if (dx || dy) { 0080 removeFromChunks(); 0081 myx += dx; 0082 myy += dy; 0083 addToChunks(); 0084 } 0085 } 0086 0087 void KtlQCanvasItem::move(const double x, const double y) 0088 { 0089 moveBy(x - myx, y - myy); 0090 } 0091 0092 void KtlQCanvasItem::setCanvas(KtlQCanvas *c) 0093 { 0094 bool v = isVisible(); 0095 setVisible(false); 0096 if (cnv) { 0097 cnv->removeItem(this); 0098 } 0099 0100 cnv = c; 0101 0102 if (cnv) { 0103 cnv->addItem(this); 0104 } 0105 0106 setVisible(v); 0107 } 0108 0109 void KtlQCanvasItem::show() 0110 { 0111 setVisible(true); 0112 } 0113 0114 void KtlQCanvasItem::hide() 0115 { 0116 setVisible(false); 0117 } 0118 0119 void KtlQCanvasItem::setVisible(bool yes) 0120 { 0121 if (vis != yes) { 0122 if (yes) { 0123 vis = uint(yes); 0124 addToChunks(); 0125 } else { 0126 removeFromChunks(); 0127 vis = uint(yes); 0128 } 0129 } 0130 } 0131 0132 void KtlQCanvasItem::setSelected(const bool yes) 0133 { 0134 if (bool(sel) != yes) { 0135 sel = uint(yes); 0136 changeChunks(); 0137 } 0138 } 0139 0140 static bool collision_double_dispatch(const KtlQCanvasPolygonalItem *p1, const KtlQCanvasRectangle *r1, const KtlQCanvasEllipse *e1, const KtlQCanvasPolygonalItem *p2, const KtlQCanvasRectangle *r2, const KtlQCanvasEllipse *e2) 0141 { 0142 const KtlQCanvasItem *i1 = nullptr; 0143 if (p1) { 0144 i1 = p1; 0145 } else { 0146 if (r1) { 0147 i1 = r1; 0148 } else { 0149 i1 = e1; 0150 } 0151 } 0152 const KtlQCanvasItem *i2 = nullptr; 0153 if (i2) { 0154 i2 = p2; 0155 } else { 0156 if (r2) { 0157 i2 = r2; 0158 } else { 0159 i2 = e2; 0160 } 0161 } 0162 // const KtlQCanvasItem* i1 = p1 ? 0163 // (const KtlQCanvasItem*)p1 : r1 ? 0164 // (const KtlQCanvasItem*)r1 : (const KtlQCanvasItem*)e1; 0165 // const KtlQCanvasItem* i2 = p2 ? 0166 // (const KtlQCanvasItem*)p2 : r2 ? 0167 // (const KtlQCanvasItem*)r2 : (const KtlQCanvasItem*)e2; 0168 0169 if (r1 && r2) { 0170 // b 0171 QRect rc1 = i1->boundingRect(); 0172 QRect rc2 = i2->boundingRect(); 0173 return rc1.intersects(rc2); 0174 } else if (e1 && e2 && e1->angleLength() >= 360 * 16 && e2->angleLength() >= 360 * 16 && e1->width() == e1->height() && e2->width() == e2->height()) { 0175 // c 0176 double xd = (e1->x()) - (e2->x()); 0177 double yd = (e1->y()) - (e2->y()); 0178 double rd = (e1->width() + e2->width()) / 2; 0179 return xd * xd + yd * yd <= rd * rd; 0180 } else if (p1 && p2) { 0181 // d 0182 QPolygon pa1 = p1->areaPoints(); 0183 QPolygon pa2 = p2 ? p2->areaPoints() : QPolygon(i2->boundingRect()); 0184 bool col = !(QRegion(pa1) & QRegion(pa2, /* true */ Qt::WindingFill)).isEmpty(); 0185 0186 return col; 0187 } else { 0188 return collision_double_dispatch(p2, r2, e2, p1, r1, e1); 0189 } 0190 } 0191 0192 bool KtlQCanvasPolygonalItem::collidesWith(const KtlQCanvasItem *i) const 0193 { 0194 return i->collidesWith(this, nullptr, nullptr); 0195 } 0196 0197 bool KtlQCanvasPolygonalItem::collidesWith(const KtlQCanvasPolygonalItem *p, const KtlQCanvasRectangle *r, const KtlQCanvasEllipse *e) const 0198 { 0199 return collision_double_dispatch(p, r, e, this, nullptr, nullptr); 0200 } 0201 0202 bool KtlQCanvasRectangle::collidesWith(const KtlQCanvasItem *i) const 0203 { 0204 return i->collidesWith(this, this, nullptr); 0205 } 0206 0207 bool KtlQCanvasRectangle::collidesWith(const KtlQCanvasPolygonalItem *p, const KtlQCanvasRectangle *r, const KtlQCanvasEllipse *e) const 0208 { 0209 return collision_double_dispatch(p, r, e, this, this, nullptr); 0210 } 0211 0212 bool KtlQCanvasEllipse::collidesWith(const KtlQCanvasItem *i) const 0213 { 0214 return i->collidesWith(this, nullptr, this); 0215 } 0216 0217 bool KtlQCanvasEllipse::collidesWith(const KtlQCanvasPolygonalItem *p, const KtlQCanvasRectangle *r, const KtlQCanvasEllipse *e) const 0218 { 0219 return collision_double_dispatch(p, r, e, this, nullptr, this); 0220 } 0221 0222 KtlQCanvasItemList KtlQCanvasItem::collisions(const bool exact) const 0223 { 0224 return canvas()->collisions(chunks(), this, exact); 0225 } 0226 0227 void KtlQCanvasItem::addToChunks() 0228 { 0229 if (isVisible() && canvas()) { 0230 QPolygon pa = chunks(); 0231 for (int i = 0; i < int(pa.count()); i++) 0232 canvas()->addItemToChunk(this, pa[i].x(), pa[i].y()); 0233 val = true; 0234 } 0235 } 0236 0237 void KtlQCanvasItem::removeFromChunks() 0238 { 0239 if (isVisible() && canvas()) { 0240 QPolygon pa = chunks(); 0241 for (int i = 0; i < int(pa.count()); i++) 0242 canvas()->removeItemFromChunk(this, pa[i].x(), pa[i].y()); 0243 } 0244 } 0245 0246 void KtlQCanvasItem::changeChunks() 0247 { 0248 if (isVisible() && canvas()) { 0249 if (!val) 0250 addToChunks(); 0251 QPolygon pa = chunks(); 0252 for (int i = 0; i < int(pa.count()); i++) 0253 canvas()->setChangedChunk(pa[i].x(), pa[i].y()); 0254 } 0255 } 0256 0257 QPolygon KtlQCanvasItem::chunks() const 0258 { 0259 QPolygon r; 0260 int n = 0; 0261 QRect br = boundingRect(); 0262 if (isVisible() && canvas()) { 0263 br &= canvas()->rect(); 0264 if (br.isValid()) { 0265 r.resize((canvas()->toChunkScaling(br.width()) + 2) * (canvas()->toChunkScaling(br.height()) + 2)); 0266 for (int j = canvas()->toChunkScaling(br.top()); j <= canvas()->toChunkScaling(br.bottom()); j++) { 0267 for (int i = canvas()->toChunkScaling(br.left()); i <= canvas()->toChunkScaling(br.right()); i++) { 0268 r[n++] = QPoint(i, j); 0269 } 0270 } 0271 } 0272 } 0273 r.resize(n); 0274 return r; 0275 } 0276 0277 /* 0278 Since most polygonal items don't have a pen, the default is 0279 NoPen and a black brush. 0280 */ 0281 static const QPen &defaultPolygonPen() 0282 { 0283 static QPen *dp = nullptr; 0284 if (!dp) 0285 dp = new QPen; 0286 return *dp; 0287 } 0288 0289 static const QBrush &defaultPolygonBrush() 0290 { 0291 static QBrush *db = nullptr; 0292 if (!db) 0293 db = new QBrush; 0294 return *db; 0295 } 0296 0297 KtlQCanvasPolygonalItem::KtlQCanvasPolygonalItem(KtlQCanvas *canvas) 0298 : KtlQCanvasItem(canvas) 0299 , br(defaultPolygonBrush()) 0300 , pn(defaultPolygonPen()) 0301 , wind(false) 0302 { 0303 if (isCanvasDebugEnabled()) { 0304 qCDebug(KTL_LOG) << "created KtlQCanvasPolygonalItem at " << this; 0305 } 0306 } 0307 0308 KtlQCanvasPolygonalItem::~KtlQCanvasPolygonalItem() 0309 { 0310 if (isCanvasDebugEnabled()) { 0311 qCDebug(KTL_LOG) << "destroying KtlQCanvasPolygonalItem at " << this; 0312 } 0313 } 0314 0315 bool KtlQCanvasPolygonalItem::winding() const 0316 { 0317 return wind; 0318 } 0319 0320 void KtlQCanvasPolygonalItem::setWinding(bool enable) 0321 { 0322 wind = enable; 0323 } 0324 0325 void KtlQCanvasPolygonalItem::invalidate() 0326 { 0327 val = false; 0328 removeFromChunks(); 0329 } 0330 0331 QPolygon KtlQCanvasPolygonalItem::chunks() const 0332 { 0333 QPolygon pa = areaPoints(); 0334 0335 if (!pa.size()) { 0336 pa.detach(); // Explicit sharing is stupid. 0337 return pa; 0338 } 0339 0340 KtlQPolygonalProcessor processor(canvas(), pa); 0341 0342 scanPolygon(pa, wind, processor); 0343 0344 return processor.result; 0345 } 0346 0347 QPolygon KtlQCanvasRectangle::chunks() const 0348 { 0349 // No need to do a polygon scan! 0350 return KtlQCanvasItem::chunks(); 0351 } 0352 0353 QRect KtlQCanvasPolygonalItem::boundingRect() const 0354 { 0355 return areaPoints().boundingRect(); 0356 } 0357 0358 void KtlQCanvasPolygonalItem::draw(QPainter &p) 0359 { 0360 p.setPen(pn); 0361 p.setBrush(br); 0362 drawShape(p); 0363 } 0364 0365 void KtlQCanvasPolygonalItem::setPen(const QPen &p) 0366 { 0367 if (pn == p) 0368 return; 0369 0370 pn.setColor(p.color()); 0371 0372 // if only the color was different, then don't need to re-add to chunks 0373 if (pn == p) { 0374 changeChunks(); 0375 } else { 0376 // Have to re-add to chunks as e.g. pen width might have changed 0377 removeFromChunks(); 0378 pn = p; 0379 addToChunks(); 0380 } 0381 } 0382 0383 void KtlQCanvasPolygonalItem::setBrush(const QBrush &b) 0384 { 0385 if (br != b) { 0386 br = b; 0387 changeChunks(); 0388 } 0389 } 0390 0391 KtlQCanvasPolygon::KtlQCanvasPolygon(KtlQCanvas *canvas) 0392 : KtlQCanvasPolygonalItem(canvas) 0393 , guardBef() 0394 , poly(new QPolygon) 0395 , guardAft() 0396 { 0397 if (isCanvasDebugEnabled()) { 0398 qCDebug(KTL_LOG) << " this=" << this; 0399 } 0400 } 0401 0402 KtlQCanvasPolygon::~KtlQCanvasPolygon() 0403 { 0404 hide(); 0405 delete poly; 0406 } 0407 0408 void KtlQCanvasPolygon::drawShape(QPainter &p) 0409 { 0410 // ### why can't we draw outlines? We could use drawPolyline for it. Lars 0411 // ### see other message. Warwick 0412 0413 p.setPen(Qt::NoPen); // since QRegion(QPolygon) excludes outline :-( )-: 0414 p.drawPolygon(*poly); 0415 } 0416 0417 void KtlQCanvasPolygon::setPoints(QPolygon pa) 0418 { 0419 removeFromChunks(); 0420 *poly = pa; 0421 poly->detach(); // Explicit sharing is stupid. 0422 poly->translate(int(x()), int(y())); 0423 addToChunks(); 0424 } 0425 0426 void KtlQCanvasPolygon::moveBy(double dx, double dy) 0427 { 0428 // Note: does NOT call KtlQCanvasPolygonalItem::moveBy(), since that 0429 // only does half this work. 0430 // 0431 int idx = int(x() + dx) - int(x()); 0432 int idy = int(y() + dy) - int(y()); 0433 if (idx || idy) { 0434 removeFromChunks(); 0435 poly->translate(idx, idy); 0436 } 0437 myx += dx; 0438 myy += dy; 0439 if (idx || idy) { 0440 addToChunks(); 0441 } 0442 } 0443 0444 QPolygon KtlQCanvasPolygon::points() const 0445 { 0446 QPolygon pa = areaPoints(); 0447 pa.translate(int(-x()), int(-y())); 0448 return pa; 0449 } 0450 0451 QPolygon KtlQCanvasPolygon::areaPoints() const 0452 { 0453 return QPolygon(*poly); // ->copy(); // 2018.06.02 - copy is only in QPolygon 0454 } 0455 0456 // ### mark: Why don't we offer a constructor that lets the user set the 0457 // points -- that way for some uses just the constructor call would be 0458 // required? 0459 0460 KtlQCanvasLine::KtlQCanvasLine(KtlQCanvas *canvas) 0461 : KtlQCanvasPolygonalItem(canvas) 0462 { 0463 if (isCanvasDebugEnabled()) { 0464 qCDebug(KTL_LOG) << " this=" << this; 0465 } 0466 x1 = y1 = x2 = y2 = 0; 0467 } 0468 0469 KtlQCanvasLine::~KtlQCanvasLine() 0470 { 0471 hide(); 0472 } 0473 0474 void KtlQCanvasLine::setPen(const QPen &p) 0475 { 0476 KtlQCanvasPolygonalItem::setPen(p); 0477 } 0478 0479 void KtlQCanvasLine::setPoints(int xa, int ya, int xb, int yb) 0480 { 0481 if (x1 != xa || x2 != xb || y1 != ya || y2 != yb) { 0482 removeFromChunks(); 0483 x1 = xa; 0484 y1 = ya; 0485 x2 = xb; 0486 y2 = yb; 0487 addToChunks(); 0488 } 0489 } 0490 0491 void KtlQCanvasLine::drawShape(QPainter &p) 0492 { 0493 p.drawLine(int(x() + x1), int(y() + y1), int(x() + x2), int(y() + y2)); 0494 } 0495 0496 QPolygon KtlQCanvasLine::areaPoints() const 0497 { 0498 QPolygon p(4); 0499 int xi = int(x()); 0500 int yi = int(y()); 0501 int pw = pen().width(); 0502 int dx = abs(x1 - x2); 0503 int dy = abs(y1 - y2); 0504 pw = pw * 4 / 3 + 2; // approx pw*sqrt(2) 0505 int px = x1 < x2 ? -pw : pw; 0506 int py = y1 < y2 ? -pw : pw; 0507 if (dx && dy && (dx > dy ? (dx * 2 / dy <= 2) : (dy * 2 / dx <= 2))) { 0508 // steep 0509 if (px == py) { 0510 p[0] = QPoint(x1 + xi, y1 + yi + py); 0511 p[1] = QPoint(x2 + xi - px, y2 + yi); 0512 p[2] = QPoint(x2 + xi, y2 + yi - py); 0513 p[3] = QPoint(x1 + xi + px, y1 + yi); 0514 } else { 0515 p[0] = QPoint(x1 + xi + px, y1 + yi); 0516 p[1] = QPoint(x2 + xi, y2 + yi - py); 0517 p[2] = QPoint(x2 + xi - px, y2 + yi); 0518 p[3] = QPoint(x1 + xi, y1 + yi + py); 0519 } 0520 } else if (dx > dy) { 0521 // horizontal 0522 p[0] = QPoint(x1 + xi + px, y1 + yi + py); 0523 p[1] = QPoint(x2 + xi - px, y2 + yi + py); 0524 p[2] = QPoint(x2 + xi - px, y2 + yi - py); 0525 p[3] = QPoint(x1 + xi + px, y1 + yi - py); 0526 } else { 0527 // vertical 0528 p[0] = QPoint(x1 + xi + px, y1 + yi + py); 0529 p[1] = QPoint(x2 + xi + px, y2 + yi - py); 0530 p[2] = QPoint(x2 + xi - px, y2 + yi - py); 0531 p[3] = QPoint(x1 + xi - px, y1 + yi + py); 0532 } 0533 return p; 0534 } 0535 0536 void KtlQCanvasLine::moveBy(double dx, double dy) 0537 { 0538 KtlQCanvasPolygonalItem::moveBy(dx, dy); 0539 } 0540 0541 KtlQCanvasRectangle::KtlQCanvasRectangle(KtlQCanvas *canvas) 0542 : KtlQCanvasPolygonalItem(canvas) 0543 , w(32) 0544 , h(32) 0545 { 0546 setObjectName("KtlQCanvasRectangle"); 0547 if (isCanvasDebugEnabled()) { 0548 qCDebug(KTL_LOG) << " this=" << this; 0549 } 0550 } 0551 0552 KtlQCanvasRectangle::KtlQCanvasRectangle(const QRect &r, KtlQCanvas *canvas) 0553 : KtlQCanvasPolygonalItem(canvas) 0554 , w(r.width()) 0555 , h(r.height()) 0556 { 0557 setObjectName("KtlQCanvasRectangle"); 0558 move(r.x(), r.y()); 0559 if (isCanvasDebugEnabled()) { 0560 qCDebug(KTL_LOG) << " this=" << this; 0561 } 0562 } 0563 0564 KtlQCanvasRectangle::KtlQCanvasRectangle(int x, int y, int width, int height, KtlQCanvas *canvas) 0565 : KtlQCanvasPolygonalItem(canvas) 0566 , w(width) 0567 , h(height) 0568 { 0569 setObjectName("KtlQCanvasRectangle"); 0570 move(x, y); 0571 if (isCanvasDebugEnabled()) { 0572 qCDebug(KTL_LOG) << " this=" << this; 0573 } 0574 } 0575 0576 KtlQCanvasRectangle::~KtlQCanvasRectangle() 0577 { 0578 hide(); 0579 } 0580 0581 int KtlQCanvasRectangle::width() const 0582 { 0583 return w; 0584 } 0585 0586 int KtlQCanvasRectangle::height() const 0587 { 0588 return h; 0589 } 0590 0591 void KtlQCanvasRectangle::setSize(const int width, const int height) 0592 { 0593 if (w != width || h != height) { 0594 removeFromChunks(); 0595 w = width; 0596 h = height; 0597 addToChunks(); 0598 } 0599 } 0600 0601 QPolygon KtlQCanvasRectangle::areaPoints() const 0602 { 0603 QPolygon pa(4); 0604 int pw = (pen().width() + 1) / 2; 0605 if (pw < 1) 0606 pw = 1; 0607 if (pen() == Qt::NoPen) 0608 pw = 0; 0609 pa[0] = QPoint(int(x()) - pw, int(y()) - pw); 0610 pa[1] = pa[0] + QPoint(w + pw * 2, 0); 0611 pa[2] = pa[1] + QPoint(0, h + pw * 2); 0612 pa[3] = pa[0] + QPoint(0, h + pw * 2); 0613 return pa; 0614 } 0615 0616 void KtlQCanvasRectangle::drawShape(QPainter &p) 0617 { 0618 p.drawRect(int(x()), int(y()), w, h); 0619 } 0620 0621 KtlQCanvasEllipse::KtlQCanvasEllipse(KtlQCanvas *canvas) 0622 : KtlQCanvasPolygonalItem(canvas) 0623 , w(32) 0624 , h(32) 0625 , a1(0) 0626 , a2(360 * 16) 0627 { 0628 if (isCanvasDebugEnabled()) { 0629 qCDebug(KTL_LOG) << " this=" << this; 0630 } 0631 } 0632 0633 /*! 0634 Constructs a \a width by \a height pixel ellipse, centered at 0635 (0, 0) on \a canvas. 0636 */ 0637 KtlQCanvasEllipse::KtlQCanvasEllipse(int width, int height, KtlQCanvas *canvas) 0638 : KtlQCanvasPolygonalItem(canvas) 0639 , w(width) 0640 , h(height) 0641 , a1(0) 0642 , a2(360 * 16) 0643 { 0644 if (isCanvasDebugEnabled()) { 0645 qCDebug(KTL_LOG) << " this=" << this; 0646 } 0647 } 0648 0649 KtlQCanvasEllipse::KtlQCanvasEllipse(int width, int height, int startangle, int angle, KtlQCanvas *canvas) 0650 : KtlQCanvasPolygonalItem(canvas) 0651 , w(width) 0652 , h(height) 0653 , a1(startangle) 0654 , a2(angle) 0655 { 0656 if (isCanvasDebugEnabled()) { 0657 qCDebug(KTL_LOG) << " this=" << this; 0658 } 0659 } 0660 0661 KtlQCanvasEllipse::~KtlQCanvasEllipse() 0662 { 0663 hide(); 0664 } 0665 0666 int KtlQCanvasEllipse::width() const 0667 { 0668 return w; 0669 } 0670 0671 int KtlQCanvasEllipse::height() const 0672 { 0673 return h; 0674 } 0675 0676 void KtlQCanvasEllipse::setSize(int width, int height) 0677 { 0678 if (w != width || h != height) { 0679 removeFromChunks(); 0680 w = width; 0681 h = height; 0682 addToChunks(); 0683 } 0684 } 0685 0686 void KtlQCanvasEllipse::setAngles(int start, int length) 0687 { 0688 if (a1 != start || a2 != length) { 0689 removeFromChunks(); 0690 a1 = start; 0691 a2 = length; 0692 addToChunks(); 0693 } 0694 } 0695 0696 QPolygon KtlQCanvasEllipse::areaPoints() const 0697 { 0698 // Q3PointArray r; // 2018.08.14 - see below 0699 // // makeArc at 0,0, then translate so that fixed point math doesn't overflow 0700 // r.makeArc(int(x()-w/2.0+0.5)-1, int(y()-h/2.0+0.5)-1, w+3, h+3, a1, a2); 0701 0702 QPainterPath path; 0703 path.arcTo(int(x() - w / 2.0 + 0.5) - 1, int(y() - h / 2.0 + 0.5) - 1, w + 3, h + 3, a1, a2 - a1); 0704 QPolygon r = path.toFillPolygon().toPolygon(); 0705 0706 r.resize(r.size() + 1); 0707 r.setPoint(r.size() - 1, int(x()), int(y())); 0708 return QPolygon(r); 0709 } 0710 0711 void KtlQCanvasEllipse::drawShape(QPainter &p) 0712 { 0713 p.setPen(Qt::NoPen); // since QRegion(QPolygon) excludes outline :-( )-: 0714 if (!a1 && a2 == 360 * 16) { 0715 p.drawEllipse(int(x() - w / 2.0 + 0.5), int(y() - h / 2.0 + 0.5), w, h); 0716 } else { 0717 p.drawPie(int(x() - w / 2.0 + 0.5), int(y() - h / 2.0 + 0.5), w, h, a1, a2); 0718 } 0719 } 0720 0721 void KtlQCanvasPolygonalItem::scanPolygon(const QPolygon &pa, int winding, KtlQPolygonalProcessor &process) const 0722 { 0723 KtlQCanvasPolygonScanner scanner(process); 0724 scanner.scan(pa, winding); 0725 } 0726 0727 #include "moc_canvasitems.cpp"