summaryrefslogtreecommitdiffstats
path: root/src/plugins/platforms/ios/qiosscreen.mm
diff options
context:
space:
mode:
Diffstat (limited to 'src/plugins/platforms/ios/qiosscreen.mm')
-rw-r--r--src/plugins/platforms/ios/qiosscreen.mm138
1 files changed, 62 insertions, 76 deletions
diff --git a/src/plugins/platforms/ios/qiosscreen.mm b/src/plugins/platforms/ios/qiosscreen.mm
index 80636ab9c6..e48592aa24 100644
--- a/src/plugins/platforms/ios/qiosscreen.mm
+++ b/src/plugins/platforms/ios/qiosscreen.mm
@@ -1,41 +1,7 @@
-/****************************************************************************
-**
-** Copyright (C) 2016 The Qt Company Ltd.
-** Contact: https://www.qt.io/licensing/
-**
-** This file is part of the plugins of the Qt Toolkit.
-**
-** $QT_BEGIN_LICENSE:LGPL$
-** Commercial License Usage
-** Licensees holding valid commercial Qt licenses may use this file in
-** accordance with the commercial license agreement provided with the
-** Software or, alternatively, in accordance with the terms contained in
-** a written agreement between you and The Qt Company. For licensing terms
-** and conditions see https://www.qt.io/terms-conditions. For further
-** information use the contact form at https://www.qt.io/contact-us.
-**
-** GNU Lesser General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU Lesser
-** General Public License version 3 as published by the Free Software
-** Foundation and appearing in the file LICENSE.LGPL3 included in the
-** packaging of this file. Please review the following information to
-** ensure the GNU Lesser General Public License version 3 requirements
-** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
-**
-** GNU General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU
-** General Public License version 2.0 or (at your option) the GNU General
-** Public license version 3 or any later version approved by the KDE Free
-** Qt Foundation. The licenses are as published by the Free Software
-** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
-** included in the packaging of this file. Please review the following
-** information to ensure the GNU General Public License requirements will
-** be met: https://www.gnu.org/licenses/gpl-2.0.html and
-** https://www.gnu.org/licenses/gpl-3.0.html.
-**
-** $QT_END_LICENSE$
-**
-****************************************************************************/
+// Copyright (C) 2016 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
+
+#undef QT_NO_FOREACH // this file contains unported legacy Q_FOREACH uses
#include "qiosglobal.h"
#include "qiosintegration.h"
@@ -51,6 +17,7 @@
#include <QtGui/qpointingdevice.h>
#include <QtGui/private/qwindow_p.h>
+#include <QtGui/private/qguiapplication_p.h>
#include <private/qcoregraphics_p.h>
#include <qpa/qwindowsysteminterface.h>
@@ -108,14 +75,17 @@ static QIOSScreen* qtPlatformScreenFor(UIScreen *uiScreen)
+ (void)screenConnected:(NSNotification*)notification
{
- Q_ASSERT_X(QIOSIntegration::instance(), Q_FUNC_INFO,
- "Screen connected before QIOSIntegration creation");
+ if (!QIOSIntegration::instance())
+ return; // Will be added when QIOSIntegration is created
QWindowSystemInterface::handleScreenAdded(new QIOSScreen([notification object]));
}
+ (void)screenDisconnected:(NSNotification*)notification
{
+ if (!QIOSIntegration::instance())
+ return;
+
QIOSScreen *screen = qtPlatformScreenFor([notification object]);
Q_ASSERT_X(screen, Q_FUNC_INFO, "Screen disconnected that we didn't know about");
@@ -124,6 +94,9 @@ static QIOSScreen* qtPlatformScreenFor(UIScreen *uiScreen)
+ (void)screenModeChanged:(NSNotification*)notification
{
+ if (!QIOSIntegration::instance())
+ return;
+
QIOSScreen *screen = qtPlatformScreenFor([notification object]);
Q_ASSERT_X(screen, Q_FUNC_INFO, "Screen changed that we didn't know about");
@@ -176,21 +149,6 @@ static QIOSScreen* qtPlatformScreenFor(UIScreen *uiScreen)
@end
-@interface UIScreen (Compatibility)
-@property (nonatomic, readonly) CGRect qt_applicationFrame;
-@end
-
-@implementation UIScreen (Compatibility)
-- (CGRect)qt_applicationFrame
-{
-#ifdef Q_OS_IOS
- return self.applicationFrame;
-#else
- return self.bounds;
-#endif
-}
-@end
-
// -------------------------------------------------------------------------
@implementation QUIWindow
@@ -213,10 +171,21 @@ static QIOSScreen* qtPlatformScreenFor(UIScreen *uiScreen)
{
[super traitCollectionDidChange:previousTraitCollection];
+ if (!qGuiApp)
+ return;
+
+ Qt::ColorScheme colorScheme = self.traitCollection.userInterfaceStyle
+ == UIUserInterfaceStyleDark
+ ? Qt::ColorScheme::Dark
+ : Qt::ColorScheme::Light;
+
if (self.screen == UIScreen.mainScreen) {
- if (previousTraitCollection.userInterfaceStyle != self.traitCollection.userInterfaceStyle) {
+ // Check if the current userInterfaceStyle reports a different appearance than
+ // the platformTheme's appearance. We might have set that one based on the UIScreen
+ if (previousTraitCollection.userInterfaceStyle != self.traitCollection.userInterfaceStyle
+ || QGuiApplicationPrivate::platformTheme()->colorScheme() != colorScheme) {
QIOSTheme::initializeSystemPalette();
- QWindowSystemInterface::handleThemeChange<QWindowSystemInterface::SynchronousDelivery>(nullptr);
+ QWindowSystemInterface::handleThemeChange<QWindowSystemInterface::SynchronousDelivery>();
}
}
}
@@ -227,6 +196,8 @@ static QIOSScreen* qtPlatformScreenFor(UIScreen *uiScreen)
QT_BEGIN_NAMESPACE
+using namespace Qt::StringLiterals;
+
/*!
Returns the model identifier of the device.
*/
@@ -243,7 +214,7 @@ static QString deviceModelIdentifier()
char value[size];
sysctlbyname(key, &value, &size, NULL, 0);
- return QString::fromLatin1(value);
+ return QString::fromLatin1(QByteArrayView(value, qsizetype(size)));
#endif
}
@@ -288,7 +259,7 @@ QIOSScreen::QIOSScreen(UIScreen *screen)
if (!qt_apple_isApplicationExtension()) {
for (UIWindow *existingWindow in qt_apple_sharedApplication().windows) {
if (existingWindow.screen == m_uiScreen) {
- m_uiWindow = [m_uiWindow retain];
+ m_uiWindow = [existingWindow retain];
break;
}
}
@@ -319,12 +290,19 @@ QIOSScreen::~QIOSScreen()
QString QIOSScreen::name() const
{
- if (m_uiScreen == [UIScreen mainScreen]) {
- return QString::fromNSString([UIDevice currentDevice].model)
- + QLatin1String(" built-in display");
- } else {
- return QLatin1String("External display");
- }
+ if (m_uiScreen == [UIScreen mainScreen])
+ return QString::fromNSString([UIDevice currentDevice].model) + " built-in display"_L1;
+ else
+ return "External display"_L1;
+}
+
+static bool isRunningOnVisionOS()
+{
+ static bool result = []{
+ // This class is documented to only be available on visionOS
+ return NSClassFromString(@"UIWindowSceneGeometryPreferencesVision");
+ }();
+ return result;
}
void QIOSScreen::updateProperties()
@@ -334,14 +312,22 @@ void QIOSScreen::updateProperties()
m_geometry = QRectF::fromCGRect(m_uiScreen.bounds).toRect();
- // The application frame doesn't take safe area insets into account, and
- // the safe area insets are not available before the UIWindow is shown,
- // and do not take split-view constraints into account, so we have to
- // combine the two to get the correct available geometry.
- QRect applicationFrame = QRectF::fromCGRect(m_uiScreen.qt_applicationFrame).toRect();
- UIEdgeInsets safeAreaInsets = m_uiWindow.qt_safeAreaInsets;
- m_availableGeometry = m_geometry.adjusted(safeAreaInsets.left, safeAreaInsets.top,
- -safeAreaInsets.right, -safeAreaInsets.bottom).intersected(applicationFrame);
+ m_availableGeometry = m_geometry;
+
+ // For convenience, we reflect the safe area margins of the screen's UIWindow
+ // by reducing the available geometry of the screen. But we only do this if
+ // the UIWindow bounds is representative of the UIScreen.
+ if (isRunningOnVisionOS()) {
+ // On visionOS there is no concept of a screen, and hence no concept of
+ // screen-relative system UI that we should keep top level windows away
+ // from, so don't apply the UIWindow safe area insets to the screen.
+ } else {
+ UIEdgeInsets safeAreaInsets = m_uiWindow.safeAreaInsets;
+ if (m_uiWindow.bounds.size.width == m_uiScreen.bounds.size.width)
+ m_availableGeometry.adjust(safeAreaInsets.left, 0, -safeAreaInsets.right, 0);
+ if (m_uiWindow.bounds.size.height == m_uiScreen.bounds.size.height)
+ m_availableGeometry.adjust(0, safeAreaInsets.top, 0, -safeAreaInsets.bottom);
+ }
#ifndef Q_OS_TVOS
if (m_uiScreen == [UIScreen mainScreen]) {
@@ -460,7 +446,7 @@ QSizeF QIOSScreen::physicalSize() const
return m_physicalSize;
}
-QDpi QIOSScreen::logicalDpi() const
+QDpi QIOSScreen::logicalBaseDpi() const
{
return QDpi(72, 72);
}
@@ -564,6 +550,6 @@ UIWindow *QIOSScreen::uiWindow() const
return m_uiWindow;
}
-#include "moc_qiosscreen.cpp"
-
QT_END_NAMESPACE
+
+#include "moc_qiosscreen.cpp"