Fixed artifacts when drawing same line with different clips.

Expanding on the change fixing QTBUG-24762 with the realization that any
line needs to be drawn in a consistent way regardless of system or
painter clip, not just dashed lines.

Task-number: QTBUG-25036
Change-Id: Ief7ef19cc92c52e7d792500a581a072ba032767e
Reviewed-by: Gunnar Sletta <gunnar.sletta@digia.com>
This commit is contained in:
Samuel Rødal 2013-03-14 08:51:07 +01:00 committed by The Qt Project
parent 97be79012c
commit c7191d3e21
2 changed files with 53 additions and 17 deletions

View File

@ -290,14 +290,14 @@ void QCosmeticStroker::setup()
ppl = buffer->bytesPerLine()>>2;
}
// dashes are sensitive to clips, so we need to clip consistently when painting to the same device
QRect clipRect = strokeSelection & Dashed ? deviceRect : clip;
// line drawing produces different results with different clips, so
// we need to clip consistently when painting to the same device
// setup FP clip bounds
xmin = clipRect.left() - 1;
xmax = clipRect.right() + 2;
ymin = clipRect.top() - 1;
ymax = clipRect.bottom() + 2;
xmin = deviceRect.left() - 1;
xmax = deviceRect.right() + 2;
ymin = deviceRect.top() - 1;
ymax = deviceRect.bottom() + 2;
lastPixel.x = -1;
}

View File

@ -280,7 +280,9 @@ private slots:
void drawTextWithComplexBrush();
void QTBUG26013_squareCapStroke();
void QTBUG25153_drawLine();
void dashing_systemClip();
void cosmeticStrokerClipping_data();
void cosmeticStrokerClipping();
private:
void fillData();
@ -4462,22 +4464,54 @@ void tst_QPainter::QTBUG25153_drawLine()
}
}
static void dashing_systemClip_paint(QPainter *p)
enum CosmeticStrokerPaint
{
p->setPen(QPen(Qt::black, 1, Qt::DashLine, Qt::RoundCap, Qt::MiterJoin));
p->drawLine(8, 8, 42, 8);
p->drawLine(42, 8, 42, 42);
p->drawLine(42, 42, 8, 42);
p->drawLine(8, 42, 8, 8);
Antialiasing,
Dashing
};
static void paint_func(QPainter *p, CosmeticStrokerPaint type)
{
p->save();
switch (type) {
case Antialiasing:
p->setPen(Qt::black);
p->setRenderHint(QPainter::Antialiasing);
p->drawLine(4, 8, 42, 42);
break;
case Dashing:
p->setPen(QPen(Qt::black, 1, Qt::DashLine, Qt::RoundCap, Qt::MiterJoin));
p->drawLine(8, 8, 42, 8);
p->drawLine(42, 8, 42, 42);
p->drawLine(42, 42, 8, 42);
p->drawLine(8, 42, 8, 8);
break;
default:
Q_ASSERT(false);
break;
}
p->restore();
}
void tst_QPainter::dashing_systemClip()
Q_DECLARE_METATYPE(CosmeticStrokerPaint)
void tst_QPainter::cosmeticStrokerClipping_data()
{
QTest::addColumn<CosmeticStrokerPaint>("paint");
QTest::newRow("antialiasing_paint") << Antialiasing;
QTest::newRow("dashing_paint") << Dashing;
}
void tst_QPainter::cosmeticStrokerClipping()
{
QFETCH(CosmeticStrokerPaint, paint);
QImage image(50, 50, QImage::Format_RGB32);
image.fill(Qt::white);
QPainter p(&image);
dashing_systemClip_paint(&p);
paint_func(&p, paint);
p.end();
QImage old = image.copy();
@ -4485,7 +4519,8 @@ void tst_QPainter::dashing_systemClip()
image.paintEngine()->setSystemClip(QRect(10, 0, image.width() - 10, image.height()));
p.begin(&image);
dashing_systemClip_paint(&p);
p.fillRect(image.rect(), Qt::white);
paint_func(&p, paint);
// doing same paint operation again with different system clip should not change the image
QCOMPARE(old, image);
@ -4493,7 +4528,8 @@ void tst_QPainter::dashing_systemClip()
old = image;
p.setClipRect(QRect(20, 20, 30, 30));
dashing_systemClip_paint(&p);
p.fillRect(image.rect(), Qt::white);
paint_func(&p, paint);
// ditto for regular clips
QCOMPARE(old, image);