diff options
author | Samuel Rødal <samuel.rodal@nokia.com> | 2010-09-20 12:54:30 (GMT) |
---|---|---|
committer | Samuli Piippo <samuli.piippo@digia.com> | 2011-06-09 10:06:57 (GMT) |
commit | de8ac0524e7ad9748d6a4f54d5d77bae7a6f3eb0 (patch) | |
tree | 06bc00a7bc541c001e280b0eb3fac07cc97da553 | |
parent | 0a245d03022efbc1664b4f8844e4ff9a1c71b063 (diff) | |
download | Qt-de8ac0524e7ad9748d6a4f54d5d77bae7a6f3eb0.zip Qt-de8ac0524e7ad9748d6a4f54d5d77bae7a6f3eb0.tar.gz Qt-de8ac0524e7ad9748d6a4f54d5d77bae7a6f3eb0.tar.bz2 |
Fixed scaled point drawing with square cap in raster paint engine.
With a large pen width and a small scale, due to the hacky way we draw
points (stroking a line from (x, y) to (x + tiny_amount, y)), we some
times end up snapping these two points to the same in rasterizeLine().
If we instead apply the SquareCap before we do clipping / snapping we
don't get this problem.
Task-number: QTBUG-13429
Reviewed-by: Trond
(cherry picked from commit 7c673a4cf64ba043bb27f90287517bdcdd7a21db)
-rw-r--r-- | src/gui/painting/qrasterizer.cpp | 41 | ||||
-rw-r--r-- | tests/auto/qpainter/tst_qpainter.cpp | 22 |
2 files changed, 39 insertions, 24 deletions
diff --git a/src/gui/painting/qrasterizer.cpp b/src/gui/painting/qrasterizer.cpp index aed9291..fae3e94 100644 --- a/src/gui/painting/qrasterizer.cpp +++ b/src/gui/painting/qrasterizer.cpp @@ -712,17 +712,21 @@ void QRasterizer::rasterizeLine(const QPointF &a, const QPointF &b, qreal width, QPointF pa = a; QPointF pb = b; - QPointF offs = QPointF(qAbs(b.y() - a.y()), qAbs(b.x() - a.x())) * width * 0.5; - if (squareCap) - offs += QPointF(offs.y(), offs.x()); + if (squareCap) { + QPointF delta = pb - pa; + pa -= (0.5f * width) * delta; + pb += (0.5f * width) * delta; + } + + QPointF offs = QPointF(qAbs(b.y() - a.y()), qAbs(b.x() - a.x())) * width * 0.5; const QRectF clip(d->clipRect.topLeft() - offs, d->clipRect.bottomRight() + QPoint(1, 1) + offs); - if (!clip.contains(a) || !clip.contains(b)) { + if (!clip.contains(pa) || !clip.contains(pb)) { qreal t1 = 0; qreal t2 = 1; - const qreal o[2] = { a.x(), a.y() }; - const qreal d[2] = { b.x() - a.x(), b.y() - a.y() }; + const qreal o[2] = { pa.x(), pa.y() }; + const qreal d[2] = { pb.x() - pa.x(), pb.y() - pa.y() }; const qreal low[2] = { clip.left(), clip.top() }; const qreal high[2] = { clip.right(), clip.bottom() }; @@ -745,8 +749,12 @@ void QRasterizer::rasterizeLine(const QPointF &a, const QPointF &b, qreal width, if (t1 >= t2) return; } - pa = a + (b - a) * t1; - pb = a + (b - a) * t2; + + QPointF npa = pa + (pb - pa) * t1; + QPointF npb = pa + (pb - pa) * t2; + + pa = npa; + pb = npb; } if (!d->antialiased) { @@ -793,12 +801,7 @@ void QRasterizer::rasterizeLine(const QPointF &a, const QPointF &b, qreal width, pa = QPointF(x, y - dy); pb = QPointF(x, y + dy); - if (squareCap) - width = 1 / width + 1.0f; - else - width = 1 / width; - - squareCap = false; + width = 1 / width; } if (q16Dot16Compare(pa.x(), pb.x())) { @@ -808,11 +811,6 @@ void QRasterizer::rasterizeLine(const QPointF &a, const QPointF &b, qreal width, const qreal dy = pb.y() - pa.y(); const qreal halfWidth = 0.5f * width * dy; - if (squareCap) { - pa.ry() -= halfWidth; - pb.ry() += halfWidth; - } - qreal left = pa.x() - halfWidth; qreal right = pa.x() + halfWidth; @@ -893,11 +891,6 @@ void QRasterizer::rasterizeLine(const QPointF &a, const QPointF &b, qreal width, delta *= 0.5f * width; const QPointF perp(delta.y(), -delta.x()); - if (squareCap) { - pa -= delta; - pb += delta; - } - QPointF top; QPointF left; QPointF right; diff --git a/tests/auto/qpainter/tst_qpainter.cpp b/tests/auto/qpainter/tst_qpainter.cpp index d453b50..729dd5e 100644 --- a/tests/auto/qpainter/tst_qpainter.cpp +++ b/tests/auto/qpainter/tst_qpainter.cpp @@ -251,6 +251,8 @@ private slots: void QTBUG5939_attachPainterPrivate(); + void drawPointScaled(); + private: void fillData(); void setPenColor(QPainter& p); @@ -4458,6 +4460,26 @@ void tst_QPainter::QTBUG5939_attachPainterPrivate() QCOMPARE(widget->deviceTransform, proxy->deviceTransform); } +void tst_QPainter::drawPointScaled() +{ + QImage image(32, 32, QImage::Format_RGB32); + image.fill(0xffffffff); + + QPainter p(&image); + + p.scale(0.1, 0.1); + + QPen pen; + pen.setWidth(1000); + pen.setColor(Qt::red); + + p.setPen(pen); + p.drawPoint(0, 0); + p.end(); + + QCOMPARE(image.pixel(16, 16), 0xffff0000); +} + QTEST_MAIN(tst_QPainter) #include "tst_qpainter.moc" |