summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/gui/kernel/qguiapplication.cpp63
-rw-r--r--src/gui/kernel/qguiapplication.h2
-rw-r--r--src/widgets/kernel/qdesktopwidget.cpp22
3 files changed, 36 insertions, 51 deletions
diff --git a/src/gui/kernel/qguiapplication.cpp b/src/gui/kernel/qguiapplication.cpp
index a29ddbe44e..63539c0103 100644
--- a/src/gui/kernel/qguiapplication.cpp
+++ b/src/gui/kernel/qguiapplication.cpp
@@ -988,6 +988,34 @@ QList<QScreen *> QGuiApplication::screens()
}
/*!
+ Returns the screen at \a point, or \c nullptr if outside of any screen.
+
+ The \a point is in relation to the virtualGeometry() of each set of virtual
+ siblings. If the point maps to more than one set of virtual siblings the first
+ match is returned.
+
+ \since 5.10
+*/
+QScreen *QGuiApplication::screenAt(const QPoint &point)
+{
+ QVarLengthArray<const QScreen *, 8> visitedScreens;
+ for (const QScreen *screen : QGuiApplication::screens()) {
+ if (visitedScreens.contains(screen))
+ continue;
+
+ // The virtual siblings include the screen itself, so iterate directly
+ for (QScreen *sibling : screen->virtualSiblings()) {
+ if (sibling->geometry().contains(point))
+ return sibling;
+
+ visitedScreens.append(sibling);
+ }
+ }
+
+ return nullptr;
+}
+
+/*!
\fn void QGuiApplication::screenAdded(QScreen *screen)
This signal is emitted whenever a new screen \a screen has been added to the system.
@@ -1050,38 +1078,11 @@ qreal QGuiApplication::devicePixelRatio() const
*/
QWindow *QGuiApplication::topLevelAt(const QPoint &pos)
{
- const QList<QScreen *> screens = QGuiApplication::screens();
- if (!screens.isEmpty()) {
- const QList<QScreen *> primaryScreens = screens.first()->virtualSiblings();
- QScreen *windowScreen = Q_NULLPTR;
-
- // Find the window on the primary virtual desktop first
- for (QScreen *screen : primaryScreens) {
- if (screen->geometry().contains(pos)) {
- windowScreen = screen;
- break;
- }
- }
-
- // If the window is not found on primary virtual desktop, find it on all screens
- // except the first which was for sure in the previous loop. Some other screens
- // may repeat. Find only when there is more than one virtual desktop.
- if (!windowScreen && screens.count() != primaryScreens.count()) {
- for (int i = 1; i < screens.size(); ++i) {
- QScreen *screen = screens.at(i);
- if (screen->geometry().contains(pos)) {
- windowScreen = screen;
- break;
- }
- }
- }
-
- if (windowScreen) {
- const QPoint devicePosition = QHighDpi::toNativePixels(pos, windowScreen);
- return windowScreen->handle()->topLevelAt(devicePosition);
- }
+ if (QScreen *windowScreen = screenAt(pos)) {
+ const QPoint devicePosition = QHighDpi::toNativePixels(pos, windowScreen);
+ return windowScreen->handle()->topLevelAt(devicePosition);
}
- return Q_NULLPTR;
+ return nullptr;
}
/*!
diff --git a/src/gui/kernel/qguiapplication.h b/src/gui/kernel/qguiapplication.h
index 6721970222..e130553b9d 100644
--- a/src/gui/kernel/qguiapplication.h
+++ b/src/gui/kernel/qguiapplication.h
@@ -110,6 +110,8 @@ public:
static QScreen *primaryScreen();
static QList<QScreen *> screens();
+ static QScreen *screenAt(const QPoint &point);
+
qreal devicePixelRatio() const;
#ifndef QT_NO_CURSOR
diff --git a/src/widgets/kernel/qdesktopwidget.cpp b/src/widgets/kernel/qdesktopwidget.cpp
index 6077ac38db..1b9cf88efe 100644
--- a/src/widgets/kernel/qdesktopwidget.cpp
+++ b/src/widgets/kernel/qdesktopwidget.cpp
@@ -352,26 +352,8 @@ int QDesktopWidget::screenNumber(const QPoint &p) const
int QDesktopWidgetPrivate::screenNumber(const QPoint &p)
{
- const QList<QScreen *> screens = QGuiApplication::screens();
- if (!screens.isEmpty()) {
- const QList<QScreen *> primaryScreens = screens.first()->virtualSiblings();
- // Find the screen index on the primary virtual desktop first
- foreach (QScreen *screen, primaryScreens) {
- if (screen->geometry().contains(p))
- return screens.indexOf(screen);
- }
- // If the screen index is not found on primary virtual desktop, find
- // the screen index on all screens except the first which was for
- // sure in the previous loop. Some other screens may repeat. Find
- // only when there is more than one virtual desktop.
- if (screens.count() != primaryScreens.count()) {
- for (int i = 1; i < screens.size(); ++i) {
- if (screens[i]->geometry().contains(p))
- return i;
- }
- }
- }
- return primaryScreen(); //even better would be closest screen
+ QScreen *screen = QGuiApplication::screenAt(p);
+ return screen ? QGuiApplication::screens().indexOf(screen) : primaryScreen();
}
void QDesktopWidget::resizeEvent(QResizeEvent *)