From b2504af4da9d3c2c902a5c1221be3c076c4aff86 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Thu, 16 Jul 2020 10:05:18 +0200 Subject: QtGui/Windows: Move the QRegion conversion functions into QtGui MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Task-number: QTBUG-81876 Change-Id: I2297291a4157e7015f499b0a6127301d9cb58526 Reviewed-by: Tor Arne Vestbø --- src/gui/painting/qregion.cpp | 65 ++++++++++++++++++++++++++++++++++++++++++++ src/gui/painting/qregion.h | 6 ++++ 2 files changed, 71 insertions(+) (limited to 'src/gui/painting') diff --git a/src/gui/painting/qregion.cpp b/src/gui/painting/qregion.cpp index a635b66d27..5685d34ea7 100644 --- a/src/gui/painting/qregion.cpp +++ b/src/gui/painting/qregion.cpp @@ -50,6 +50,10 @@ #include +#ifdef Q_OS_WIN +# include +#endif + QT_BEGIN_NAMESPACE /*! @@ -4314,4 +4318,65 @@ bool QRegion::intersects(const QRect &rect) const #endif + +#if defined(Q_OS_WIN) || defined(Q_QDOC) + +static inline HRGN qt_RectToHRGN(const QRect &rc) +{ + return CreateRectRgn(rc.left(), rc.top(), rc.right() + 1, rc.bottom() + 1); +} + +/*! + \since 6.0 + + Returns a HRGN that is equivalent to the given region. +*/ +HRGN QRegion::toHRGN() const +{ + const int size = rectCount(); + if (size == 0) + return nullptr; + + HRGN resultRgn = nullptr; + const auto rects = begin(); + resultRgn = qt_RectToHRGN(rects[0]); + for (int i = 1; i < size; ++i) { + HRGN tmpRgn = qt_RectToHRGN(rects[i]); + int err = CombineRgn(resultRgn, resultRgn, tmpRgn, RGN_OR); + if (err == ERROR) + qWarning("Error combining HRGNs."); + DeleteObject(tmpRgn); + } + return resultRgn; +} + +/*! + \since 6.0 + + Returns a QRegion that is equivalent to the given \a hrgn. + */ +QRegion QRegion::fromHRGN(HRGN hrgn) +{ + DWORD regionDataSize = GetRegionData(hrgn, 0, nullptr); + if (regionDataSize == 0) + return QRegion(); + + auto regionData = reinterpret_cast(malloc(regionDataSize)); + if (!regionData) + return QRegion(); + + QRegion region; + if (GetRegionData(hrgn, regionDataSize, regionData) == regionDataSize) { + auto pRect = reinterpret_cast(regionData->Buffer); + for (DWORD i = 0; i < regionData->rdh.nCount; ++i) + region += QRect(pRect[i].left, pRect[i].top, + pRect[i].right - pRect[i].left, + pRect[i].bottom - pRect[i].top); + } + + free(regionData); + return region; +} +#endif // Q_OS_WIN || Q_QDOC + QT_END_NAMESPACE diff --git a/src/gui/painting/qregion.h b/src/gui/painting/qregion.h index 49174e7510..c4c0164a5b 100644 --- a/src/gui/painting/qregion.h +++ b/src/gui/painting/qregion.h @@ -134,6 +134,12 @@ public: inline bool operator!=(const QRegion &r) const { return !(operator==(r)); } operator QVariant() const; + // Platform specific conversion functions +#if defined(Q_OS_WIN) || defined(Q_QDOC) + HRGN toHRGN() const; + static QRegion fromHRGN(HRGN hrgn); +#endif + #ifndef QT_NO_DATASTREAM friend Q_GUI_EXPORT QDataStream &operator<<(QDataStream &, const QRegion &); friend Q_GUI_EXPORT QDataStream &operator>>(QDataStream &, QRegion &); -- cgit v1.2.3