summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/gui/CMakeLists.txt2
-rw-r--r--src/gui/kernel/qshortcutmap.cpp43
-rw-r--r--src/gui/kernel/qshortcutmap_p.h1
-rw-r--r--src/gui/platform/darwin/qapplekeymapper.mm (renamed from src/plugins/platforms/cocoa/qcocoakeymapper.mm)128
-rw-r--r--src/gui/platform/darwin/qapplekeymapper_p.h (renamed from src/plugins/platforms/cocoa/qcocoakeymapper.h)22
-rw-r--r--src/plugins/platforms/cocoa/CMakeLists.txt1
-rw-r--r--src/plugins/platforms/cocoa/qcocoaapplicationdelegate.mm2
-rw-r--r--src/plugins/platforms/cocoa/qcocoaintegration.h4
-rw-r--r--src/plugins/platforms/cocoa/qcocoaintegration.mm4
-rw-r--r--src/plugins/platforms/cocoa/qcocoamenuitem.mm6
-rw-r--r--src/plugins/platforms/cocoa/qcocoansmenu.mm6
-rw-r--r--src/plugins/platforms/cocoa/qnsview_dragging.mm6
-rw-r--r--src/plugins/platforms/cocoa/qnsview_keys.mm8
-rw-r--r--src/plugins/platforms/cocoa/qnsview_mouse.mm4
-rw-r--r--src/plugins/platforms/cocoa/qnsview_tablet.mm2
-rw-r--r--src/plugins/platforms/ios/qiosviewcontroller.h2
-rw-r--r--src/plugins/platforms/ios/qiosviewcontroller.mm33
-rw-r--r--src/plugins/platforms/ios/quiview.h1
-rw-r--r--src/plugins/platforms/ios/quiview.mm47
19 files changed, 274 insertions, 48 deletions
diff --git a/src/gui/CMakeLists.txt b/src/gui/CMakeLists.txt
index 979de8aadf..40c373c6d9 100644
--- a/src/gui/CMakeLists.txt
+++ b/src/gui/CMakeLists.txt
@@ -359,6 +359,7 @@ qt_internal_extend_target(Gui CONDITION MACOS
platform/macos/qcocoanativeinterface.mm
LIBRARIES
${FWAppKit}
+ ${FWCarbon}
PUBLIC_LIBRARIES
${FWAppKit}
)
@@ -369,6 +370,7 @@ qt_internal_extend_target(Gui CONDITION APPLE
painting/qcoregraphics.mm painting/qcoregraphics_p.h
painting/qrasterbackingstore.cpp painting/qrasterbackingstore_p.h
platform/darwin/qmacmime.mm platform/darwin/qmacmime_p.h
+ platform/darwin/qapplekeymapper.mm platform/darwin/qapplekeymapper_p.h
text/coretext/qcoretextfontdatabase.mm text/coretext/qcoretextfontdatabase_p.h
text/coretext/qfontengine_coretext.mm text/coretext/qfontengine_coretext_p.h
LIBRARIES
diff --git a/src/gui/kernel/qshortcutmap.cpp b/src/gui/kernel/qshortcutmap.cpp
index 2945115402..d83a00bc48 100644
--- a/src/gui/kernel/qshortcutmap.cpp
+++ b/src/gui/kernel/qshortcutmap.cpp
@@ -43,7 +43,8 @@
#include "qdebug.h"
#include "qevent.h"
#include "qlist.h"
-#include "qcoreapplication.h"
+#include "qguiapplication.h"
+#include "qwindow.h"
#include <private/qkeymapper_p.h>
#include <QtCore/qloggingcategory.h>
@@ -665,6 +666,46 @@ void QShortcutMap::dispatchEvent(QKeyEvent *e)
QCoreApplication::sendEvent(const_cast<QObject *>(next->owner), &se);
}
+QList<QKeySequence> QShortcutMap::keySequences(bool getAll) const
+{
+ Q_D(const QShortcutMap);
+ QList<QKeySequence> keys;
+ for (auto sequence : d->sequences) {
+ bool addSequence = false;
+ if (sequence.enabled) {
+ if (getAll || sequence.context == Qt::ApplicationShortcut ||
+ sequence.owner == QGuiApplication::focusObject()) {
+ addSequence = true;
+ } else {
+ QObject *possibleWindow = sequence.owner;
+ while (possibleWindow) {
+ if (qobject_cast<QWindow *>(possibleWindow))
+ break;
+ possibleWindow = possibleWindow->parent();
+ }
+ if (possibleWindow == QGuiApplication::focusWindow()) {
+ if (sequence.context == Qt::WindowShortcut) {
+ addSequence = true;
+ } else if (sequence.context == Qt::WidgetWithChildrenShortcut) {
+ QObject *possibleWidget = QGuiApplication::focusObject();
+ while (possibleWidget->parent()) {
+ possibleWidget = possibleWidget->parent();
+ if (possibleWidget == sequence.owner) {
+ addSequence = true;
+ break;
+ }
+ }
+ }
+ }
+ }
+ if (addSequence)
+ keys << sequence.keyseq;
+ }
+ }
+ return keys;
+
+}
+
/* \internal
QShortcutMap dump function, only available when DEBUG_QSHORTCUTMAP is
defined.
diff --git a/src/gui/kernel/qshortcutmap_p.h b/src/gui/kernel/qshortcutmap_p.h
index ff92a38e56..287549ea3a 100644
--- a/src/gui/kernel/qshortcutmap_p.h
+++ b/src/gui/kernel/qshortcutmap_p.h
@@ -86,6 +86,7 @@ public:
bool tryShortcut(QKeyEvent *e);
bool hasShortcutForKeySequence(const QKeySequence &seq) const;
+ QList<QKeySequence> keySequences(bool getAll = false) const;
#ifdef Dump_QShortcutMap
void dumpMap() const;
diff --git a/src/plugins/platforms/cocoa/qcocoakeymapper.mm b/src/gui/platform/darwin/qapplekeymapper.mm
index caa68ae694..c66fe784ed 100644
--- a/src/plugins/platforms/cocoa/qcocoakeymapper.mm
+++ b/src/gui/platform/darwin/qapplekeymapper.mm
@@ -1,6 +1,6 @@
/****************************************************************************
**
-** Copyright (C) 2020 The Qt Company Ltd.
+** Copyright (C) 2021 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
** This file is part of the plugins of the Qt Toolkit.
@@ -37,9 +37,17 @@
**
****************************************************************************/
+#include <qglobal.h>
+
+#ifdef Q_OS_MACOS
#include <AppKit/AppKit.h>
+#endif
+
+#if defined(QT_PLATFORM_UIKIT)
+#include <UIKit/UIKit.h>
+#endif
-#include "qcocoakeymapper.h"
+#include "qapplekeymapper_p.h"
#include <QtCore/qloggingcategory.h>
#include <QtGui/QGuiApplication>
@@ -65,6 +73,33 @@ static Qt::KeyboardModifiers swapModifiersIfNeeded(const Qt::KeyboardModifiers m
return swappedModifiers;
}
+Qt::Key QAppleKeyMapper::fromNSString(Qt::KeyboardModifiers qtModifiers, NSString *characters,
+ NSString *charactersIgnoringModifiers)
+{
+ if ([characters isEqualToString:@"\t"]) {
+ if (qtModifiers & Qt::ShiftModifier)
+ return Qt::Key_Backtab;
+ return Qt::Key_Tab;
+ } else if ([characters isEqualToString:@"\r"]) {
+ if (qtModifiers & Qt::KeypadModifier)
+ return Qt::Key_Enter;
+ return Qt::Key_Return;
+ }
+ if ([characters length] != 0 || [charactersIgnoringModifiers length] != 0) {
+ QChar ch;
+ if (((qtModifiers & Qt::MetaModifier) || (qtModifiers & Qt::AltModifier)) &&
+ ([charactersIgnoringModifiers length] != 0)) {
+ ch = QChar([charactersIgnoringModifiers characterAtIndex:0]);
+ } else if ([characters length] != 0) {
+ ch = QChar([characters characterAtIndex:0]);
+ }
+ if (!ch.isNull())
+ return Qt::Key(ch.toUpper().unicode());
+ }
+ return Qt::Key_unknown;
+}
+
+#ifdef Q_OS_MACOS
static constexpr std::tuple<NSEventModifierFlags, Qt::KeyboardModifier> cocoaModifierMap[] = {
{ NSEventModifierFlagShift, Qt::ShiftModifier },
{ NSEventModifierFlagControl, Qt::ControlModifier },
@@ -73,7 +108,7 @@ static constexpr std::tuple<NSEventModifierFlags, Qt::KeyboardModifier> cocoaMod
{ NSEventModifierFlagNumericPad, Qt::KeypadModifier }
};
-Qt::KeyboardModifiers QCocoaKeyMapper::fromCocoaModifiers(NSEventModifierFlags cocoaModifiers)
+Qt::KeyboardModifiers QAppleKeyMapper::fromCocoaModifiers(NSEventModifierFlags cocoaModifiers)
{
Qt::KeyboardModifiers qtModifiers = Qt::NoModifier;
for (const auto &[cocoaModifier, qtModifier] : cocoaModifierMap) {
@@ -84,7 +119,7 @@ Qt::KeyboardModifiers QCocoaKeyMapper::fromCocoaModifiers(NSEventModifierFlags c
return swapModifiersIfNeeded(qtModifiers);
}
-NSEventModifierFlags QCocoaKeyMapper::toCocoaModifiers(Qt::KeyboardModifiers qtModifiers)
+NSEventModifierFlags QAppleKeyMapper::toCocoaModifiers(Qt::KeyboardModifiers qtModifiers)
{
qtModifiers = swapModifiersIfNeeded(qtModifiers);
@@ -353,7 +388,7 @@ static const QHash<char16_t, Qt::Key> cocoaKeys = {
{ NSHelpFunctionKey, Qt::Key_Help },
};
-QChar QCocoaKeyMapper::toCocoaKey(Qt::Key key)
+QChar QAppleKeyMapper::toCocoaKey(Qt::Key key)
{
// Prioritize overloaded keys
if (key == Qt::Key_Return)
@@ -371,7 +406,7 @@ QChar QCocoaKeyMapper::toCocoaKey(Qt::Key key)
return reverseCocoaKeys.value(key);
}
-Qt::Key QCocoaKeyMapper::fromCocoaKey(QChar keyCode)
+Qt::Key QAppleKeyMapper::fromCocoaKey(QChar keyCode)
{
if (auto key = cocoaKeys.value(keyCode.unicode()))
return key;
@@ -381,12 +416,12 @@ Qt::Key QCocoaKeyMapper::fromCocoaKey(QChar keyCode)
// ------------------------------------------------
-Qt::KeyboardModifiers QCocoaKeyMapper::queryKeyboardModifiers()
+Qt::KeyboardModifiers QAppleKeyMapper::queryKeyboardModifiers()
{
return fromCocoaModifiers(NSEvent.modifierFlags);
}
-bool QCocoaKeyMapper::updateKeyboard()
+bool QAppleKeyMapper::updateKeyboard()
{
QCFType<TISInputSourceRef> source = TISCopyInputMethodKeyboardLayoutOverride();
if (!source)
@@ -442,11 +477,11 @@ static constexpr Qt::KeyboardModifiers modifierCombinations[] = {
Returns a key map for the given \virtualKey based on all
possible modifier combinations.
*/
-const QCocoaKeyMapper::KeyMap &QCocoaKeyMapper::keyMapForKey(VirtualKeyCode virtualKey, QChar unicodeKey) const
+const QAppleKeyMapper::KeyMap &QAppleKeyMapper::keyMapForKey(VirtualKeyCode virtualKey, QChar unicodeKey) const
{
static_assert(sizeof(modifierCombinations) / sizeof(Qt::KeyboardModifiers) == kNumModifierCombinations);
- const_cast<QCocoaKeyMapper *>(this)->updateKeyboard();
+ const_cast<QAppleKeyMapper *>(this)->updateKeyboard();
auto &keyMap = m_keyMap[virtualKey];
if (keyMap[Qt::NoModifier] != Qt::Key_unknown)
@@ -509,7 +544,7 @@ const QCocoaKeyMapper::KeyMap &QCocoaKeyMapper::keyMapForKey(VirtualKeyCode virt
return keyMap;
}
-QList<int> QCocoaKeyMapper::possibleKeys(const QKeyEvent *event) const
+QList<int> QAppleKeyMapper::possibleKeys(const QKeyEvent *event) const
{
QList<int> ret;
@@ -544,4 +579,75 @@ QList<int> QCocoaKeyMapper::possibleKeys(const QKeyEvent *event) const
return ret;
}
+
+
+#else
+// Keyboard keys (non-modifiers)
+API_AVAILABLE(ios(13.4)) static QHash<NSString *, Qt::Key> uiKitKeys = {
+#if QT_IOS_PLATFORM_SDK_EQUAL_OR_ABOVE(__IPHONE_13_4)
+ { UIKeyInputF1, Qt::Key_F1 },
+ { UIKeyInputF2, Qt::Key_F2 },
+ { UIKeyInputF3, Qt::Key_F3 },
+ { UIKeyInputF4, Qt::Key_F4 },
+ { UIKeyInputF5, Qt::Key_F5 },
+ { UIKeyInputF6, Qt::Key_F6 },
+ { UIKeyInputF7, Qt::Key_F7 },
+ { UIKeyInputF8, Qt::Key_F8 },
+ { UIKeyInputF9, Qt::Key_F9 },
+ { UIKeyInputF10, Qt::Key_F10 },
+ { UIKeyInputF11, Qt::Key_F11 },
+ { UIKeyInputF12, Qt::Key_F12 },
+ { UIKeyInputHome, Qt::Key_Home },
+ { UIKeyInputEnd, Qt::Key_End },
+ { UIKeyInputPageUp, Qt::Key_PageUp },
+ { UIKeyInputPageDown, Qt::Key_PageDown },
+#endif
+ { UIKeyInputEscape, Qt::Key_Escape },
+ { UIKeyInputUpArrow, Qt::Key_Up },
+ { UIKeyInputDownArrow, Qt::Key_Down },
+ { UIKeyInputLeftArrow, Qt::Key_Left },
+ { UIKeyInputRightArrow, Qt::Key_Right }
+};
+
+API_AVAILABLE(ios(13.4)) Qt::Key QAppleKeyMapper::fromUIKitKey(NSString *keyCode)
+{
+ if (auto key = uiKitKeys.value(keyCode))
+ return key;
+
+ return Qt::Key_unknown;
+}
+
+static constexpr std::tuple<ulong, Qt::KeyboardModifier> uiKitModifierMap[] = {
+ { UIKeyModifierShift, Qt::ShiftModifier },
+ { UIKeyModifierControl, Qt::ControlModifier },
+ { UIKeyModifierCommand, Qt::MetaModifier },
+ { UIKeyModifierAlternate, Qt::AltModifier },
+ { UIKeyModifierNumericPad, Qt::KeypadModifier }
+};
+
+ulong QAppleKeyMapper::toUIKitModifiers(Qt::KeyboardModifiers qtModifiers)
+{
+ qtModifiers = swapModifiersIfNeeded(qtModifiers);
+
+ ulong nativeModifiers = 0;
+ for (const auto &[nativeModifier, qtModifier] : uiKitModifierMap) {
+ if (qtModifiers & qtModifier)
+ nativeModifiers |= nativeModifier;
+ }
+
+ return nativeModifiers;
+}
+
+Qt::KeyboardModifiers QAppleKeyMapper::fromUIKitModifiers(ulong nativeModifiers)
+{
+ Qt::KeyboardModifiers qtModifiers = Qt::NoModifier;
+ for (const auto &[nativeModifier, qtModifier] : uiKitModifierMap) {
+ if (nativeModifiers & nativeModifier)
+ qtModifiers |= qtModifier;
+ }
+
+ return swapModifiersIfNeeded(qtModifiers);
+}
+#endif
+
QT_END_NAMESPACE
diff --git a/src/plugins/platforms/cocoa/qcocoakeymapper.h b/src/gui/platform/darwin/qapplekeymapper_p.h
index dbf164c18e..8664ab378b 100644
--- a/src/plugins/platforms/cocoa/qcocoakeymapper.h
+++ b/src/gui/platform/darwin/qapplekeymapper_p.h
@@ -1,6 +1,6 @@
/****************************************************************************
**
-** Copyright (C) 2016 The Qt Company Ltd.
+** Copyright (C) 2021 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
** This file is part of the plugins of the Qt Toolkit.
@@ -37,10 +37,12 @@
**
****************************************************************************/
-#ifndef QCOCOAKEYMAPPER_H
-#define QCOCOAKEYMAPPER_H
+#ifndef QAPPLEKEYMAPPER_H
+#define QAPPLEKEYMAPPER_H
+#ifdef Q_OS_MACOS
#include <Carbon/Carbon.h>
+#endif
#include <QtCore/QList>
#include <QtGui/QKeyEvent>
@@ -49,19 +51,26 @@
QT_BEGIN_NAMESPACE
-class QCocoaKeyMapper
+class Q_GUI_EXPORT QAppleKeyMapper
{
public:
static Qt::KeyboardModifiers queryKeyboardModifiers();
QList<int> possibleKeys(const QKeyEvent *event) const;
-
+ static Qt::Key fromNSString(Qt::KeyboardModifiers qtMods, NSString *characters,
+ NSString *charactersIgnoringModifiers);
+#ifdef Q_OS_MACOS
static Qt::KeyboardModifiers fromCocoaModifiers(NSEventModifierFlags cocoaModifiers);
static NSEventModifierFlags toCocoaModifiers(Qt::KeyboardModifiers);
static QChar toCocoaKey(Qt::Key key);
static Qt::Key fromCocoaKey(QChar keyCode);
-
+#else
+ static Qt::Key fromUIKitKey(NSString *keyCode);
+ static Qt::KeyboardModifiers fromUIKitModifiers(ulong uikitModifiers);
+ static ulong toUIKitModifiers(Qt::KeyboardModifiers);
+#endif
private:
+#ifdef Q_OS_MACOS
static constexpr int kNumModifierCombinations = 16;
struct KeyMap : std::array<char32_t, kNumModifierCombinations>
{
@@ -85,6 +94,7 @@ private:
mutable UInt32 m_deadKeyState = 0; // Maintains dead key state beween calls to UCKeyTranslate
mutable QHash<VirtualKeyCode, KeyMap> m_keyMap;
+#endif
};
QT_END_NAMESPACE
diff --git a/src/plugins/platforms/cocoa/CMakeLists.txt b/src/plugins/platforms/cocoa/CMakeLists.txt
index d9832c2c6c..8dbf534c9b 100644
--- a/src/plugins/platforms/cocoa/CMakeLists.txt
+++ b/src/plugins/platforms/cocoa/CMakeLists.txt
@@ -26,7 +26,6 @@ qt_internal_add_plugin(QCocoaIntegrationPlugin
qcocoainputcontext.h qcocoainputcontext.mm
qcocoaintegration.h qcocoaintegration.mm
qcocoaintrospection.h qcocoaintrospection.mm
- qcocoakeymapper.h qcocoakeymapper.mm
qcocoamenu.h qcocoamenu.mm
qcocoamenubar.h qcocoamenubar.mm
qcocoamenuitem.h qcocoamenuitem.mm
diff --git a/src/plugins/platforms/cocoa/qcocoaapplicationdelegate.mm b/src/plugins/platforms/cocoa/qcocoaapplicationdelegate.mm
index e6e46cda81..40d8f639fc 100644
--- a/src/plugins/platforms/cocoa/qcocoaapplicationdelegate.mm
+++ b/src/plugins/platforms/cocoa/qcocoaapplicationdelegate.mm
@@ -371,7 +371,7 @@ QT_USE_NAMESPACE
return;
QScopedScopeLevelCounter scopeLevelCounter(QGuiApplicationPrivate::instance()->threadData.loadRelaxed());
- QGuiApplicationPrivate::modifier_buttons = QCocoaKeyMapper::fromCocoaModifiers([NSEvent modifierFlags]);
+ QGuiApplicationPrivate::modifier_buttons = QAppleKeyMapper::fromCocoaModifiers([NSEvent modifierFlags]);
static QMetaMethod activatedSignal = QMetaMethod::fromSignal(&QCocoaMenuItem::activated);
activatedSignal.invoke(platformItem, Qt::QueuedConnection);
diff --git a/src/plugins/platforms/cocoa/qcocoaintegration.h b/src/plugins/platforms/cocoa/qcocoaintegration.h
index 4f1969dd98..caf47e38d3 100644
--- a/src/plugins/platforms/cocoa/qcocoaintegration.h
+++ b/src/plugins/platforms/cocoa/qcocoaintegration.h
@@ -48,7 +48,6 @@
#include "qcocoaclipboard.h"
#include "qcocoadrag.h"
#include "qcocoaservices.h"
-#include "qcocoakeymapper.h"
#if QT_CONFIG(vulkan)
#include "qcocoavulkaninstance.h"
#endif
@@ -57,6 +56,7 @@
#include <qpa/qplatformintegration.h>
#include <QtGui/private/qcoretextfontdatabase_p.h>
#include <QtGui/private/qopenglcontext_p.h>
+#include <QtGui/private/qapplekeymapper_p.h>
Q_FORWARD_DECLARE_OBJC_CLASS(NSToolbar);
@@ -156,7 +156,7 @@ private:
QScopedPointer<QCocoaDrag> mCocoaDrag;
QScopedPointer<QCocoaNativeInterface> mNativeInterface;
QScopedPointer<QCocoaServices> mServices;
- QScopedPointer<QCocoaKeyMapper> mKeyboardMapper;
+ QScopedPointer<QAppleKeyMapper> mKeyboardMapper;
#if QT_CONFIG(vulkan)
mutable QCocoaVulkanInstance *mCocoaVulkanInstance = nullptr;
diff --git a/src/plugins/platforms/cocoa/qcocoaintegration.mm b/src/plugins/platforms/cocoa/qcocoaintegration.mm
index 872d9bb7f1..1ab30df7e8 100644
--- a/src/plugins/platforms/cocoa/qcocoaintegration.mm
+++ b/src/plugins/platforms/cocoa/qcocoaintegration.mm
@@ -136,7 +136,7 @@ QCocoaIntegration::QCocoaIntegration(const QStringList &paramList)
, mCocoaDrag(new QCocoaDrag)
, mNativeInterface(new QCocoaNativeInterface)
, mServices(new QCocoaServices)
- , mKeyboardMapper(new QCocoaKeyMapper)
+ , mKeyboardMapper(new QAppleKeyMapper)
{
logVersionInformation();
@@ -420,7 +420,7 @@ QVariant QCocoaIntegration::styleHint(StyleHint hint) const
Qt::KeyboardModifiers QCocoaIntegration::queryKeyboardModifiers() const
{
- return QCocoaKeyMapper::queryKeyboardModifiers();
+ return QAppleKeyMapper::queryKeyboardModifiers();
}
QList<int> QCocoaIntegration::possibleKeys(const QKeyEvent *event) const
diff --git a/src/plugins/platforms/cocoa/qcocoamenuitem.mm b/src/plugins/platforms/cocoa/qcocoamenuitem.mm
index 4806b244c3..f11d7bd996 100644
--- a/src/plugins/platforms/cocoa/qcocoamenuitem.mm
+++ b/src/plugins/platforms/cocoa/qcocoamenuitem.mm
@@ -50,9 +50,9 @@
#include "qcocoahelpers.h"
#include "qcocoaapplication.h" // for custom application category
#include "qcocoamenuloader.h"
-#include "qcocoakeymapper.h"
#include <QtGui/private/qcoregraphics_p.h>
#include <QtCore/qregularexpression.h>
+#include <QtGui/private/qapplekeymapper_p.h>
#include <QtCore/QDebug>
@@ -356,7 +356,7 @@ NSMenuItem *QCocoaMenuItem::sync()
auto key = accel[0].key();
auto modifiers = accel[0].keyboardModifiers();
- QChar cocoaKey = QCocoaKeyMapper::toCocoaKey(key);
+ QChar cocoaKey = QAppleKeyMapper::toCocoaKey(key);
if (cocoaKey.isNull())
cocoaKey = QChar(key).toLower().unicode();
// Similar to qt_mac_removePrivateUnicode change the delete key,
@@ -365,7 +365,7 @@ NSMenuItem *QCocoaMenuItem::sync()
cocoaKey = QChar(NSDeleteCharacter);
m_native.keyEquivalent = QStringView(&cocoaKey, 1).toNSString();
- m_native.keyEquivalentModifierMask = QCocoaKeyMapper::toCocoaModifiers(modifiers);
+ m_native.keyEquivalentModifierMask = QAppleKeyMapper::toCocoaModifiers(modifiers);
} else
#endif
{
diff --git a/src/plugins/platforms/cocoa/qcocoansmenu.mm b/src/plugins/platforms/cocoa/qcocoansmenu.mm
index b94d31251e..6760ae59ff 100644
--- a/src/plugins/platforms/cocoa/qcocoansmenu.mm
+++ b/src/plugins/platforms/cocoa/qcocoansmenu.mm
@@ -46,10 +46,10 @@
#include "qcocoawindow.h"
#include "qnsview.h"
#include "qcocoahelpers.h"
-#include "qcocoakeymapper.h"
#include <QtCore/qcoreapplication.h>
#include <QtCore/qcoreevent.h>
+#include <QtGui/private/qapplekeymapper_p.h>
static NSString *qt_mac_removePrivateUnicode(NSString *string)
{
@@ -254,7 +254,7 @@ static NSString *qt_mac_removePrivateUnicode(NSString *string)
QChar ch;
int keyCode;
ulong nativeModifiers = event.modifierFlags;
- Qt::KeyboardModifiers modifiers = QCocoaKeyMapper::fromCocoaModifiers(nativeModifiers);
+ Qt::KeyboardModifiers modifiers = QAppleKeyMapper::fromCocoaModifiers(nativeModifiers);
NSString *charactersIgnoringModifiers = event.charactersIgnoringModifiers;
NSString *characters = event.characters;
@@ -264,7 +264,7 @@ static NSString *qt_mac_removePrivateUnicode(NSString *string)
} else {
ch = QChar([charactersIgnoringModifiers characterAtIndex:0]);
}
- keyCode = QCocoaKeyMapper::fromCocoaKey(ch);
+ keyCode = QAppleKeyMapper::fromCocoaKey(ch);
} else {
// might be a dead key
ch = QChar::ReplacementCharacter;
diff --git a/src/plugins/platforms/cocoa/qnsview_dragging.mm b/src/plugins/platforms/cocoa/qnsview_dragging.mm
index d4ab5f4a24..945217e928 100644
--- a/src/plugins/platforms/cocoa/qnsview_dragging.mm
+++ b/src/plugins/platforms/cocoa/qnsview_dragging.mm
@@ -197,7 +197,7 @@ static QPoint mapWindowCoordinates(QWindow *source, QWindow *target, QPoint poin
if (!target)
return NSDragOperationNone;
- const auto modifiers = QCocoaKeyMapper::fromCocoaModifiers(NSApp.currentEvent.modifierFlags);
+ const auto modifiers = QAppleKeyMapper::fromCocoaModifiers(NSApp.currentEvent.modifierFlags);
const auto buttons = currentlyPressedMouseButtons();
const auto point = mapWindowCoordinates(m_platformWindow->window(), target, windowPoint);
@@ -261,7 +261,7 @@ static QPoint mapWindowCoordinates(QWindow *source, QWindow *target, QPoint poin
QPlatformDropQtResponse response(false, Qt::IgnoreAction);
QCocoaDrag* nativeDrag = QCocoaIntegration::instance()->drag();
- const auto modifiers = QCocoaKeyMapper::fromCocoaModifiers(NSApp.currentEvent.modifierFlags);
+ const auto modifiers = QAppleKeyMapper::fromCocoaModifiers(NSApp.currentEvent.modifierFlags);
const auto buttons = currentlyPressedMouseButtons();
const auto point = mapWindowCoordinates(m_platformWindow->window(), target, windowPoint);
@@ -302,7 +302,7 @@ static QPoint mapWindowCoordinates(QWindow *source, QWindow *target, QPoint poin
// this case won't send the matching release event, so we have to
// synthesize it here.
m_buttons = currentlyPressedMouseButtons();
- const auto modifiers = QCocoaKeyMapper::fromCocoaModifiers(NSApp.currentEvent.modifierFlags);
+ const auto modifiers = QAppleKeyMapper::fromCocoaModifiers(NSApp.currentEvent.modifierFlags);
NSPoint windowPoint = [self.window convertRectFromScreen:NSMakeRect(screenPoint.x, screenPoint.y, 1, 1)].origin;
NSPoint nsViewPoint = [self convertPoint: windowPoint fromView: nil];
diff --git a/src/plugins/platforms/cocoa/qnsview_keys.mm b/src/plugins/platforms/cocoa/qnsview_keys.mm
index 09d78485f4..23b8254d63 100644
--- a/src/plugins/platforms/cocoa/qnsview_keys.mm
+++ b/src/plugins/platforms/cocoa/qnsview_keys.mm
@@ -45,7 +45,7 @@
{
ulong timestamp = [nsevent timestamp] * 1000;
ulong nativeModifiers = [nsevent modifierFlags];
- Qt::KeyboardModifiers modifiers = QCocoaKeyMapper::fromCocoaModifiers(nativeModifiers);
+ Qt::KeyboardModifiers modifiers = QAppleKeyMapper::fromCocoaModifiers(nativeModifiers);
NSString *charactersIgnoringModifiers = [nsevent charactersIgnoringModifiers];
NSString *characters = [nsevent characters];
if (m_inputSource != characters) {
@@ -74,7 +74,7 @@
ch = QChar([charactersIgnoringModifiers characterAtIndex:0]);
else if ([characters length] != 0)
ch = QChar([characters characterAtIndex:0]);
- keyCode = QCocoaKeyMapper::fromCocoaKey(ch);
+ keyCode = QAppleKeyMapper::fromCocoaKey(ch);
}
// we will send a key event unless the input method sets m_sendKeyEvent to false
@@ -194,7 +194,7 @@
{
ulong timestamp = [nsevent timestamp] * 1000;
ulong nativeModifiers = [nsevent modifierFlags];
- Qt::KeyboardModifiers modifiers = QCocoaKeyMapper::fromCocoaModifiers(nativeModifiers);
+ Qt::KeyboardModifiers modifiers = QAppleKeyMapper::fromCocoaModifiers(nativeModifiers);
// Scan codes are hardware dependent codes for each key. There is no way to get these
// from Carbon or Cocoa, so leave it 0, as documented in QKeyEvent::nativeScanCode().
@@ -238,7 +238,7 @@
(lastKnownModifiers & mac_mask) ? QEvent::KeyRelease
: QEvent::KeyPress,
qtCode,
- modifiers ^ QCocoaKeyMapper::fromCocoaModifiers(mac_mask),
+ modifiers ^ QAppleKeyMapper::fromCocoaModifiers(mac_mask),
nativeScanCode, nativeVirtualKey,
nativeModifiers ^ mac_mask);
}
diff --git a/src/plugins/platforms/cocoa/qnsview_mouse.mm b/src/plugins/platforms/cocoa/qnsview_mouse.mm
index 336f1085b9..d00cfb7886 100644
--- a/src/plugins/platforms/cocoa/qnsview_mouse.mm
+++ b/src/plugins/platforms/cocoa/qnsview_mouse.mm
@@ -279,7 +279,7 @@
QCocoaDrag* nativeDrag = QCocoaIntegration::instance()->drag();
nativeDrag->setLastMouseEvent(theEvent, self);
- const auto modifiers = QCocoaKeyMapper::fromCocoaModifiers(theEvent.modifierFlags);
+ const auto modifiers = QAppleKeyMapper::fromCocoaModifiers(theEvent.modifierFlags);
auto button = cocoaButton2QtButton(theEvent);
if (button == Qt::LeftButton && m_sendUpAsRightButton)
button = Qt::RightButton;
@@ -678,7 +678,7 @@
// after scrolling in Qt Creator: not taking the phase into account causes
// the end of the event stream to be interpreted as font size changes.
if (theEvent.momentumPhase == NSEventPhaseNone)
- m_currentWheelModifiers = QCocoaKeyMapper::fromCocoaModifiers(theEvent.modifierFlags);
+ m_currentWheelModifiers = QAppleKeyMapper::fromCocoaModifiers(theEvent.modifierFlags);
// "isInverted": natural OS X scrolling, inverted from the Qt/other platform/Jens perspective.
bool isInverted = [theEvent isDirectionInvertedFromDevice];
diff --git a/src/plugins/platforms/cocoa/qnsview_tablet.mm b/src/plugins/platforms/cocoa/qnsview_tablet.mm
index 804c502775..2b269d038a 100644
--- a/src/plugins/platforms/cocoa/qnsview_tablet.mm
+++ b/src/plugins/platforms/cocoa/qnsview_tablet.mm
@@ -109,7 +109,7 @@ Q_GLOBAL_STATIC(QCocoaTabletDeviceDataHash, tabletDeviceDataHash)
if (rotation > 180.0)
rotation -= 360.0;
- Qt::KeyboardModifiers keyboardModifiers = QCocoaKeyMapper::fromCocoaModifiers(theEvent.modifierFlags);
+ Qt::KeyboardModifiers keyboardModifiers = QAppleKeyMapper::fromCocoaModifiers(theEvent.modifierFlags);
Qt::MouseButtons buttons = ignoreButtonMapping ? static_cast<Qt::MouseButtons>(static_cast<uint>([theEvent buttonMask])) : m_buttons;
qCDebug(lcQpaTablet, "event on tablet %d with tool %d type %d unique ID %lld pos %6.1f, %6.1f root pos %6.1f, %6.1f buttons 0x%x pressure %4.2lf tilt %d, %d rotation %6.2lf",
diff --git a/src/plugins/platforms/ios/qiosviewcontroller.h b/src/plugins/platforms/ios/qiosviewcontroller.h
index 7af4c83b48..79fe5ae3c5 100644
--- a/src/plugins/platforms/ios/qiosviewcontroller.h
+++ b/src/plugins/platforms/ios/qiosviewcontroller.h
@@ -50,6 +50,8 @@ QT_END_NAMESPACE
- (instancetype)initWithQIOSScreen:(QT_PREPEND_NAMESPACE(QIOSScreen) *)screen;
- (void)updateProperties;
+- (NSArray*)keyCommands;
+- (void)handleShortcut:(UIKeyCommand*)keyCommand;
#ifndef Q_OS_TVOS
@property (nonatomic, assign) UIInterfaceOrientation lockedOrientation;
diff --git a/src/plugins/platforms/ios/qiosviewcontroller.mm b/src/plugins/platforms/ios/qiosviewcontroller.mm
index cd4af46ef7..7d994f4394 100644
--- a/src/plugins/platforms/ios/qiosviewcontroller.mm
+++ b/src/plugins/platforms/ios/qiosviewcontroller.mm
@@ -42,12 +42,14 @@
#include <QtCore/qscopedvaluerollback.h>
#include <QtCore/private/qcore_mac_p.h>
+#include <QtGui/private/qapplekeymapper_p.h>
#include <QtGui/QGuiApplication>
#include <QtGui/QWindow>
#include <QtGui/QScreen>
#include <QtGui/private/qwindow_p.h>
+#include <QtGui/private/qguiapplication_p.h>
#include "qiosintegration.h"
#include "qiosscreen.h"
@@ -523,5 +525,36 @@
#endif
}
+- (NSArray*)keyCommands
+{
+ // FIXME: If we are on iOS 13.4 or later we can use UIKey instead of doing this
+ // So it should be safe to remove this entire function and handleShortcut() as
+ // a result
+ NSMutableArray<UIKeyCommand *> *keyCommands = nil;
+ QShortcutMap &shortcutMap = QGuiApplicationPrivate::instance()->shortcutMap;
+ keyCommands = [[NSMutableArray<UIKeyCommand *> alloc] init];
+ const QList<QKeySequence> keys = shortcutMap.keySequences();
+ for (const QKeySequence &seq : keys) {
+ const QString keyString = seq.toString();
+ [keyCommands addObject:[UIKeyCommand
+ keyCommandWithInput:QString(keyString[keyString.length() - 1]).toNSString()
+ modifierFlags:QAppleKeyMapper::toUIKitModifiers(seq[0].keyboardModifiers())
+ action:@selector(handleShortcut:)]];
+ }
+ return keyCommands;
+}
+
+- (void)handleShortcut:(UIKeyCommand *)keyCommand
+{
+ const QString str = QString::fromNSString([keyCommand input]);
+ Qt::KeyboardModifiers qtMods = QAppleKeyMapper::fromUIKitModifiers(keyCommand.modifierFlags);
+ QChar ch = str.isEmpty() ? QChar() : str.at(0);
+ QShortcutMap &shortcutMap = QGuiApplicationPrivate::instance()->shortcutMap;
+ QKeyEvent keyEvent(QEvent::ShortcutOverride, Qt::Key(ch.toUpper().unicode()), qtMods, str);
+ shortcutMap.tryShortcut(&keyEvent);
+}
+
+
+
@end
diff --git a/src/plugins/platforms/ios/quiview.h b/src/plugins/platforms/ios/quiview.h
index 1ab9481dd6..6a8e5a7707 100644
--- a/src/plugins/platforms/ios/quiview.h
+++ b/src/plugins/platforms/ios/quiview.h
@@ -56,6 +56,7 @@ QT_END_NAMESPACE
- (instancetype)initWithQIOSWindow:(QT_PREPEND_NAMESPACE(QIOSWindow) *)window;
- (void)sendUpdatedExposeEvent;
- (BOOL)isActiveWindow;
+- (bool)handlePresses:(NSSet<UIPress *> *)presses eventType:(QEvent::Type)type;
@property (nonatomic, assign) QT_PREPEND_NAMESPACE(QIOSWindow) *platformWindow;
@end
diff --git a/src/plugins/platforms/ios/quiview.mm b/src/plugins/platforms/ios/quiview.mm
index 4c56e03f42..5ca4d5ccc8 100644
--- a/src/plugins/platforms/ios/quiview.mm
+++ b/src/plugins/platforms/ios/quiview.mm
@@ -52,6 +52,7 @@
#include <QtGui/qpointingdevice.h>
#include <QtGui/private/qguiapplication_p.h>
#include <QtGui/private/qwindow_p.h>
+#include <QtGui/private/qapplekeymapper_p.h>
#include <qpa/qwindowsysteminterface_p.h>
Q_LOGGING_CATEGORY(lcQpaTablet, "qt.qpa.input.tablet")
@@ -571,7 +572,7 @@ Q_LOGGING_CATEGORY(lcQpaTablet, "qt.qpa.input.tablet")
QWindowSystemInterface::handleTouchCancelEvent(self.platformWindow->window(), ulong(timestamp * 1000), iosIntegration->touchDevice());
}
-- (int)mapPressTypeToKey:(UIPress*)press
+- (int)mapPressTypeToKey:(UIPress*)press withModifiers:(Qt::KeyboardModifiers)qtModifiers
{
switch (press.type) {
case UIPressTypeUpArrow: return Qt::Key_Up;
@@ -582,6 +583,16 @@ Q_LOGGING_CATEGORY(lcQpaTablet, "qt.qpa.input.tablet")
case UIPressTypeMenu: return Qt::Key_Menu;
case UIPressTypePlayPause: return Qt::Key_MediaTogglePlayPause;
}
+#if QT_IOS_PLATFORM_SDK_EQUAL_OR_ABOVE(__IPHONE_13_4)
+ if (@available(ios 13.4, *)) {
+ NSString *charactersIgnoringModifiers = press.key.charactersIgnoringModifiers;
+ Qt::Key key = QAppleKeyMapper::fromUIKitKey(charactersIgnoringModifiers);
+ if (key != Qt::Key_unknown)
+ return key;
+ return QAppleKeyMapper::fromNSString(qtModifiers, press.key.characters,
+ charactersIgnoringModifiers);
+ }
+#endif
return Qt::Key_unknown;
}
@@ -593,32 +604,52 @@ Q_LOGGING_CATEGORY(lcQpaTablet, "qt.qpa.input.tablet")
bool handled = false;
for (UIPress* press in presses) {
- int key = [self mapPressTypeToKey:press];
+ Qt::KeyboardModifiers qtModifiers = Qt::NoModifier;
+#if QT_IOS_PLATFORM_SDK_EQUAL_OR_ABOVE(__IPHONE_13_4)
+ if (@available(ios 13.4, *))
+ qtModifiers = QAppleKeyMapper::fromUIKitModifiers(press.key.modifierFlags);
+#endif
+ int key = [self mapPressTypeToKey:press withModifiers:qtModifiers];
if (key == Qt::Key_unknown)
continue;
- if (QWindowSystemInterface::handleKeyEvent(self.platformWindow->window(), type, key, Qt::NoModifier))
+ if (QWindowSystemInterface::handleKeyEvent(self.platformWindow->window(), type, key, qtModifiers))
handled = true;
}
return handled;
}
+- (BOOL)handlePresses:(NSSet<UIPress *> *)presses eventType:(QEvent::Type)type
+{
+ bool handlePress = false;
+ if (qApp->focusWindow()) {
+ QInputMethodQueryEvent queryEvent(Qt::ImEnabled);
+ if (qApp->focusObject() && QCoreApplication::sendEvent(qApp->focusObject(), &queryEvent))
+ handlePress = queryEvent.value(Qt::ImEnabled).toBool();
+ if (!handlePress && [self processPresses:presses withType:type])
+ return true;
+ }
+ return false;
+}
+
- (void)pressesBegan:(NSSet<UIPress *> *)presses withEvent:(UIPressesEvent *)event
{
- if (![self processPresses:presses withType:QEvent::KeyPress])
+ if (![self handlePresses:presses eventType:QEvent::KeyPress])
[super pressesBegan:presses withEvent:event];
}
- (void)pressesChanged:(NSSet<UIPress *> *)presses withEvent:(UIPressesEvent *)event
{
- if (![self processPresses:presses withType:QEvent::KeyPress])
- [super pressesChanged:presses withEvent:event];
+ if (![self handlePresses:presses eventType:QEvent::KeyPress])
+ [super pressesBegan:presses withEvent:event];
+ [super pressesChanged:presses withEvent:event];
}
- (void)pressesEnded:(NSSet<UIPress *> *)presses withEvent:(UIPressesEvent *)event
{
- if (![self processPresses:presses withType:QEvent::KeyRelease])
- [super pressesEnded:presses withEvent:event];
+ if (![self handlePresses:presses eventType:QEvent::KeyRelease])
+ [super pressesBegan:presses withEvent:event];
+ [super pressesEnded:presses withEvent:event];
}
- (BOOL)canPerformAction:(SEL)action withSender:(id)sender