iOS: Handle keyboard events when using an external keyboard
This enables the two possible approaches for handling external keyboard events. While support still exists for before 13.4 then both approaches are needed. This ensures that all external keyboard events are handled as key events and passed on accordingly. Additionally, this accounts for possible shortcuts too, therefore a new function is added to QShortcutMap to aid that. As a result, code has now moved from QCocoaKeyMapper to be part of the gui/platforms/darwin part to make it easier to reuse this code elsewhere. Fixes: QTBUG-85727 Change-Id: I349af43468b03fd8dcb16adba02669974affe154 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@qt.io>
This commit is contained in:
parent
a5bb7b3ca5
commit
15576c9610
@ -359,6 +359,7 @@ qt_internal_extend_target(Gui CONDITION MACOS
|
|||||||
platform/macos/qcocoanativeinterface.mm
|
platform/macos/qcocoanativeinterface.mm
|
||||||
LIBRARIES
|
LIBRARIES
|
||||||
${FWAppKit}
|
${FWAppKit}
|
||||||
|
${FWCarbon}
|
||||||
PUBLIC_LIBRARIES
|
PUBLIC_LIBRARIES
|
||||||
${FWAppKit}
|
${FWAppKit}
|
||||||
)
|
)
|
||||||
@ -369,6 +370,7 @@ qt_internal_extend_target(Gui CONDITION APPLE
|
|||||||
painting/qcoregraphics.mm painting/qcoregraphics_p.h
|
painting/qcoregraphics.mm painting/qcoregraphics_p.h
|
||||||
painting/qrasterbackingstore.cpp painting/qrasterbackingstore_p.h
|
painting/qrasterbackingstore.cpp painting/qrasterbackingstore_p.h
|
||||||
platform/darwin/qmacmime.mm platform/darwin/qmacmime_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/qcoretextfontdatabase.mm text/coretext/qcoretextfontdatabase_p.h
|
||||||
text/coretext/qfontengine_coretext.mm text/coretext/qfontengine_coretext_p.h
|
text/coretext/qfontengine_coretext.mm text/coretext/qfontengine_coretext_p.h
|
||||||
LIBRARIES
|
LIBRARIES
|
||||||
|
@ -43,7 +43,8 @@
|
|||||||
#include "qdebug.h"
|
#include "qdebug.h"
|
||||||
#include "qevent.h"
|
#include "qevent.h"
|
||||||
#include "qlist.h"
|
#include "qlist.h"
|
||||||
#include "qcoreapplication.h"
|
#include "qguiapplication.h"
|
||||||
|
#include "qwindow.h"
|
||||||
#include <private/qkeymapper_p.h>
|
#include <private/qkeymapper_p.h>
|
||||||
#include <QtCore/qloggingcategory.h>
|
#include <QtCore/qloggingcategory.h>
|
||||||
|
|
||||||
@ -665,6 +666,46 @@ void QShortcutMap::dispatchEvent(QKeyEvent *e)
|
|||||||
QCoreApplication::sendEvent(const_cast<QObject *>(next->owner), &se);
|
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
|
/* \internal
|
||||||
QShortcutMap dump function, only available when DEBUG_QSHORTCUTMAP is
|
QShortcutMap dump function, only available when DEBUG_QSHORTCUTMAP is
|
||||||
defined.
|
defined.
|
||||||
|
@ -86,6 +86,7 @@ public:
|
|||||||
|
|
||||||
bool tryShortcut(QKeyEvent *e);
|
bool tryShortcut(QKeyEvent *e);
|
||||||
bool hasShortcutForKeySequence(const QKeySequence &seq) const;
|
bool hasShortcutForKeySequence(const QKeySequence &seq) const;
|
||||||
|
QList<QKeySequence> keySequences(bool getAll = false) const;
|
||||||
|
|
||||||
#ifdef Dump_QShortcutMap
|
#ifdef Dump_QShortcutMap
|
||||||
void dumpMap() const;
|
void dumpMap() const;
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
**
|
**
|
||||||
** Copyright (C) 2020 The Qt Company Ltd.
|
** Copyright (C) 2021 The Qt Company Ltd.
|
||||||
** Contact: https://www.qt.io/licensing/
|
** Contact: https://www.qt.io/licensing/
|
||||||
**
|
**
|
||||||
** This file is part of the plugins of the Qt Toolkit.
|
** This file is part of the plugins of the Qt Toolkit.
|
||||||
@ -37,9 +37,17 @@
|
|||||||
**
|
**
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
#include <AppKit/AppKit.h>
|
#include <qglobal.h>
|
||||||
|
|
||||||
#include "qcocoakeymapper.h"
|
#ifdef Q_OS_MACOS
|
||||||
|
#include <AppKit/AppKit.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined(QT_PLATFORM_UIKIT)
|
||||||
|
#include <UIKit/UIKit.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include "qapplekeymapper_p.h"
|
||||||
|
|
||||||
#include <QtCore/qloggingcategory.h>
|
#include <QtCore/qloggingcategory.h>
|
||||||
#include <QtGui/QGuiApplication>
|
#include <QtGui/QGuiApplication>
|
||||||
@ -65,6 +73,33 @@ static Qt::KeyboardModifiers swapModifiersIfNeeded(const Qt::KeyboardModifiers m
|
|||||||
return swappedModifiers;
|
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[] = {
|
static constexpr std::tuple<NSEventModifierFlags, Qt::KeyboardModifier> cocoaModifierMap[] = {
|
||||||
{ NSEventModifierFlagShift, Qt::ShiftModifier },
|
{ NSEventModifierFlagShift, Qt::ShiftModifier },
|
||||||
{ NSEventModifierFlagControl, Qt::ControlModifier },
|
{ NSEventModifierFlagControl, Qt::ControlModifier },
|
||||||
@ -73,7 +108,7 @@ static constexpr std::tuple<NSEventModifierFlags, Qt::KeyboardModifier> cocoaMod
|
|||||||
{ NSEventModifierFlagNumericPad, Qt::KeypadModifier }
|
{ NSEventModifierFlagNumericPad, Qt::KeypadModifier }
|
||||||
};
|
};
|
||||||
|
|
||||||
Qt::KeyboardModifiers QCocoaKeyMapper::fromCocoaModifiers(NSEventModifierFlags cocoaModifiers)
|
Qt::KeyboardModifiers QAppleKeyMapper::fromCocoaModifiers(NSEventModifierFlags cocoaModifiers)
|
||||||
{
|
{
|
||||||
Qt::KeyboardModifiers qtModifiers = Qt::NoModifier;
|
Qt::KeyboardModifiers qtModifiers = Qt::NoModifier;
|
||||||
for (const auto &[cocoaModifier, qtModifier] : cocoaModifierMap) {
|
for (const auto &[cocoaModifier, qtModifier] : cocoaModifierMap) {
|
||||||
@ -84,7 +119,7 @@ Qt::KeyboardModifiers QCocoaKeyMapper::fromCocoaModifiers(NSEventModifierFlags c
|
|||||||
return swapModifiersIfNeeded(qtModifiers);
|
return swapModifiersIfNeeded(qtModifiers);
|
||||||
}
|
}
|
||||||
|
|
||||||
NSEventModifierFlags QCocoaKeyMapper::toCocoaModifiers(Qt::KeyboardModifiers qtModifiers)
|
NSEventModifierFlags QAppleKeyMapper::toCocoaModifiers(Qt::KeyboardModifiers qtModifiers)
|
||||||
{
|
{
|
||||||
qtModifiers = swapModifiersIfNeeded(qtModifiers);
|
qtModifiers = swapModifiersIfNeeded(qtModifiers);
|
||||||
|
|
||||||
@ -353,7 +388,7 @@ static const QHash<char16_t, Qt::Key> cocoaKeys = {
|
|||||||
{ NSHelpFunctionKey, Qt::Key_Help },
|
{ NSHelpFunctionKey, Qt::Key_Help },
|
||||||
};
|
};
|
||||||
|
|
||||||
QChar QCocoaKeyMapper::toCocoaKey(Qt::Key key)
|
QChar QAppleKeyMapper::toCocoaKey(Qt::Key key)
|
||||||
{
|
{
|
||||||
// Prioritize overloaded keys
|
// Prioritize overloaded keys
|
||||||
if (key == Qt::Key_Return)
|
if (key == Qt::Key_Return)
|
||||||
@ -371,7 +406,7 @@ QChar QCocoaKeyMapper::toCocoaKey(Qt::Key key)
|
|||||||
return reverseCocoaKeys.value(key);
|
return reverseCocoaKeys.value(key);
|
||||||
}
|
}
|
||||||
|
|
||||||
Qt::Key QCocoaKeyMapper::fromCocoaKey(QChar keyCode)
|
Qt::Key QAppleKeyMapper::fromCocoaKey(QChar keyCode)
|
||||||
{
|
{
|
||||||
if (auto key = cocoaKeys.value(keyCode.unicode()))
|
if (auto key = cocoaKeys.value(keyCode.unicode()))
|
||||||
return key;
|
return key;
|
||||||
@ -381,12 +416,12 @@ Qt::Key QCocoaKeyMapper::fromCocoaKey(QChar keyCode)
|
|||||||
|
|
||||||
// ------------------------------------------------
|
// ------------------------------------------------
|
||||||
|
|
||||||
Qt::KeyboardModifiers QCocoaKeyMapper::queryKeyboardModifiers()
|
Qt::KeyboardModifiers QAppleKeyMapper::queryKeyboardModifiers()
|
||||||
{
|
{
|
||||||
return fromCocoaModifiers(NSEvent.modifierFlags);
|
return fromCocoaModifiers(NSEvent.modifierFlags);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool QCocoaKeyMapper::updateKeyboard()
|
bool QAppleKeyMapper::updateKeyboard()
|
||||||
{
|
{
|
||||||
QCFType<TISInputSourceRef> source = TISCopyInputMethodKeyboardLayoutOverride();
|
QCFType<TISInputSourceRef> source = TISCopyInputMethodKeyboardLayoutOverride();
|
||||||
if (!source)
|
if (!source)
|
||||||
@ -442,11 +477,11 @@ static constexpr Qt::KeyboardModifiers modifierCombinations[] = {
|
|||||||
Returns a key map for the given \virtualKey based on all
|
Returns a key map for the given \virtualKey based on all
|
||||||
possible modifier combinations.
|
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);
|
static_assert(sizeof(modifierCombinations) / sizeof(Qt::KeyboardModifiers) == kNumModifierCombinations);
|
||||||
|
|
||||||
const_cast<QCocoaKeyMapper *>(this)->updateKeyboard();
|
const_cast<QAppleKeyMapper *>(this)->updateKeyboard();
|
||||||
|
|
||||||
auto &keyMap = m_keyMap[virtualKey];
|
auto &keyMap = m_keyMap[virtualKey];
|
||||||
if (keyMap[Qt::NoModifier] != Qt::Key_unknown)
|
if (keyMap[Qt::NoModifier] != Qt::Key_unknown)
|
||||||
@ -509,7 +544,7 @@ const QCocoaKeyMapper::KeyMap &QCocoaKeyMapper::keyMapForKey(VirtualKeyCode virt
|
|||||||
return keyMap;
|
return keyMap;
|
||||||
}
|
}
|
||||||
|
|
||||||
QList<int> QCocoaKeyMapper::possibleKeys(const QKeyEvent *event) const
|
QList<int> QAppleKeyMapper::possibleKeys(const QKeyEvent *event) const
|
||||||
{
|
{
|
||||||
QList<int> ret;
|
QList<int> ret;
|
||||||
|
|
||||||
@ -544,4 +579,75 @@ QList<int> QCocoaKeyMapper::possibleKeys(const QKeyEvent *event) const
|
|||||||
return ret;
|
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
|
QT_END_NAMESPACE
|
@ -1,6 +1,6 @@
|
|||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
**
|
**
|
||||||
** Copyright (C) 2016 The Qt Company Ltd.
|
** Copyright (C) 2021 The Qt Company Ltd.
|
||||||
** Contact: https://www.qt.io/licensing/
|
** Contact: https://www.qt.io/licensing/
|
||||||
**
|
**
|
||||||
** This file is part of the plugins of the Qt Toolkit.
|
** This file is part of the plugins of the Qt Toolkit.
|
||||||
@ -37,10 +37,12 @@
|
|||||||
**
|
**
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
#ifndef QCOCOAKEYMAPPER_H
|
#ifndef QAPPLEKEYMAPPER_H
|
||||||
#define QCOCOAKEYMAPPER_H
|
#define QAPPLEKEYMAPPER_H
|
||||||
|
|
||||||
|
#ifdef Q_OS_MACOS
|
||||||
#include <Carbon/Carbon.h>
|
#include <Carbon/Carbon.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#include <QtCore/QList>
|
#include <QtCore/QList>
|
||||||
#include <QtGui/QKeyEvent>
|
#include <QtGui/QKeyEvent>
|
||||||
@ -49,19 +51,26 @@
|
|||||||
|
|
||||||
QT_BEGIN_NAMESPACE
|
QT_BEGIN_NAMESPACE
|
||||||
|
|
||||||
class QCocoaKeyMapper
|
class Q_GUI_EXPORT QAppleKeyMapper
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
static Qt::KeyboardModifiers queryKeyboardModifiers();
|
static Qt::KeyboardModifiers queryKeyboardModifiers();
|
||||||
QList<int> possibleKeys(const QKeyEvent *event) const;
|
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 Qt::KeyboardModifiers fromCocoaModifiers(NSEventModifierFlags cocoaModifiers);
|
||||||
static NSEventModifierFlags toCocoaModifiers(Qt::KeyboardModifiers);
|
static NSEventModifierFlags toCocoaModifiers(Qt::KeyboardModifiers);
|
||||||
|
|
||||||
static QChar toCocoaKey(Qt::Key key);
|
static QChar toCocoaKey(Qt::Key key);
|
||||||
static Qt::Key fromCocoaKey(QChar keyCode);
|
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:
|
private:
|
||||||
|
#ifdef Q_OS_MACOS
|
||||||
static constexpr int kNumModifierCombinations = 16;
|
static constexpr int kNumModifierCombinations = 16;
|
||||||
struct KeyMap : std::array<char32_t, kNumModifierCombinations>
|
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 UInt32 m_deadKeyState = 0; // Maintains dead key state beween calls to UCKeyTranslate
|
||||||
|
|
||||||
mutable QHash<VirtualKeyCode, KeyMap> m_keyMap;
|
mutable QHash<VirtualKeyCode, KeyMap> m_keyMap;
|
||||||
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
QT_END_NAMESPACE
|
QT_END_NAMESPACE
|
@ -26,7 +26,6 @@ qt_internal_add_plugin(QCocoaIntegrationPlugin
|
|||||||
qcocoainputcontext.h qcocoainputcontext.mm
|
qcocoainputcontext.h qcocoainputcontext.mm
|
||||||
qcocoaintegration.h qcocoaintegration.mm
|
qcocoaintegration.h qcocoaintegration.mm
|
||||||
qcocoaintrospection.h qcocoaintrospection.mm
|
qcocoaintrospection.h qcocoaintrospection.mm
|
||||||
qcocoakeymapper.h qcocoakeymapper.mm
|
|
||||||
qcocoamenu.h qcocoamenu.mm
|
qcocoamenu.h qcocoamenu.mm
|
||||||
qcocoamenubar.h qcocoamenubar.mm
|
qcocoamenubar.h qcocoamenubar.mm
|
||||||
qcocoamenuitem.h qcocoamenuitem.mm
|
qcocoamenuitem.h qcocoamenuitem.mm
|
||||||
|
@ -371,7 +371,7 @@ QT_USE_NAMESPACE
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
QScopedScopeLevelCounter scopeLevelCounter(QGuiApplicationPrivate::instance()->threadData.loadRelaxed());
|
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);
|
static QMetaMethod activatedSignal = QMetaMethod::fromSignal(&QCocoaMenuItem::activated);
|
||||||
activatedSignal.invoke(platformItem, Qt::QueuedConnection);
|
activatedSignal.invoke(platformItem, Qt::QueuedConnection);
|
||||||
|
@ -48,7 +48,6 @@
|
|||||||
#include "qcocoaclipboard.h"
|
#include "qcocoaclipboard.h"
|
||||||
#include "qcocoadrag.h"
|
#include "qcocoadrag.h"
|
||||||
#include "qcocoaservices.h"
|
#include "qcocoaservices.h"
|
||||||
#include "qcocoakeymapper.h"
|
|
||||||
#if QT_CONFIG(vulkan)
|
#if QT_CONFIG(vulkan)
|
||||||
#include "qcocoavulkaninstance.h"
|
#include "qcocoavulkaninstance.h"
|
||||||
#endif
|
#endif
|
||||||
@ -57,6 +56,7 @@
|
|||||||
#include <qpa/qplatformintegration.h>
|
#include <qpa/qplatformintegration.h>
|
||||||
#include <QtGui/private/qcoretextfontdatabase_p.h>
|
#include <QtGui/private/qcoretextfontdatabase_p.h>
|
||||||
#include <QtGui/private/qopenglcontext_p.h>
|
#include <QtGui/private/qopenglcontext_p.h>
|
||||||
|
#include <QtGui/private/qapplekeymapper_p.h>
|
||||||
|
|
||||||
Q_FORWARD_DECLARE_OBJC_CLASS(NSToolbar);
|
Q_FORWARD_DECLARE_OBJC_CLASS(NSToolbar);
|
||||||
|
|
||||||
@ -156,7 +156,7 @@ private:
|
|||||||
QScopedPointer<QCocoaDrag> mCocoaDrag;
|
QScopedPointer<QCocoaDrag> mCocoaDrag;
|
||||||
QScopedPointer<QCocoaNativeInterface> mNativeInterface;
|
QScopedPointer<QCocoaNativeInterface> mNativeInterface;
|
||||||
QScopedPointer<QCocoaServices> mServices;
|
QScopedPointer<QCocoaServices> mServices;
|
||||||
QScopedPointer<QCocoaKeyMapper> mKeyboardMapper;
|
QScopedPointer<QAppleKeyMapper> mKeyboardMapper;
|
||||||
|
|
||||||
#if QT_CONFIG(vulkan)
|
#if QT_CONFIG(vulkan)
|
||||||
mutable QCocoaVulkanInstance *mCocoaVulkanInstance = nullptr;
|
mutable QCocoaVulkanInstance *mCocoaVulkanInstance = nullptr;
|
||||||
|
@ -136,7 +136,7 @@ QCocoaIntegration::QCocoaIntegration(const QStringList ¶mList)
|
|||||||
, mCocoaDrag(new QCocoaDrag)
|
, mCocoaDrag(new QCocoaDrag)
|
||||||
, mNativeInterface(new QCocoaNativeInterface)
|
, mNativeInterface(new QCocoaNativeInterface)
|
||||||
, mServices(new QCocoaServices)
|
, mServices(new QCocoaServices)
|
||||||
, mKeyboardMapper(new QCocoaKeyMapper)
|
, mKeyboardMapper(new QAppleKeyMapper)
|
||||||
{
|
{
|
||||||
logVersionInformation();
|
logVersionInformation();
|
||||||
|
|
||||||
@ -420,7 +420,7 @@ QVariant QCocoaIntegration::styleHint(StyleHint hint) const
|
|||||||
|
|
||||||
Qt::KeyboardModifiers QCocoaIntegration::queryKeyboardModifiers() const
|
Qt::KeyboardModifiers QCocoaIntegration::queryKeyboardModifiers() const
|
||||||
{
|
{
|
||||||
return QCocoaKeyMapper::queryKeyboardModifiers();
|
return QAppleKeyMapper::queryKeyboardModifiers();
|
||||||
}
|
}
|
||||||
|
|
||||||
QList<int> QCocoaIntegration::possibleKeys(const QKeyEvent *event) const
|
QList<int> QCocoaIntegration::possibleKeys(const QKeyEvent *event) const
|
||||||
|
@ -50,9 +50,9 @@
|
|||||||
#include "qcocoahelpers.h"
|
#include "qcocoahelpers.h"
|
||||||
#include "qcocoaapplication.h" // for custom application category
|
#include "qcocoaapplication.h" // for custom application category
|
||||||
#include "qcocoamenuloader.h"
|
#include "qcocoamenuloader.h"
|
||||||
#include "qcocoakeymapper.h"
|
|
||||||
#include <QtGui/private/qcoregraphics_p.h>
|
#include <QtGui/private/qcoregraphics_p.h>
|
||||||
#include <QtCore/qregularexpression.h>
|
#include <QtCore/qregularexpression.h>
|
||||||
|
#include <QtGui/private/qapplekeymapper_p.h>
|
||||||
|
|
||||||
#include <QtCore/QDebug>
|
#include <QtCore/QDebug>
|
||||||
|
|
||||||
@ -356,7 +356,7 @@ NSMenuItem *QCocoaMenuItem::sync()
|
|||||||
auto key = accel[0].key();
|
auto key = accel[0].key();
|
||||||
auto modifiers = accel[0].keyboardModifiers();
|
auto modifiers = accel[0].keyboardModifiers();
|
||||||
|
|
||||||
QChar cocoaKey = QCocoaKeyMapper::toCocoaKey(key);
|
QChar cocoaKey = QAppleKeyMapper::toCocoaKey(key);
|
||||||
if (cocoaKey.isNull())
|
if (cocoaKey.isNull())
|
||||||
cocoaKey = QChar(key).toLower().unicode();
|
cocoaKey = QChar(key).toLower().unicode();
|
||||||
// Similar to qt_mac_removePrivateUnicode change the delete key,
|
// Similar to qt_mac_removePrivateUnicode change the delete key,
|
||||||
@ -365,7 +365,7 @@ NSMenuItem *QCocoaMenuItem::sync()
|
|||||||
cocoaKey = QChar(NSDeleteCharacter);
|
cocoaKey = QChar(NSDeleteCharacter);
|
||||||
|
|
||||||
m_native.keyEquivalent = QStringView(&cocoaKey, 1).toNSString();
|
m_native.keyEquivalent = QStringView(&cocoaKey, 1).toNSString();
|
||||||
m_native.keyEquivalentModifierMask = QCocoaKeyMapper::toCocoaModifiers(modifiers);
|
m_native.keyEquivalentModifierMask = QAppleKeyMapper::toCocoaModifiers(modifiers);
|
||||||
} else
|
} else
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
|
@ -46,10 +46,10 @@
|
|||||||
#include "qcocoawindow.h"
|
#include "qcocoawindow.h"
|
||||||
#include "qnsview.h"
|
#include "qnsview.h"
|
||||||
#include "qcocoahelpers.h"
|
#include "qcocoahelpers.h"
|
||||||
#include "qcocoakeymapper.h"
|
|
||||||
|
|
||||||
#include <QtCore/qcoreapplication.h>
|
#include <QtCore/qcoreapplication.h>
|
||||||
#include <QtCore/qcoreevent.h>
|
#include <QtCore/qcoreevent.h>
|
||||||
|
#include <QtGui/private/qapplekeymapper_p.h>
|
||||||
|
|
||||||
static NSString *qt_mac_removePrivateUnicode(NSString *string)
|
static NSString *qt_mac_removePrivateUnicode(NSString *string)
|
||||||
{
|
{
|
||||||
@ -254,7 +254,7 @@ static NSString *qt_mac_removePrivateUnicode(NSString *string)
|
|||||||
QChar ch;
|
QChar ch;
|
||||||
int keyCode;
|
int keyCode;
|
||||||
ulong nativeModifiers = event.modifierFlags;
|
ulong nativeModifiers = event.modifierFlags;
|
||||||
Qt::KeyboardModifiers modifiers = QCocoaKeyMapper::fromCocoaModifiers(nativeModifiers);
|
Qt::KeyboardModifiers modifiers = QAppleKeyMapper::fromCocoaModifiers(nativeModifiers);
|
||||||
NSString *charactersIgnoringModifiers = event.charactersIgnoringModifiers;
|
NSString *charactersIgnoringModifiers = event.charactersIgnoringModifiers;
|
||||||
NSString *characters = event.characters;
|
NSString *characters = event.characters;
|
||||||
|
|
||||||
@ -264,7 +264,7 @@ static NSString *qt_mac_removePrivateUnicode(NSString *string)
|
|||||||
} else {
|
} else {
|
||||||
ch = QChar([charactersIgnoringModifiers characterAtIndex:0]);
|
ch = QChar([charactersIgnoringModifiers characterAtIndex:0]);
|
||||||
}
|
}
|
||||||
keyCode = QCocoaKeyMapper::fromCocoaKey(ch);
|
keyCode = QAppleKeyMapper::fromCocoaKey(ch);
|
||||||
} else {
|
} else {
|
||||||
// might be a dead key
|
// might be a dead key
|
||||||
ch = QChar::ReplacementCharacter;
|
ch = QChar::ReplacementCharacter;
|
||||||
|
@ -197,7 +197,7 @@ static QPoint mapWindowCoordinates(QWindow *source, QWindow *target, QPoint poin
|
|||||||
if (!target)
|
if (!target)
|
||||||
return NSDragOperationNone;
|
return NSDragOperationNone;
|
||||||
|
|
||||||
const auto modifiers = QCocoaKeyMapper::fromCocoaModifiers(NSApp.currentEvent.modifierFlags);
|
const auto modifiers = QAppleKeyMapper::fromCocoaModifiers(NSApp.currentEvent.modifierFlags);
|
||||||
const auto buttons = currentlyPressedMouseButtons();
|
const auto buttons = currentlyPressedMouseButtons();
|
||||||
const auto point = mapWindowCoordinates(m_platformWindow->window(), target, windowPoint);
|
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);
|
QPlatformDropQtResponse response(false, Qt::IgnoreAction);
|
||||||
QCocoaDrag* nativeDrag = QCocoaIntegration::instance()->drag();
|
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 buttons = currentlyPressedMouseButtons();
|
||||||
const auto point = mapWindowCoordinates(m_platformWindow->window(), target, windowPoint);
|
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
|
// this case won't send the matching release event, so we have to
|
||||||
// synthesize it here.
|
// synthesize it here.
|
||||||
m_buttons = currentlyPressedMouseButtons();
|
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 windowPoint = [self.window convertRectFromScreen:NSMakeRect(screenPoint.x, screenPoint.y, 1, 1)].origin;
|
||||||
NSPoint nsViewPoint = [self convertPoint: windowPoint fromView: nil];
|
NSPoint nsViewPoint = [self convertPoint: windowPoint fromView: nil];
|
||||||
|
@ -45,7 +45,7 @@
|
|||||||
{
|
{
|
||||||
ulong timestamp = [nsevent timestamp] * 1000;
|
ulong timestamp = [nsevent timestamp] * 1000;
|
||||||
ulong nativeModifiers = [nsevent modifierFlags];
|
ulong nativeModifiers = [nsevent modifierFlags];
|
||||||
Qt::KeyboardModifiers modifiers = QCocoaKeyMapper::fromCocoaModifiers(nativeModifiers);
|
Qt::KeyboardModifiers modifiers = QAppleKeyMapper::fromCocoaModifiers(nativeModifiers);
|
||||||
NSString *charactersIgnoringModifiers = [nsevent charactersIgnoringModifiers];
|
NSString *charactersIgnoringModifiers = [nsevent charactersIgnoringModifiers];
|
||||||
NSString *characters = [nsevent characters];
|
NSString *characters = [nsevent characters];
|
||||||
if (m_inputSource != characters) {
|
if (m_inputSource != characters) {
|
||||||
@ -74,7 +74,7 @@
|
|||||||
ch = QChar([charactersIgnoringModifiers characterAtIndex:0]);
|
ch = QChar([charactersIgnoringModifiers characterAtIndex:0]);
|
||||||
else if ([characters length] != 0)
|
else if ([characters length] != 0)
|
||||||
ch = QChar([characters characterAtIndex: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
|
// 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 timestamp = [nsevent timestamp] * 1000;
|
||||||
ulong nativeModifiers = [nsevent modifierFlags];
|
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
|
// 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().
|
// from Carbon or Cocoa, so leave it 0, as documented in QKeyEvent::nativeScanCode().
|
||||||
@ -238,7 +238,7 @@
|
|||||||
(lastKnownModifiers & mac_mask) ? QEvent::KeyRelease
|
(lastKnownModifiers & mac_mask) ? QEvent::KeyRelease
|
||||||
: QEvent::KeyPress,
|
: QEvent::KeyPress,
|
||||||
qtCode,
|
qtCode,
|
||||||
modifiers ^ QCocoaKeyMapper::fromCocoaModifiers(mac_mask),
|
modifiers ^ QAppleKeyMapper::fromCocoaModifiers(mac_mask),
|
||||||
nativeScanCode, nativeVirtualKey,
|
nativeScanCode, nativeVirtualKey,
|
||||||
nativeModifiers ^ mac_mask);
|
nativeModifiers ^ mac_mask);
|
||||||
}
|
}
|
||||||
|
@ -279,7 +279,7 @@
|
|||||||
QCocoaDrag* nativeDrag = QCocoaIntegration::instance()->drag();
|
QCocoaDrag* nativeDrag = QCocoaIntegration::instance()->drag();
|
||||||
nativeDrag->setLastMouseEvent(theEvent, self);
|
nativeDrag->setLastMouseEvent(theEvent, self);
|
||||||
|
|
||||||
const auto modifiers = QCocoaKeyMapper::fromCocoaModifiers(theEvent.modifierFlags);
|
const auto modifiers = QAppleKeyMapper::fromCocoaModifiers(theEvent.modifierFlags);
|
||||||
auto button = cocoaButton2QtButton(theEvent);
|
auto button = cocoaButton2QtButton(theEvent);
|
||||||
if (button == Qt::LeftButton && m_sendUpAsRightButton)
|
if (button == Qt::LeftButton && m_sendUpAsRightButton)
|
||||||
button = Qt::RightButton;
|
button = Qt::RightButton;
|
||||||
@ -678,7 +678,7 @@
|
|||||||
// after scrolling in Qt Creator: not taking the phase into account causes
|
// 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.
|
// the end of the event stream to be interpreted as font size changes.
|
||||||
if (theEvent.momentumPhase == NSEventPhaseNone)
|
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.
|
// "isInverted": natural OS X scrolling, inverted from the Qt/other platform/Jens perspective.
|
||||||
bool isInverted = [theEvent isDirectionInvertedFromDevice];
|
bool isInverted = [theEvent isDirectionInvertedFromDevice];
|
||||||
|
@ -109,7 +109,7 @@ Q_GLOBAL_STATIC(QCocoaTabletDeviceDataHash, tabletDeviceDataHash)
|
|||||||
if (rotation > 180.0)
|
if (rotation > 180.0)
|
||||||
rotation -= 360.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;
|
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",
|
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",
|
||||||
|
@ -50,6 +50,8 @@ QT_END_NAMESPACE
|
|||||||
|
|
||||||
- (instancetype)initWithQIOSScreen:(QT_PREPEND_NAMESPACE(QIOSScreen) *)screen;
|
- (instancetype)initWithQIOSScreen:(QT_PREPEND_NAMESPACE(QIOSScreen) *)screen;
|
||||||
- (void)updateProperties;
|
- (void)updateProperties;
|
||||||
|
- (NSArray*)keyCommands;
|
||||||
|
- (void)handleShortcut:(UIKeyCommand*)keyCommand;
|
||||||
|
|
||||||
#ifndef Q_OS_TVOS
|
#ifndef Q_OS_TVOS
|
||||||
@property (nonatomic, assign) UIInterfaceOrientation lockedOrientation;
|
@property (nonatomic, assign) UIInterfaceOrientation lockedOrientation;
|
||||||
|
@ -42,12 +42,14 @@
|
|||||||
|
|
||||||
#include <QtCore/qscopedvaluerollback.h>
|
#include <QtCore/qscopedvaluerollback.h>
|
||||||
#include <QtCore/private/qcore_mac_p.h>
|
#include <QtCore/private/qcore_mac_p.h>
|
||||||
|
#include <QtGui/private/qapplekeymapper_p.h>
|
||||||
|
|
||||||
#include <QtGui/QGuiApplication>
|
#include <QtGui/QGuiApplication>
|
||||||
#include <QtGui/QWindow>
|
#include <QtGui/QWindow>
|
||||||
#include <QtGui/QScreen>
|
#include <QtGui/QScreen>
|
||||||
|
|
||||||
#include <QtGui/private/qwindow_p.h>
|
#include <QtGui/private/qwindow_p.h>
|
||||||
|
#include <QtGui/private/qguiapplication_p.h>
|
||||||
|
|
||||||
#include "qiosintegration.h"
|
#include "qiosintegration.h"
|
||||||
#include "qiosscreen.h"
|
#include "qiosscreen.h"
|
||||||
@ -523,5 +525,36 @@
|
|||||||
#endif
|
#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
|
@end
|
||||||
|
|
||||||
|
@ -56,6 +56,7 @@ QT_END_NAMESPACE
|
|||||||
- (instancetype)initWithQIOSWindow:(QT_PREPEND_NAMESPACE(QIOSWindow) *)window;
|
- (instancetype)initWithQIOSWindow:(QT_PREPEND_NAMESPACE(QIOSWindow) *)window;
|
||||||
- (void)sendUpdatedExposeEvent;
|
- (void)sendUpdatedExposeEvent;
|
||||||
- (BOOL)isActiveWindow;
|
- (BOOL)isActiveWindow;
|
||||||
|
- (bool)handlePresses:(NSSet<UIPress *> *)presses eventType:(QEvent::Type)type;
|
||||||
@property (nonatomic, assign) QT_PREPEND_NAMESPACE(QIOSWindow) *platformWindow;
|
@property (nonatomic, assign) QT_PREPEND_NAMESPACE(QIOSWindow) *platformWindow;
|
||||||
@end
|
@end
|
||||||
|
|
||||||
|
@ -52,6 +52,7 @@
|
|||||||
#include <QtGui/qpointingdevice.h>
|
#include <QtGui/qpointingdevice.h>
|
||||||
#include <QtGui/private/qguiapplication_p.h>
|
#include <QtGui/private/qguiapplication_p.h>
|
||||||
#include <QtGui/private/qwindow_p.h>
|
#include <QtGui/private/qwindow_p.h>
|
||||||
|
#include <QtGui/private/qapplekeymapper_p.h>
|
||||||
#include <qpa/qwindowsysteminterface_p.h>
|
#include <qpa/qwindowsysteminterface_p.h>
|
||||||
|
|
||||||
Q_LOGGING_CATEGORY(lcQpaTablet, "qt.qpa.input.tablet")
|
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());
|
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) {
|
switch (press.type) {
|
||||||
case UIPressTypeUpArrow: return Qt::Key_Up;
|
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 UIPressTypeMenu: return Qt::Key_Menu;
|
||||||
case UIPressTypePlayPause: return Qt::Key_MediaTogglePlayPause;
|
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;
|
return Qt::Key_unknown;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -593,32 +604,52 @@ Q_LOGGING_CATEGORY(lcQpaTablet, "qt.qpa.input.tablet")
|
|||||||
|
|
||||||
bool handled = false;
|
bool handled = false;
|
||||||
for (UIPress* press in presses) {
|
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)
|
if (key == Qt::Key_unknown)
|
||||||
continue;
|
continue;
|
||||||
if (QWindowSystemInterface::handleKeyEvent(self.platformWindow->window(), type, key, Qt::NoModifier))
|
if (QWindowSystemInterface::handleKeyEvent(self.platformWindow->window(), type, key, qtModifiers))
|
||||||
handled = true;
|
handled = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
return handled;
|
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
|
- (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];
|
[super pressesBegan:presses withEvent:event];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)pressesChanged:(NSSet<UIPress *> *)presses withEvent:(UIPressesEvent *)event
|
- (void)pressesChanged:(NSSet<UIPress *> *)presses withEvent:(UIPressesEvent *)event
|
||||||
{
|
{
|
||||||
if (![self processPresses:presses withType:QEvent::KeyPress])
|
if (![self handlePresses:presses eventType:QEvent::KeyPress])
|
||||||
[super pressesChanged:presses withEvent:event];
|
[super pressesBegan:presses withEvent:event];
|
||||||
|
[super pressesChanged:presses withEvent:event];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (void)pressesEnded:(NSSet<UIPress *> *)presses withEvent:(UIPressesEvent *)event
|
- (void)pressesEnded:(NSSet<UIPress *> *)presses withEvent:(UIPressesEvent *)event
|
||||||
{
|
{
|
||||||
if (![self processPresses:presses withType:QEvent::KeyRelease])
|
if (![self handlePresses:presses eventType:QEvent::KeyRelease])
|
||||||
[super pressesEnded:presses withEvent:event];
|
[super pressesBegan:presses withEvent:event];
|
||||||
|
[super pressesEnded:presses withEvent:event];
|
||||||
}
|
}
|
||||||
|
|
||||||
- (BOOL)canPerformAction:(SEL)action withSender:(id)sender
|
- (BOOL)canPerformAction:(SEL)action withSender:(id)sender
|
||||||
|
Loading…
Reference in New Issue
Block a user