Improve QRectF::toRect()

Implement the better rounding mechanism that was previously blocked
by requiring C++14 to be constexpr.

Change-Id: I4e5b179ce0703f5c0b41c3f0ea00d28dfe53740c
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Lars Knoll <lars.knoll@qt.io>
bb10
Allan Sandfeld Jensen 2020-06-24 13:38:42 +02:00
parent 927813fc95
commit a0deaf42e2
2 changed files with 14 additions and 7 deletions

View File

@ -874,7 +874,14 @@ constexpr inline bool operator!=(const QRectF &r1, const QRectF &r2) noexcept
constexpr inline QRect QRectF::toRect() const noexcept
{
return QRect(QPoint(qRound(xp), qRound(yp)), QPoint(qRound(xp + w) - 1, qRound(yp + h) - 1));
// This rounding is designed to minimize the maximum possible difference
// in topLeft(), bottomRight(), and size() after rounding.
// All dimensions are at most off by 0.75, and topLeft by at most 0.5.
const int nxp = qRound(xp);
const int nyp = qRound(yp);
const int nw = qRound(w + (xp - nxp)/2);
const int nh = qRound(h + (yp - nyp)/2);
return QRect(nxp, nyp, nw, nh);
}
constexpr inline QRectF operator+(const QRectF &lhs, const QMarginsF &rhs) noexcept

View File

@ -4373,12 +4373,12 @@ void tst_QRect::toRect()
for (qreal h = 1.0; h < 2.0; h += 0.25) {
const QRectF rectf(x, y, w, h);
const QRectF rect = rectf.toRect();
QVERIFY(qAbs(rect.x() - rectf.x()) < 1.0);
QVERIFY(qAbs(rect.y() - rectf.y()) < 1.0);
QVERIFY(qAbs(rect.width() - rectf.width()) < 1.0);
QVERIFY(qAbs(rect.height() - rectf.height()) < 1.0);
QVERIFY(qAbs(rect.right() - rectf.right()) < 1.0);
QVERIFY(qAbs(rect.bottom() - rectf.bottom()) < 1.0);
QVERIFY(qAbs(rect.x() - rectf.x()) <= 0.75);
QVERIFY(qAbs(rect.y() - rectf.y()) <= 0.75);
QVERIFY(qAbs(rect.width() - rectf.width()) <= 0.75);
QVERIFY(qAbs(rect.height() - rectf.height()) <= 0.75);
QVERIFY(qAbs(rect.right() - rectf.right()) <= 0.75);
QVERIFY(qAbs(rect.bottom() - rectf.bottom()) <= 0.75);
const QRectF arect = rectf.toAlignedRect();
QVERIFY(qAbs(arect.x() - rectf.x()) < 1.0);