VirtualBox

Ignore:
Timestamp:
Jan 20, 2016 10:27:56 AM (9 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
105133
Message:

FE/Qt: Qt5 migration (part 68): Implementing keyboard handling for Qt5 under Mac OS X.

Location:
trunk/src/VBox/Frontends/VirtualBox/src
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Frontends/VirtualBox/src/runtime/UIKeyboardHandler.cpp

    r59413 r59414  
    4949/* COM includes: */
    5050# include "CKeyboard.h"
     51
     52/* Other VBox includes: */
     53# ifdef Q_WS_MAC
     54#  if QT_VERSION >= 0x050000
     55#   include "iprt/cpp/utils.h"
     56#  endif /* QT_VERSION >= 0x050000 */
     57# endif /* Q_WS_MAC */
    5158
    5259#endif /* !VBOX_WITH_PRECOMPILED_HEADERS */
     
    946953# if defined(Q_WS_MAC)
    947954
    948 #  warning "implement me!"
     955    /* Acquire carbon event reference from the cocoa one: */
     956    EventRef event = static_cast<EventRef>(darwinCocoaToCarbonEvent(pMessage));
     957
     958    /* Depending on event kind: */
     959    const UInt32 uEventKind = ::GetEventKind(event);
     960    switch(uEventKind)
     961    {
     962        /* Watch for simple key-events: */
     963        case kEventRawKeyDown:
     964        case kEventRawKeyRepeat:
     965        case kEventRawKeyUp:
     966        {
     967            /* Acquire keycode: */
     968            UInt32 uKeyCode = ~0U;
     969            ::GetEventParameter(event, kEventParamKeyCode, typeUInt32,
     970                                NULL, sizeof(uKeyCode), NULL, &uKeyCode);
     971
     972            /* The usb keyboard driver translates these codes to different virtual
     973             * keycodes depending of the keyboard type. There are ANSI, ISO, JIS
     974             * and unknown. For European keyboards (ISO) the key 0xa and 0x32 have
     975             * to be switched. Here we are doing this at runtime, cause the user
     976             * can have more than one keyboard (of different type), where he may
     977             * switch at will all the time. Default is the ANSI standard as defined
     978             * in g_aDarwinToSet1. Please note that the "~" on some English ISO
     979             * keyboards will be wrongly swapped. This can maybe fixed by
     980             * using a Apple keyboard layout in the guest. */
     981            if (   (uKeyCode == 0xa || uKeyCode == 0x32)
     982                && KBGetLayoutType(LMGetKbdType()) == kKeyboardISO)
     983                uKeyCode = 0x3c - uKeyCode;
     984
     985            /* Translate keycode to set 1 scan code: */
     986            unsigned uScanCode = ::DarwinKeycodeToSet1Scancode(uKeyCode);
     987
     988            /* If scan code is valid: */
     989            if (uScanCode)
     990            {
     991                /* Calculate flags: */
     992                int iFlags = 0;
     993                if (uEventKind != kEventRawKeyUp)
     994                    iFlags |= KeyPressed;
     995                if (uScanCode & VBOXKEY_EXTENDED)
     996                    iFlags |= KeyExtended;
     997                /** @todo KeyPause, KeyPrint. */
     998                uScanCode &= VBOXKEY_SCANCODE_MASK;
     999
     1000                /* Get the unicode string (if present): */
     1001                AssertCompileSize(wchar_t, 2);
     1002                AssertCompileSize(UniChar, 2);
     1003                ByteCount cbWritten = 0;
     1004                wchar_t ucs[8];
     1005                if (::GetEventParameter(event, kEventParamKeyUnicodes, typeUnicodeText,
     1006                                        NULL, sizeof(ucs), &cbWritten, &ucs[0]) != 0)
     1007                    cbWritten = 0;
     1008                ucs[cbWritten / sizeof(wchar_t)] = 0; /* The api doesn't terminate it. */
     1009
     1010                /* Finally, handle parsed key-event: */
     1011                fResult = keyEvent(uKeyCode, uScanCode, iFlags, uScreenId, ucs[0] ? ucs : NULL);
     1012            }
     1013
     1014            break;
     1015        }
     1016        /* Watch for modifier key-events: */
     1017        case kEventRawKeyModifiersChanged:
     1018        {
     1019            /* Acquire new modifier mask, it may contain
     1020             * multiple modifier changes, kind of annoying: */
     1021            UInt32 uNewMask = 0;
     1022            ::GetEventParameter(event, kEventParamKeyModifiers, typeUInt32,
     1023                                NULL, sizeof(uNewMask), NULL, &uNewMask);
     1024
     1025            /* Adjust new modifier mask to distinguish left/right modifiers: */
     1026            uNewMask = ::DarwinAdjustModifierMask(uNewMask, pMessage);
     1027
     1028            /* Determine what is really changed: */
     1029            const UInt32 changed = uNewMask ^ m_uDarwinKeyModifiers;
     1030            if (changed)
     1031            {
     1032                for (UInt32 bit = 0; bit < 32; ++bit)
     1033                {
     1034                    /* Skip unchanged bits: */
     1035                    if (!(changed & (1 << bit)))
     1036                        continue;
     1037                    /* Acquire set 1 scan code from new mask: */
     1038                    unsigned uScanCode = ::DarwinModifierMaskToSet1Scancode(1 << bit);
     1039                    /* Skip invalid scan codes: */
     1040                    if (!uScanCode)
     1041                        continue;
     1042                    /* Acquire darwin keycode from new mask: */
     1043                    unsigned uKeyCode = ::DarwinModifierMaskToDarwinKeycode(1 << bit);
     1044                    /* Assert invalid keycodes: */
     1045                    Assert(uKeyCode);
     1046
     1047                    /* For non-lockable modifier: */
     1048                    if (!(uScanCode & VBOXKEY_LOCK))
     1049                    {
     1050                        /* Calculate flags: */
     1051                        unsigned uFlags = (uNewMask & (1 << bit)) ? KeyPressed : 0;
     1052                        if (uScanCode & VBOXKEY_EXTENDED)
     1053                            uFlags |= KeyExtended;
     1054                        uScanCode &= VBOXKEY_SCANCODE_MASK;
     1055
     1056                        /* Finally, handle parsed key-event: */
     1057                        keyEvent(uKeyCode, uScanCode & 0xff, uFlags, uScreenId);
     1058                    }
     1059                    /* For lockable modifier: */
     1060                    else
     1061                    {
     1062                        /* Calculate flags: */
     1063                        unsigned uFlags = 0;
     1064                        if (uScanCode & VBOXKEY_EXTENDED)
     1065                            uFlags |= KeyExtended;
     1066                        uScanCode &= VBOXKEY_SCANCODE_MASK;
     1067
     1068                        /* Finally, handle parsed press/release pair: */
     1069                        keyEvent(uKeyCode, uScanCode, uFlags | KeyPressed, uScreenId);
     1070                        keyEvent(uKeyCode, uScanCode, uFlags, uScreenId);
     1071                    }
     1072                }
     1073            }
     1074
     1075            /* Remember new modifier mask: */
     1076            m_uDarwinKeyModifiers = uNewMask;
     1077
     1078            /* Always return true here because we'll otherwise getting a Qt event
     1079             * we don't want and that will only cause the Pause warning to pop up: */
     1080            fResult = true;
     1081
     1082            break;
     1083        }
     1084        default:
     1085            break;
     1086    }
    9491087
    9501088# elif defined(Q_WS_WIN)
     
    15871725#if QT_VERSION < 0x050000
    15881726    return m_views[m_iKeyboardHookViewIndex]->macEvent(pvCocoaEvent, event);
    1589 #endif /* QT_VERSION < 0x050000 */
     1727#else /* QT_VERSION >= 0x050000 */
     1728    Q_UNUSED(event);
     1729    QByteArray eventType("mac_generic_NSEvent");
     1730    return m_views[m_iKeyboardHookViewIndex]->nativeEvent(eventType, unconst(pvCocoaEvent));
     1731#endif /* QT_VERSION >= 0x050000 */
    15901732}
    15911733
  • trunk/src/VBox/Frontends/VirtualBox/src/runtime/UIMachineView.cpp

    r59413 r59414  
    18891889# if defined(Q_WS_MAC)
    18901890
    1891 #  warning "implement me!"
     1891    /* Make sure it's generic NSEvent: */
     1892    if (eventType != "mac_generic_NSEvent")
     1893        return false;
     1894    EventRef event = static_cast<EventRef>(darwinCocoaToCarbonEvent(pMessage));
     1895
     1896    /* Check if some NSEvent should be filtered out.
     1897     * Returning @c true means filtering-out,
     1898     * Returning @c false means passing event to Qt. */
     1899    switch(::GetEventClass(event))
     1900    {
     1901        /* Watch for keyboard-events: */
     1902        case kEventClassKeyboard:
     1903        {
     1904            switch(::GetEventKind(event))
     1905            {
     1906                /* Watch for key-events: */
     1907                case kEventRawKeyDown:
     1908                case kEventRawKeyRepeat:
     1909                case kEventRawKeyUp:
     1910                case kEventRawKeyModifiersChanged:
     1911                {
     1912                    /* Delegate key-event handling to the keyboard-handler: */
     1913                    return machineLogic()->keyboardHandler()->nativeEventFilter(pMessage, screenId());
     1914                }
     1915                default:
     1916                    break;
     1917            }
     1918            break;
     1919        }
     1920        default:
     1921            break;
     1922    }
    18921923
    18931924# elif defined(Q_WS_WIN)
  • trunk/src/VBox/Frontends/VirtualBox/src/widgets/UIHostComboEditor.cpp

    r59309 r59414  
    586586    if (eventType != "mac_generic_NSEvent")
    587587        return QLineEdit::nativeEvent(eventType, pMessage, pResult);
    588     EventRef event = (EventRef)darwinCocoaToCarbonEvent(pMessage);
     588    EventRef event = static_cast<EventRef>(darwinCocoaToCarbonEvent(pMessage));
    589589
    590590    /* Check if some NSEvent should be filtered out.
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette