Add QPlatformIntegration::BackingStoreStaticContents capability

This was a feature in Qt 4, but the only platform that carried it over
to Qt 5 was Windows, in ab76593f18396e693f24066592244ca95e135ea2, and
that's still the situation.

As a first step in possibly implementing this on more platforms, lets
replace the hard-coded check in QWidgetRepaintManager::hasStaticContents
with a proper QPlatformIntegration capability check in the only call site.

Change-Id: I2067109f45116cd8c62facf7224cd748f19e845b
Reviewed-by: Axel Spoerl <axel.spoerl@qt.io>
(cherry picked from commit cce303b6a70bfc5e7f191529724969ca7509039f)
Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
This commit is contained in:
Tor Arne Vestbø 2024-02-11 01:05:06 +01:00 committed by Qt Cherry-pick Bot
parent 6ff8306403
commit fceb53e4c8
7 changed files with 30 additions and 9 deletions

View File

@ -229,6 +229,11 @@ QPlatformServices *QPlatformIntegration::services() const
\value ScreenWindowGrabbing The platform supports grabbing window on screen. \value ScreenWindowGrabbing The platform supports grabbing window on screen.
On Wayland, this capability can be reported as \c false. The default implementation On Wayland, this capability can be reported as \c false. The default implementation
of hasCapability() returns \c true. of hasCapability() returns \c true.
\value BackingStoreStaticContents The platform backingstore supports static contents.
On resize of the backingstore the static contents region is provided, and the backing
store is expected to propagate the static content to the resized backing store, without
clients needing to repaint the static content region.
*/ */
/*! /*!

View File

@ -99,7 +99,8 @@ public:
MaximizeUsingFullscreenGeometry, MaximizeUsingFullscreenGeometry,
PaintEvents, PaintEvents,
RhiBasedRendering, RhiBasedRendering,
ScreenWindowGrabbing // whether QScreen::grabWindow() is supported ScreenWindowGrabbing, // whether QScreen::grabWindow() is supported
BackingStoreStaticContents
}; };
virtual ~QPlatformIntegration() { } virtual ~QPlatformIntegration() { }

View File

@ -267,6 +267,13 @@ bool QBackingStore::scroll(const QRegion &area, int dx, int dy)
*/ */
void QBackingStore::setStaticContents(const QRegion &region) void QBackingStore::setStaticContents(const QRegion &region)
{ {
[[maybe_unused]] static const bool didCheckPlatformSupport = []{
const auto *integration = QGuiApplicationPrivate::platformIntegration();
if (!integration->hasCapability(QPlatformIntegration::BackingStoreStaticContents))
qWarning("QBackingStore::setStaticContents(): Platform does not support static contents");
return true;
}();
d_ptr->staticContents = region; d_ptr->staticContents = region;
} }

View File

@ -286,6 +286,8 @@ bool QWindowsIntegration::hasCapability(QPlatformIntegration::Capability cap) co
return true; return true;
case SwitchableWidgetComposition: case SwitchableWidgetComposition:
return false; // QTBUG-68329 QTBUG-53515 QTBUG-54734 return false; // QTBUG-68329 QTBUG-53515 QTBUG-54734
case BackingStoreStaticContents:
return true;
default: default:
return QPlatformIntegration::hasCapability(cap); return QPlatformIntegration::hasCapability(cap);
} }

View File

@ -706,7 +706,9 @@ void QWidgetRepaintManager::paintAndFlush()
const QRect tlwRect = tlw->data->crect; const QRect tlwRect = tlw->data->crect;
if (!updatesDisabled && store->size() != tlwRect.size()) { if (!updatesDisabled && store->size() != tlwRect.size()) {
if (hasStaticContents() && !store->size().isEmpty() ) { QPlatformIntegration *integration = QGuiApplicationPrivate::platformIntegration();
if (hasStaticContents() && !store->size().isEmpty()
&& integration->hasCapability(QPlatformIntegration::BackingStoreStaticContents)) {
// Repaint existing dirty area and newly visible area. // Repaint existing dirty area and newly visible area.
const QRect clipRect(QPoint(0, 0), store->size()); const QRect clipRect(QPoint(0, 0), store->size());
const QRegion staticRegion(staticContents(nullptr, clipRect)); const QRegion staticRegion(staticContents(nullptr, clipRect));
@ -1140,11 +1142,7 @@ void QWidgetRepaintManager::removeStaticWidget(QWidget *widget)
bool QWidgetRepaintManager::hasStaticContents() const bool QWidgetRepaintManager::hasStaticContents() const
{ {
#if defined(Q_OS_WIN)
return !staticWidgets.isEmpty(); return !staticWidgets.isEmpty();
#else
return !staticWidgets.isEmpty() && false;
#endif
} }
/*! /*!

View File

@ -4,6 +4,8 @@
#include <qwindow.h> #include <qwindow.h>
#include <qbackingstore.h> #include <qbackingstore.h>
#include <qpa/qplatformbackingstore.h> #include <qpa/qplatformbackingstore.h>
#include <qpa/qplatformintegration.h>
#include <private/qguiapplication_p.h>
#include <qpainter.h> #include <qpainter.h>
#include <QTest> #include <QTest>
@ -276,9 +278,9 @@ void tst_QBackingStore::flush()
void tst_QBackingStore::staticContents() void tst_QBackingStore::staticContents()
{ {
#if !defined(Q_OS_WIN) const auto *integration = QGuiApplicationPrivate::platformIntegration();
QSKIP("Platform does not support static backingstore content"); if (!integration->hasCapability(QPlatformIntegration::BackingStoreStaticContents))
#endif QSKIP("Platform does not support static backingstore content");
QWindow window; QWindow window;
window.create(); window.create();

View File

@ -11,7 +11,9 @@
#include <private/qhighdpiscaling_p.h> #include <private/qhighdpiscaling_p.h>
#include <private/qwidget_p.h> #include <private/qwidget_p.h>
#include <private/qwidgetrepaintmanager_p.h> #include <private/qwidgetrepaintmanager_p.h>
#include <qpa/qplatformintegration.h>
#include <qpa/qplatformbackingstore.h> #include <qpa/qplatformbackingstore.h>
#include <private/qguiapplication_p.h>
//#define MANUAL_DEBUG //#define MANUAL_DEBUG
@ -429,6 +431,10 @@ void tst_QWidgetRepaintManager::opaqueChildren()
*/ */
void tst_QWidgetRepaintManager::staticContents() void tst_QWidgetRepaintManager::staticContents()
{ {
const auto *integration = QGuiApplicationPrivate::platformIntegration();
if (!integration->hasCapability(QPlatformIntegration::BackingStoreStaticContents))
QSKIP("Platform does not support static backingstore content");
TestWidget widget; TestWidget widget;
widget.setAttribute(Qt::WA_StaticContents); widget.setAttribute(Qt::WA_StaticContents);
widget.initialShow(); widget.initialShow();