diff --git a/src/SFML/Window/CMakeLists.txt b/src/SFML/Window/CMakeLists.txt index 3f49678d..edad6e76 100644 --- a/src/SFML/Window/CMakeLists.txt +++ b/src/SFML/Window/CMakeLists.txt @@ -68,7 +68,9 @@ else() # MACOSX ${SRCROOT}/OSX/cg_sf_conversion.hpp ${SRCROOT}/OSX/cg_sf_conversion.cpp ${SRCROOT}/OSX/InputImpl.mm - ${SRCROOT}/OSX/InputImpl.hpp + ${SRCROOT}/OSX/InputImpl.hpp + ${SRCROOT}/OSX/HIDInputManager.hpp + ${SRCROOT}/OSX/HIDInputManager.mm ${SRCROOT}/OSX/JoystickImpl.cpp ${SRCROOT}/OSX/JoystickImpl.hpp ${SRCROOT}/OSX/SFApplication.h @@ -105,7 +107,7 @@ if(WINDOWS) elseif(LINUX) set(WINDOW_EXT_LIBS ${WINDOW_EXT_LIBS} ${X11_X11_LIB} ${X11_Xrandr_LIB}) elseif(MACOSX) - set(WINDOW_EXT_LIBS ${WINDOW_EXT_LIBS} "-framework Foundation -framework AppKit -framework IOKit") + set(WINDOW_EXT_LIBS ${WINDOW_EXT_LIBS} "-framework Foundation -framework AppKit -framework IOKit -framework Carbon") endif() # define the sfml-window target diff --git a/src/SFML/Window/OSX/HIDInputManager.hpp b/src/SFML/Window/OSX/HIDInputManager.hpp new file mode 100644 index 00000000..e66612a5 --- /dev/null +++ b/src/SFML/Window/OSX/HIDInputManager.hpp @@ -0,0 +1,178 @@ +//////////////////////////////////////////////////////////// +// +// SFML - Simple and Fast Multimedia Library +// Copyright (C) 2007-2011 Marco Antognini (antognini.marco@gmail.com), +// Laurent Gomila (laurent.gom@gmail.com), +// +// This software is provided 'as-is', without any express or implied warranty. +// In no event will the authors be held liable for any damages arising from the use of this software. +// +// Permission is granted to anyone to use this software for any purpose, +// including commercial applications, and to alter it and redistribute it freely, +// subject to the following restrictions: +// +// 1. The origin of this software must not be misrepresented; +// you must not claim that you wrote the original software. +// If you use this software in a product, an acknowledgment +// in the product documentation would be appreciated but is not required. +// +// 2. Altered source versions must be plainly marked as such, +// and must not be misrepresented as being the original software. +// +// 3. This notice may not be removed or altered from any source distribution. +// +//////////////////////////////////////////////////////////// + +#ifndef SFML_HIDINPUTMANAGER_HPP +#define SFML_HIDINPUTMANAGER_HPP + +//////////////////////////////////////////////////////////// +// Headers +//////////////////////////////////////////////////////////// +#include +#include +#include +#include +#include +#include +#include + +namespace sf +{ +namespace priv +{ +//////////////////////////////////////////////////////////// +/// \brief This class manage as a singleton instance the +/// keyboard and mouse states. It's only purpose is +/// to help sf::priv::InputImpl class. +/// +/// sf::priv::JoystickImpl is not concerned by this class. +/// +//////////////////////////////////////////////////////////// +class HIDInputManager : NonCopyable +{ +public : + + //////////////////////////////////////////////////////////// + /// \brief Get the unique instance of the class + /// + /// \note Private use only + /// + /// \return Reference to the HIDInputManager instance + /// + //////////////////////////////////////////////////////////// + static HIDInputManager& GetInstance(); + + //////////////////////////////////////////////////////////// + /// \brief Check if a key is pressed + /// + /// \param key Key to check + /// + /// \return True if the key is pressed, false otherwise + /// + //////////////////////////////////////////////////////////// + bool IsKeyPressed(Keyboard::Key key); + + //////////////////////////////////////////////////////////// + /// \brief Check if a mouse button is pressed + /// + /// \param button Button to check + /// + /// \return True if the button is pressed, false otherwise + /// + //////////////////////////////////////////////////////////// + bool IsMouseButtonPressed(Mouse::Button button); + + //////////////////////////////////////////////////////////// + /// Try to convert a character into a SFML key code. + /// + /// Return sf::Keyboard::KeyCount if it doesn't match any 'localized' keys. + /// + /// By 'localized' I mean keys that depend on the keyboard layout + /// and might not be the same as the US keycode in some country + /// (e.g. the keys 'Y' and 'Z' are switched on QWERTZ keyboard and + /// US keyboard layouts.) + /// + //////////////////////////////////////////////////////////// + static Keyboard::Key LocalizedKeys(UniChar ch); + + //////////////////////////////////////////////////////////// + /// Try to convert a virtual keycode into a SFML key code. + /// + /// Return sf::Keyboard::KeyCount if the keycode is unknown. + /// + //////////////////////////////////////////////////////////// + static Keyboard::Key NonLocalizedKeys(UniChar virtualKeycode); + +private : + + //////////////////////////////////////////////////////////// + /// \brief Default constructor + /// + //////////////////////////////////////////////////////////// + HIDInputManager(); + + //////////////////////////////////////////////////////////// + /// \brief Destructor + /// + //////////////////////////////////////////////////////////// + ~HIDInputManager(); + + //////////////////////////////////////////////////////////// + /// \brief Initialize the keyboard part of this class + /// + /// If something went wrong FreeUp is called + /// + //////////////////////////////////////////////////////////// + void InitializeKeyboard(); + + //////////////////////////////////////////////////////////// + /// \brief Release all resources + /// + /// Close all connections to any devices, if required + /// Set amIValid to false + /// + //////////////////////////////////////////////////////////// + void FreeUp(); + + //////////////////////////////////////////////////////////// + /// \brief Create a mask (dictionary) for an IOHIDManager + /// + /// \param page HID page + /// \param usage HID usage page + /// \return a retained CFDictionaryRef + /// + //////////////////////////////////////////////////////////// + static CFDictionaryRef CopyDevicesMaskForManager(UInt32 page, UInt32 usage); + + //////////////////////////////////////////////////////////// + /// \brief Converte a HID key usage to it's conrresponding virtual code + /// + /// See IOHIDUsageTables.h + /// + /// \param usage Any kHIDUsage_Keyboard* usage + /// \return the virtual code associate to the given HID key usage + /// or 0xff if it is associate to no virtual code + /// + //////////////////////////////////////////////////////////// + static UInt8 UsageToVirtualCode(UInt32 usage); + +private : + + //////////////////////////////////////////////////////////// + // Member data + //////////////////////////////////////////////////////////// + bool amIValid; ///< If any error occurs this variable is false + CFDataRef myLayoutData; ///< CFData containing the layout + UCKeyboardLayout* myLayout; ///< Current Keyboard Layout + IOHIDManagerRef myManager; ///< HID Manager + IOHIDElementRef myKeys[Keyboard::KeyCount]; ///< All the keys on the current keyboard + /* myKeys index correspond to sf::Keyboard::Key enum */ + /* if no key is assigned to a key XYZ then myKeys[XYZ] = 0 */ +}; + +} // namespace priv + +} // namespace sf + +#endif \ No newline at end of file diff --git a/src/SFML/Window/OSX/HIDInputManager.mm b/src/SFML/Window/OSX/HIDInputManager.mm new file mode 100644 index 00000000..e9165a9c --- /dev/null +++ b/src/SFML/Window/OSX/HIDInputManager.mm @@ -0,0 +1,877 @@ +//////////////////////////////////////////////////////////// +// +// SFML - Simple and Fast Multimedia Library +// Copyright (C) 2007-2011 Marco Antognini (antognini.marco@gmail.com), +// Laurent Gomila (laurent.gom@gmail.com), +// +// This software is provided 'as-is', without any express or implied warranty. +// In no event will the authors be held liable for any damages arising from the use of this software. +// +// Permission is granted to anyone to use this software for any purpose, +// including commercial applications, and to alter it and redistribute it freely, +// subject to the following restrictions: +// +// 1. The origin of this software must not be misrepresented; +// you must not claim that you wrote the original software. +// If you use this software in a product, an acknowledgment +// in the product documentation would be appreciated but is not required. +// +// 2. Altered source versions must be plainly marked as such, +// and must not be misrepresented as being the original software. +// +// 3. This notice may not be removed or altered from any source distribution. +// +//////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////// +// Headers +//////////////////////////////////////////////////////////// +#include +#include +#include +#include + +namespace sf +{ +namespace priv +{ +//////////////////////////////////////////////////////////// +HIDInputManager& HIDInputManager::GetInstance() +{ + static HIDInputManager instance; + return instance; +} + + +//////////////////////////////////////////////////////////// +bool HIDInputManager::IsKeyPressed(Keyboard::Key key) +{ + if (!amIValid) { + sf::Err() << "HIDInputManager is invalid." << std::endl; + return false; + } + + // Have we an associate IOHIDElementRef to that key ? + if (myKeys[key] == 0) { // No + + sf::Err() << key + << " is not associate to any IOHIDElementRef." + << std::endl; + + return false; + + } else { // Yes + + IOHIDValueRef value = 0; + + IOHIDDeviceRef device = IOHIDElementGetDevice(myKeys[key]); + IOHIDDeviceGetValue(device, myKeys[key], &value); + + if (!value) { + + // This means some kind of error / deconnection so we remove this + // element from our keys + + CFRelease(myKeys[key]); + myKeys[key] = 0; + + sf::Err() << key + << " is dead (cannot access its value)." + << std::endl; + + return false; + + } else if (IOHIDValueGetIntegerValue(value) == 1) { + + // This means the key is pressed + return true; + + } else { + + // This means the key is released + return false; + } + + } +} + + +//////////////////////////////////////////////////////////// +bool HIDInputManager::IsMouseButtonPressed(Mouse::Button button) +{ + if (!amIValid) { + sf::Err() << "HIDInputManager is invalid." << std::endl; + return false; + } + + // @to be implemented + return false; +} + + +//////////////////////////////////////////////////////////// +HIDInputManager::HIDInputManager() +: amIValid(true) +, myLayoutData(0) +, myLayout(0) +, myManager(0) +{ + // And initialize myKeys with 0s. + std::fill(myKeys, myKeys + Keyboard::KeyCount, (IOHIDElementRef)0); + + // Get the current keyboard layout + TISInputSourceRef tis = TISCopyCurrentKeyboardLayoutInputSource(); + myLayoutData = (CFDataRef)TISGetInputSourceProperty(tis, + kTISPropertyUnicodeKeyLayoutData); + + if (myLayoutData == 0) { + sf::Err() << "Cannot get the keyboard layout" << std::endl; + FreeUp(); + return; + } + + // Keep a reference for ourself + CFRetain(myLayoutData); + myLayout = (UCKeyboardLayout *)CFDataGetBytePtr(myLayoutData); + + // The TIS is no more needed + CFRelease(tis); + + // Create an HID Manager reference + myManager = IOHIDManagerCreate(kCFAllocatorDefault, kIOHIDOptionsTypeNone); + + // Open the HID Manager reference + IOReturn openStatus = IOHIDManagerOpen(myManager, kIOHIDOptionsTypeNone); + + if (openStatus != kIOReturnSuccess) { + sf::Err() << "Error when opening the HID manager" << std::endl; + + FreeUp(); + return; + } + + // Initialize the keyboard + InitializeKeyboard(); + + if (!amIValid) { + return; // Something went wrong + } + + // TODO init mouse +} + + +//////////////////////////////////////////////////////////// +HIDInputManager::~HIDInputManager() +{ + FreeUp(); +} + + +void HIDInputManager::InitializeKeyboard() +{ + //////////////////////////////////////////////////////////// + // The purpose of this function is to initalize myKeys so we can get + // the associate IOHIDElementRef of a sf::Keyboard::Key in constant time. + + + // Filter and keep only the keyboards + CFDictionaryRef mask = CopyDevicesMaskForManager(kHIDPage_GenericDesktop, + kHIDUsage_GD_Keyboard); + + IOHIDManagerSetDeviceMatching(myManager, mask); + + CFRelease(mask); + mask = 0; + + CFSetRef keyboards = IOHIDManagerCopyDevices(myManager); + if (keyboards == NULL) { + sf::Err() << "Cannot find any keyboard (1)" << std::endl; + FreeUp(); + return; + } + + // Is there at least one keyboard ? + CFIndex keyboardCount = CFSetGetCount(keyboards); + if (keyboardCount < 1) { + sf::Err() << "Cannot find any keyboard (2)" << std::endl; + CFRelease(keyboards); + FreeUp(); + return; + } + + // Get the first keyboard + CFTypeRef devicesArray[keyboardCount]; + CFSetGetValues(keyboards, devicesArray); + + IOHIDDeviceRef keyboard = (IOHIDDeviceRef)devicesArray[0]; + + CFArrayRef keys = IOHIDDeviceCopyMatchingElements(keyboard, + NULL, + kIOHIDOptionsTypeNone); + + // Release unused stuff + CFRelease(keyboards); + + if (keys == NULL) { + sf::Err() << "We got a keyboard without any keys (1)" << std::endl; + FreeUp(); + return; + } + + // How many elements are there ? + CFIndex keysCount = CFArrayGetCount(keys); + + if (keysCount == 0) { + sf::Err() << "We got a keyboard without any keys (2)" << std::endl; + CFRelease(keys); + FreeUp(); + return; + } + + // Go through all connected elements. + for (int i = 0; i < keysCount; ++i) { + IOHIDElementRef aKey = (IOHIDElementRef) CFArrayGetValueAtIndex(keys, i); + + // Skip non-matching keys elements + if (IOHIDElementGetUsagePage(aKey) != kHIDPage_KeyboardOrKeypad) { + continue; + } + + // Get its virtual code + UInt32 usageCode = IOHIDElementGetUsage(aKey); + UInt8 virtualCode = UsageToVirtualCode(usageCode); + + if (virtualCode == 0xff) { + continue; // no corresponding virtual code -> skip + } + + // Now translate the virtual code to unicode according to + // the current keyboard layout + + UInt32 deadKeyState = 0; + // unicode string length is usually less or equal to 4 + UniCharCount maxStringLength = 4; + UniCharCount actualStringLength = 0; + UniChar unicodeString[maxStringLength]; + + OSStatus error; + + error = UCKeyTranslate(myLayout, // current layout + virtualCode, // our key + kUCKeyActionDown, // or kUCKeyActionUp ? + 0x100, // no modifiers + LMGetKbdType(), // keyboard's type + kUCKeyTranslateNoDeadKeysBit,// some sort of option + &deadKeyState, // unused stuff + maxStringLength, // our memory limit + &actualStringLength, // length of what we get + unicodeString); // what we get + + if (error == noErr) { + // Translation went fine + + // The corresponding SFML key code + Keyboard::Key code = Keyboard::KeyCount; + + // First we look if the key down is from a list of caracter + // that depend on keyboard localization. + if (actualStringLength > 0) { + code = LocalizedKeys(unicodeString[0]); + } + + // The key is not a localized one, so we try to find a corresponding + // code through virtual key code. + if (code == Keyboard::KeyCount) { + code = NonLocalizedKeys(virtualCode); + } + + // A code was found, wonderful! + if (code != Keyboard::KeyCount) { + + // Last step : verify that the key was not found twice or more + + // Some keys (modifiers) appears to be twice on my keyboard + // I've no idea why +// if (myKeys[code] != 0) { +// UInt32 firstUsageCode = IOHIDElementGetUsage(myKeys[code]); +// sf::Err() << "The current keyboard has several times the " +// << "same keys. Only the first one is considered " +// << "as valid. sf::Keyboard::Key is " +// << code +// << ", virtual key code is 0x" +// << std::hex +// << (UInt32)virtualCode +// << " and HID usage code is 0x" +// << usageCode +// << ". First HID usage code is 0x" +// << firstUsageCode +// << std::dec +// << "." +// << std::endl; +// } + + if (myKeys[code] == 0) { + + // Ok, everything went fine. Now we have a unique + // corresponding sf::Keyboard::Key to one IOHIDElementRef. + + myKeys[code] = aKey; + + // And don't forget to keep the reference alive for our usage + CFRetain(myKeys[code]); + + } + + } + + //////////////////////////////////////////////////////////// + // These are known to be unbound : + // Supposed Virtual | HID | Supposed Key + // =============================================== + // 0x1b | 0x2d | Hyphen + // 0x39 | 0x39 | CapsLock + // 0x47 | 0x53 | NumLock + // 0x4c | 0x58 | Keypad Enter + // 0x41 | 0x63 | Keypad Period + // 0x6e | 0x65 | Application + // 0x51 | 0x67 | Keypad Equal + // 0x4c | 0x77 | Select + +// else { // The key is unknown. +// sf::Err() << "This is an unknow key. Virtual key code is 0x" +// << std::hex +// << (UInt32)virtualCode +// << " and HID usage code is 0x" +// << usageCode +// << std::dec +// << "." +// << std::endl; +// } + + } /* if (error == noErr) */ + + else { + sf::Err() << "Cannot translate the virtual key code, error : " + << error + << std::endl; + } + + } /* for (int i = 0; i < keysCount; ++i) */ + + CFRelease(keys); + + //////////////////////////////////////////////////////////// + // At this point myKeys is filled with as many IOHIDElementRef as possible +} + + +//////////////////////////////////////////////////////////// +void HIDInputManager::FreeUp() +{ + amIValid = false; + + if (myLayoutData != 0) CFRelease(myLayoutData); + // Do not release myLayout ! It is owned by myLayoutData. + if (myManager != 0) CFRelease(myManager); + + for (unsigned int i = 0; i < Keyboard::KeyCount; ++i) { + if (myKeys[i] != 0) { + CFRelease(myKeys[i]); + } + } +} + + +//////////////////////////////////////////////////////////// +CFDictionaryRef HIDInputManager::CopyDevicesMaskForManager(UInt32 page, UInt32 usage) +{ + // Create the dictionary. + CFMutableDictionaryRef dict = CFDictionaryCreateMutable(kCFAllocatorDefault, 2, + &kCFTypeDictionaryKeyCallBacks, + &kCFTypeDictionaryValueCallBacks); + + // Add the page value. + CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberIntType, &page); + CFDictionarySetValue(dict, CFSTR(kIOHIDDeviceUsagePageKey), value); + CFRelease(value); + + // Add the usage value (which is only valid if page value exists). + value = CFNumberCreate(kCFAllocatorDefault, kCFNumberIntType, &usage); + CFDictionarySetValue(dict, CFSTR(kIOHIDDeviceUsageKey), value); + CFRelease(value); + + return dict; +} + + +//////////////////////////////////////////////////////////// +UInt8 HIDInputManager::UsageToVirtualCode(UInt32 usage) +{ + // Some usage key doesn't have any corresponding virtual code or it was not + // found. + switch (usage) { + case kHIDUsage_KeyboardErrorRollOver: return 0xff; + case kHIDUsage_KeyboardPOSTFail: return 0xff; + case kHIDUsage_KeyboardErrorUndefined: return 0xff; + + case kHIDUsage_KeyboardA: return 0x00; + case kHIDUsage_KeyboardB: return 0x0b; + case kHIDUsage_KeyboardC: return 0x08; + case kHIDUsage_KeyboardD: return 0x02; + case kHIDUsage_KeyboardE: return 0x0e; + case kHIDUsage_KeyboardF: return 0x03; + case kHIDUsage_KeyboardG: return 0x05; + case kHIDUsage_KeyboardH: return 0x04; + case kHIDUsage_KeyboardI: return 0x22; + case kHIDUsage_KeyboardJ: return 0x26; + case kHIDUsage_KeyboardK: return 0x28; + case kHIDUsage_KeyboardL: return 0x25; + case kHIDUsage_KeyboardM: return 0x2e; + case kHIDUsage_KeyboardN: return 0x2d; + case kHIDUsage_KeyboardO: return 0x1f; + case kHIDUsage_KeyboardP: return 0x23; + case kHIDUsage_KeyboardQ: return 0x0c; + case kHIDUsage_KeyboardR: return 0x0f; + case kHIDUsage_KeyboardS: return 0x01; + case kHIDUsage_KeyboardT: return 0x11; + case kHIDUsage_KeyboardU: return 0x20; + case kHIDUsage_KeyboardV: return 0x09; + case kHIDUsage_KeyboardW: return 0x0d; + case kHIDUsage_KeyboardX: return 0x07; + case kHIDUsage_KeyboardY: return 0x10; + case kHIDUsage_KeyboardZ: return 0x06; + + case kHIDUsage_Keyboard1: return 0x12; + case kHIDUsage_Keyboard2: return 0x13; + case kHIDUsage_Keyboard3: return 0x14; + case kHIDUsage_Keyboard4: return 0x15; + case kHIDUsage_Keyboard5: return 0x17; + case kHIDUsage_Keyboard6: return 0x16; + case kHIDUsage_Keyboard7: return 0x1a; + case kHIDUsage_Keyboard8: return 0x1c; + case kHIDUsage_Keyboard9: return 0x19; + case kHIDUsage_Keyboard0: return 0x1d; + + case kHIDUsage_KeyboardReturnOrEnter: return 0x24; + case kHIDUsage_KeyboardEscape: return 0x35; + case kHIDUsage_KeyboardDeleteOrBackspace: return 0x33; + case kHIDUsage_KeyboardTab: return 0x30; + case kHIDUsage_KeyboardSpacebar: return 0x31; + case kHIDUsage_KeyboardHyphen: return 0x1b; + case kHIDUsage_KeyboardEqualSign: return 0x18; + case kHIDUsage_KeyboardOpenBracket: return 0x21; + case kHIDUsage_KeyboardCloseBracket: return 0x1e; + case kHIDUsage_KeyboardBackslash: return 0x2a; + case kHIDUsage_KeyboardNonUSPound: return 0xff; + case kHIDUsage_KeyboardSemicolon: return 0x29; + case kHIDUsage_KeyboardQuote: return 0x27; + case kHIDUsage_KeyboardGraveAccentAndTilde: return 0x32; + case kHIDUsage_KeyboardComma: return 0x2b; + case kHIDUsage_KeyboardPeriod: return 0x2F; + case kHIDUsage_KeyboardSlash: return 0x2c; + case kHIDUsage_KeyboardCapsLock: return 0x39; + + case kHIDUsage_KeyboardF1: return 0x7a; + case kHIDUsage_KeyboardF2: return 0x78; + case kHIDUsage_KeyboardF3: return 0x63; + case kHIDUsage_KeyboardF4: return 0x76; + case kHIDUsage_KeyboardF5: return 0x60; + case kHIDUsage_KeyboardF6: return 0x61; + case kHIDUsage_KeyboardF7: return 0x62; + case kHIDUsage_KeyboardF8: return 0x64; + case kHIDUsage_KeyboardF9: return 0x65; + case kHIDUsage_KeyboardF10: return 0x6d; + case kHIDUsage_KeyboardF11: return 0x67; + case kHIDUsage_KeyboardF12: return 0x6f; + + case kHIDUsage_KeyboardPrintScreen: return 0xff; + case kHIDUsage_KeyboardScrollLock: return 0xff; + case kHIDUsage_KeyboardPause: return 0xff; + case kHIDUsage_KeyboardInsert: return 0x72; + case kHIDUsage_KeyboardHome: return 0x73; + case kHIDUsage_KeyboardPageUp: return 0x74; + case kHIDUsage_KeyboardDeleteForward: return 0x75; + case kHIDUsage_KeyboardEnd: return 0x77; + case kHIDUsage_KeyboardPageDown: return 0x79; + + case kHIDUsage_KeyboardRightArrow: return 0x7c; + case kHIDUsage_KeyboardLeftArrow: return 0x7b; + case kHIDUsage_KeyboardDownArrow: return 0x7d; + case kHIDUsage_KeyboardUpArrow: return 0x7e; + + case kHIDUsage_KeypadNumLock: return 0x47; + case kHIDUsage_KeypadSlash: return 0x4b; + case kHIDUsage_KeypadAsterisk: return 0x43; + case kHIDUsage_KeypadHyphen: return 0x4e; + case kHIDUsage_KeypadPlus: return 0x45; + case kHIDUsage_KeypadEnter: return 0x4c; + + case kHIDUsage_Keypad1: return 0x53; + case kHIDUsage_Keypad2: return 0x54; + case kHIDUsage_Keypad3: return 0x55; + case kHIDUsage_Keypad4: return 0x56; + case kHIDUsage_Keypad5: return 0x57; + case kHIDUsage_Keypad6: return 0x58; + case kHIDUsage_Keypad7: return 0x59; + case kHIDUsage_Keypad8: return 0x5b; + case kHIDUsage_Keypad9: return 0x5c; + case kHIDUsage_Keypad0: return 0x52; + + case kHIDUsage_KeypadPeriod: return 0x41; + case kHIDUsage_KeyboardNonUSBackslash: return 0xff; + case kHIDUsage_KeyboardApplication: return 0x6e; + case kHIDUsage_KeyboardPower: return 0xff; + case kHIDUsage_KeypadEqualSign: return 0x51; + + case kHIDUsage_KeyboardF13: return 0x69; + case kHIDUsage_KeyboardF14: return 0x6b; + case kHIDUsage_KeyboardF15: return 0x71; + case kHIDUsage_KeyboardF16: return 0xff; + case kHIDUsage_KeyboardF17: return 0xff; + case kHIDUsage_KeyboardF18: return 0xff; + case kHIDUsage_KeyboardF19: return 0xff; + case kHIDUsage_KeyboardF20: return 0xff; + case kHIDUsage_KeyboardF21: return 0xff; + case kHIDUsage_KeyboardF22: return 0xff; + case kHIDUsage_KeyboardF23: return 0xff; + case kHIDUsage_KeyboardF24: return 0xff; + + case kHIDUsage_KeyboardExecute: return 0xff; + case kHIDUsage_KeyboardHelp: return 0xff; + case kHIDUsage_KeyboardMenu: return 0x7F; + case kHIDUsage_KeyboardSelect: return 0x4c; + case kHIDUsage_KeyboardStop: return 0xff; + case kHIDUsage_KeyboardAgain: return 0xff; + case kHIDUsage_KeyboardUndo: return 0xff; + case kHIDUsage_KeyboardCut: return 0xff; + case kHIDUsage_KeyboardCopy: return 0xff; + case kHIDUsage_KeyboardPaste: return 0xff; + case kHIDUsage_KeyboardFind: return 0xff; + + case kHIDUsage_KeyboardMute: return 0xff; + case kHIDUsage_KeyboardVolumeUp: return 0xff; + case kHIDUsage_KeyboardVolumeDown: return 0xff; + + case kHIDUsage_KeyboardLockingCapsLock: return 0xff; + case kHIDUsage_KeyboardLockingNumLock: return 0xff; + case kHIDUsage_KeyboardLockingScrollLock: return 0xff; + + case kHIDUsage_KeypadComma: return 0xff; + case kHIDUsage_KeypadEqualSignAS400: return 0xff; + case kHIDUsage_KeyboardInternational1: return 0xff; + case kHIDUsage_KeyboardInternational2: return 0xff; + case kHIDUsage_KeyboardInternational3: return 0xff; + case kHIDUsage_KeyboardInternational4: return 0xff; + case kHIDUsage_KeyboardInternational5: return 0xff; + case kHIDUsage_KeyboardInternational6: return 0xff; + case kHIDUsage_KeyboardInternational7: return 0xff; + case kHIDUsage_KeyboardInternational8: return 0xff; + case kHIDUsage_KeyboardInternational9: return 0xff; + + case kHIDUsage_KeyboardLANG1: return 0xff; + case kHIDUsage_KeyboardLANG2: return 0xff; + case kHIDUsage_KeyboardLANG3: return 0xff; + case kHIDUsage_KeyboardLANG4: return 0xff; + case kHIDUsage_KeyboardLANG5: return 0xff; + case kHIDUsage_KeyboardLANG6: return 0xff; + case kHIDUsage_KeyboardLANG7: return 0xff; + case kHIDUsage_KeyboardLANG8: return 0xff; + case kHIDUsage_KeyboardLANG9: return 0xff; + + case kHIDUsage_KeyboardAlternateErase: return 0xff; + case kHIDUsage_KeyboardSysReqOrAttention: return 0xff; + case kHIDUsage_KeyboardCancel: return 0xff; + case kHIDUsage_KeyboardClear: return 0xff; + case kHIDUsage_KeyboardPrior: return 0xff; + case kHIDUsage_KeyboardReturn: return 0xff; + case kHIDUsage_KeyboardSeparator: return 0xff; + case kHIDUsage_KeyboardOut: return 0xff; + case kHIDUsage_KeyboardOper: return 0xff; + case kHIDUsage_KeyboardClearOrAgain: return 0xff; + case kHIDUsage_KeyboardCrSelOrProps: return 0xff; + case kHIDUsage_KeyboardExSel: return 0xff; + + /* 0xa5-0xdf Reserved */ + + case kHIDUsage_KeyboardLeftControl: return 0x3b; + case kHIDUsage_KeyboardLeftShift: return 0x38; + case kHIDUsage_KeyboardLeftAlt: return 0x3a; + case kHIDUsage_KeyboardLeftGUI: return 0x37; + case kHIDUsage_KeyboardRightControl: return 0x3e; + case kHIDUsage_KeyboardRightShift: return 0x3c; + case kHIDUsage_KeyboardRightAlt: return 0x3d; + case kHIDUsage_KeyboardRightGUI: return 0x36; + + /* 0xe8-0xffff Reserved */ + + case kHIDUsage_Keyboard_Reserved: return 0xff; + default: return 0xff; + } +} + + +//////////////////////////////////////////////////////// +Keyboard::Key HIDInputManager::LocalizedKeys(UniChar ch) +{ + switch (ch) { + case 'a': + case 'A': return sf::Keyboard::A; + + case 'b': + case 'B': return sf::Keyboard::B; + + case 'c': + case 'C': return sf::Keyboard::C; + + case 'd': + case 'D': return sf::Keyboard::D; + + case 'e': + case 'E': return sf::Keyboard::E; + + case 'f': + case 'F': return sf::Keyboard::F; + + case 'g': + case 'G': return sf::Keyboard::G; + + case 'h': + case 'H': return sf::Keyboard::H; + + case 'i': + case 'I': return sf::Keyboard::I; + + case 'j': + case 'J': return sf::Keyboard::J; + + case 'k': + case 'K': return sf::Keyboard::K; + + case 'l': + case 'L': return sf::Keyboard::L; + + case 'm': + case 'M': return sf::Keyboard::M; + + case 'n': + case 'N': return sf::Keyboard::N; + + case 'o': + case 'O': return sf::Keyboard::O; + + case 'p': + case 'P': return sf::Keyboard::P; + + case 'q': + case 'Q': return sf::Keyboard::Q; + + case 'r': + case 'R': return sf::Keyboard::R; + + case 's': + case 'S': return sf::Keyboard::S; + + case 't': + case 'T': return sf::Keyboard::T; + + case 'u': + case 'U': return sf::Keyboard::U; + + case 'v': + case 'V': return sf::Keyboard::V; + + case 'w': + case 'W': return sf::Keyboard::W; + + case 'x': + case 'X': return sf::Keyboard::X; + + case 'y': + case 'Y': return sf::Keyboard::Y; + + case 'z': + case 'Z': return sf::Keyboard::Z; + + // The key is not 'localized'. + default: return sf::Keyboard::KeyCount; + } +} + + +//////////////////////////////////////////////////////// +Keyboard::Key HIDInputManager::NonLocalizedKeys(UniChar virtualKeycode) +{ + // (Some) 0x code based on http://forums.macrumors.com/showthread.php?t=780577 + // Some sf::Keyboard::Key are present twice. + switch (virtualKeycode) { + // These cases should not be used but anyway... + case 0x00: return sf::Keyboard::A; + case 0x0b: return sf::Keyboard::B; + case 0x08: return sf::Keyboard::C; + case 0x02: return sf::Keyboard::D; + case 0x0e: return sf::Keyboard::E; + case 0x03: return sf::Keyboard::F; + case 0x05: return sf::Keyboard::G; + case 0x04: return sf::Keyboard::H; + case 0x22: return sf::Keyboard::I; + case 0x26: return sf::Keyboard::J; + case 0x28: return sf::Keyboard::K; + case 0x25: return sf::Keyboard::L; + case 0x2e: return sf::Keyboard::M; + case 0x2d: return sf::Keyboard::N; + case 0x1f: return sf::Keyboard::O; + case 0x23: return sf::Keyboard::P; + case 0x0c: return sf::Keyboard::Q; + case 0x0f: return sf::Keyboard::R; + case 0x01: return sf::Keyboard::S; + case 0x11: return sf::Keyboard::T; + case 0x20: return sf::Keyboard::U; + case 0x09: return sf::Keyboard::V; + case 0x0d: return sf::Keyboard::W; + case 0x07: return sf::Keyboard::X; + case 0x10: return sf::Keyboard::Y; + case 0x06: return sf::Keyboard::Z; + + // These cases should not be used but anyway... + case 0x1d: return sf::Keyboard::Num0; + case 0x12: return sf::Keyboard::Num1; + case 0x13: return sf::Keyboard::Num2; + case 0x14: return sf::Keyboard::Num3; + case 0x15: return sf::Keyboard::Num4; + case 0x17: return sf::Keyboard::Num5; + case 0x16: return sf::Keyboard::Num6; + case 0x1a: return sf::Keyboard::Num7; + case 0x1c: return sf::Keyboard::Num8; + case 0x19: return sf::Keyboard::Num9; + + case 0x35: return sf::Keyboard::Escape; + + // Modifier keys : never happen with keyDown/keyUp methods (?) + case 0x3b: return sf::Keyboard::LControl; + case 0x38: return sf::Keyboard::LShift; + case 0x3a: return sf::Keyboard::LAlt; + case 0x37: return sf::Keyboard::LSystem; + case 0x3e: return sf::Keyboard::RControl; + case 0x3c: return sf::Keyboard::RShift; + case 0x3d: return sf::Keyboard::RAlt; + case 0x36: return sf::Keyboard::RSystem; + + case 0x7f: return sf::Keyboard::Menu; + case NSMenuFunctionKey: return sf::Keyboard::Menu; + + case 0x21: return sf::Keyboard::LBracket; + case 0x1e: return sf::Keyboard::RBracket; + case 0x29: return sf::Keyboard::SemiColon; + case 0x2b: return sf::Keyboard::Comma; +// case 0x41: /* keypad */ return sf::Keyboard::Period; + case 0x2f: /* keyboard */ return sf::Keyboard::Period; + case 0x27: return sf::Keyboard::Quote; + case 0x2c: return sf::Keyboard::Slash; + case 0x2a: return sf::Keyboard::BackSlash; + +#warning sf::Keyboard::Tilde might be in conflict with some other key. + // 0x0a is for "Non-US Backslash" according to HID Calibrator, + // a sample provided by Apple. + case 0x0a: return sf::Keyboard::Tilde; + +// case 0x51: /* keypad */ return sf::Keyboard::Equal; + case 0x18: /* keyboard */ return sf::Keyboard::Equal; + case 0x32: return sf::Keyboard::Dash; + case 0x31: return sf::Keyboard::Space; +// case 0x4c: /* keypad */ return sf::Keyboard::Return; + case 0x24: /* keyboard */ return sf::Keyboard::Return; + case 0x33: return sf::Keyboard::Back; + case 0x30: return sf::Keyboard::Tab; + + // Duplicates (see next §). + case 0x74: return sf::Keyboard::PageUp; + case 0x79: return sf::Keyboard::PageDown; + case 0x77: return sf::Keyboard::End; + case 0x73: return sf::Keyboard::Home; + + case NSPageUpFunctionKey: return sf::Keyboard::PageUp; + case NSPageDownFunctionKey: return sf::Keyboard::PageDown; + case NSEndFunctionKey: return sf::Keyboard::End; + case NSHomeFunctionKey: return sf::Keyboard::Home; + + case 0x72: return sf::Keyboard::Insert; + case NSInsertFunctionKey: return sf::Keyboard::Insert; + case 0x75: return sf::Keyboard::Delete; + case NSDeleteFunctionKey: return sf::Keyboard::Delete; + + case 0x45: return sf::Keyboard::Add; + case 0x4e: return sf::Keyboard::Subtract; + case 0x43: return sf::Keyboard::Multiply; + case 0x4b: return sf::Keyboard::Divide; + + // Duplicates (see next §). + case 0x7b: return sf::Keyboard::Left; + case 0x7c: return sf::Keyboard::Right; + case 0x7e: return sf::Keyboard::Up; + case 0x7d: return sf::Keyboard::Down; + + case NSLeftArrowFunctionKey: return sf::Keyboard::Left; + case NSRightArrowFunctionKey: return sf::Keyboard::Right; + case NSUpArrowFunctionKey: return sf::Keyboard::Up; + case NSDownArrowFunctionKey: return sf::Keyboard::Down; + + case 0x52: return sf::Keyboard::Numpad0; + case 0x53: return sf::Keyboard::Numpad1; + case 0x54: return sf::Keyboard::Numpad2; + case 0x55: return sf::Keyboard::Numpad3; + case 0x56: return sf::Keyboard::Numpad4; + case 0x57: return sf::Keyboard::Numpad5; + case 0x58: return sf::Keyboard::Numpad6; + case 0x59: return sf::Keyboard::Numpad7; + case 0x5b: return sf::Keyboard::Numpad8; + case 0x5c: return sf::Keyboard::Numpad9; + + // Duplicates (see next §). + case 0x7a: return sf::Keyboard::F1; + case 0x78: return sf::Keyboard::F2; + case 0x63: return sf::Keyboard::F3; + case 0x76: return sf::Keyboard::F4; + case 0x60: return sf::Keyboard::F5; + case 0x61: return sf::Keyboard::F6; + case 0x62: return sf::Keyboard::F7; + case 0x64: return sf::Keyboard::F8; + case 0x65: return sf::Keyboard::F9; + case 0x6d: return sf::Keyboard::F10; + case 0x67: return sf::Keyboard::F11; + case 0x6f: return sf::Keyboard::F12; + case 0x69: return sf::Keyboard::F13; + case 0x6b: return sf::Keyboard::F14; + case 0x71: return sf::Keyboard::F15; + + case NSF1FunctionKey: return sf::Keyboard::F1; + case NSF2FunctionKey: return sf::Keyboard::F2; + case NSF3FunctionKey: return sf::Keyboard::F3; + case NSF4FunctionKey: return sf::Keyboard::F4; + case NSF5FunctionKey: return sf::Keyboard::F5; + case NSF6FunctionKey: return sf::Keyboard::F6; + case NSF7FunctionKey: return sf::Keyboard::F7; + case NSF8FunctionKey: return sf::Keyboard::F8; + case NSF9FunctionKey: return sf::Keyboard::F9; + case NSF10FunctionKey: return sf::Keyboard::F10; + case NSF11FunctionKey: return sf::Keyboard::F11; + case NSF12FunctionKey: return sf::Keyboard::F12; + case NSF13FunctionKey: return sf::Keyboard::F13; + case NSF14FunctionKey: return sf::Keyboard::F14; + case NSF15FunctionKey: return sf::Keyboard::F15; + + case NSPauseFunctionKey: return sf::Keyboard::Pause; + +#warning keycode 0x1b is not bound to any key. + // This key is ' on CH-FR, ) on FR and - on US layouts. + + // An unknown key. + default: return sf::Keyboard::KeyCount; + } +} + + +} // namespace priv + +} // namespace sf + diff --git a/src/SFML/Window/OSX/InputImpl.mm b/src/SFML/Window/OSX/InputImpl.mm index 4a36759c..0690442f 100644 --- a/src/SFML/Window/OSX/InputImpl.mm +++ b/src/SFML/Window/OSX/InputImpl.mm @@ -30,10 +30,20 @@ #include #include #include +#include #import #import +//////////////////////////////////////////////////////////// +/// In order to keep track of the keyboard's state and mouse buttons' state +/// we use the HID manager. Mouse position is handled differently. +/// +/// NB : we probably could use +/// NSEvent +addGlobalMonitorForEventsMatchingMask:handler: for mouse only. +/// +//////////////////////////////////////////////////////////// + namespace sf { namespace priv @@ -92,16 +102,14 @@ SFOpenGLView* GetSFOpenGLViewFromSFMLWindow(const Window& window) //////////////////////////////////////////////////////////// bool InputImpl::IsKeyPressed(Keyboard::Key key) { - // @to be implemented - return false; + return HIDInputManager::GetInstance().IsKeyPressed(key); } //////////////////////////////////////////////////////////// bool InputImpl::IsMouseButtonPressed(Mouse::Button button) { - // @to be implemented - return false; + return HIDInputManager::GetInstance().IsMouseButtonPressed(button); } diff --git a/src/SFML/Window/OSX/SFOpenGLView.mm b/src/SFML/Window/OSX/SFOpenGLView.mm index cb10daaf..e3f7dbb0 100644 --- a/src/SFML/Window/OSX/SFOpenGLView.mm +++ b/src/SFML/Window/OSX/SFOpenGLView.mm @@ -27,6 +27,7 @@ // Headers //////////////////////////////////////////////////////////// #include +#include // For LocalizedKeys and NonLocalizedKeys #include #import @@ -60,25 +61,6 @@ NSUInteger EraseMaskFromData(NSUInteger data, NSUInteger mask); //////////////////////////////////////////////////////////// NSUInteger KeepOnlyMaskFromData(NSUInteger data, NSUInteger mask); -//////////////////////////////////////////////////////////// -/// Try to convert a character into a SFML key code. -/// Return sf::Keyboard::KeyCount if it doesn't match any 'localized' keys. -/// -/// By 'localized' I mean keys that depend on the keyboard layout -/// and might not be the same as the US keycode in some country -/// (e.g. the keys 'Y' and 'Z' are switched on QWERTZ keyboard and -/// US keyboard layouts.) -/// -//////////////////////////////////////////////////////////// -sf::Keyboard::Key LocalizedKeys(unichar ch); - -//////////////////////////////////////////////////////////// -/// Try to convert a keycode into a SFML key code. -/// Return sf::Keyboard::KeyCount if the keycode is unknown. -/// -//////////////////////////////////////////////////////////// -sf::Keyboard::Key NonLocalizedKeys(unsigned short keycode); - //////////////////////////////////////////////////////////// /// SFOpenGLView class : Privates Methods Declaration /// @@ -105,6 +87,8 @@ sf::Keyboard::Key NonLocalizedKeys(unsigned short keycode); //////////////////////////////////////////////////////////// /// Converte the NSEvent mouse button type to SFML type. +/// +/// Returns ButtonCount if the button is unknown /// //////////////////////////////////////////////////////////// -(sf::Mouse::Button)mouseButtonFromEvent:(NSEvent *)event; @@ -197,7 +181,7 @@ sf::Keyboard::Key NonLocalizedKeys(unsigned short keycode); /*we don't care about this : */0); CGEventPost(kCGHIDEventTap, event); CFRelease(event); - // This is a workaround to deprecated CGSetLocalEventsSuppressionInterval. + // This is a workaround to deprecated CGSetLocalEventsSuppressionInterval function } @@ -489,6 +473,7 @@ sf::Keyboard::Key NonLocalizedKeys(unsigned short keycode); { if (myRequester == 0) return; + // Handle key down event if (myUseKeyRepeat || ![theEvent isARepeat]) { sf::Event::KeyEvent key = [SFOpenGLView convertNSKeyEventToSFMLEvent:theEvent]; @@ -497,6 +482,7 @@ sf::Keyboard::Key NonLocalizedKeys(unsigned short keycode); } } + // Handle text entred event if ((myUseKeyRepeat || ![theEvent isARepeat]) && [[theEvent characters] length] > 0) { // Ignore escape key and non text keycode. (See NSEvent.h) @@ -966,25 +952,27 @@ sf::Keyboard::Key NonLocalizedKeys(unsigned short keycode); // Key code. key.Code = sf::Keyboard::KeyCount; - // First we look if the key down is from a list of caracter that depend on keyboard localization. + + // First we look if the key down is from a list of caracter + // that depend on keyboard localization. NSString* string = [anEvent charactersIgnoringModifiers]; if ([string length] > 0) { - key.Code = LocalizedKeys([string characterAtIndex:0]); + key.Code = sf::priv::HIDInputManager::LocalizedKeys([string characterAtIndex:0]); } - // The key is not a localized one, the other keys. + // The key is not a localized one, so we try to find a corresponding code + // through virtual key code. if (key.Code == sf::Keyboard::KeyCount) { - key.Code = NonLocalizedKeys([anEvent keyCode]); + key.Code = sf::priv::HIDInputManager::NonLocalizedKeys([anEvent keyCode]); } -#ifdef SFML_DEBUG // We don't want to bother the final customer with annoying messages. +#ifdef SFML_DEBUG // Don't bother the final customers with annoying messages. if (key.Code == sf::Keyboard::KeyCount) { // The key is unknown. - sf::Err() - << "This is an unknow key. Should not happen (?). Keycode is 0x" - << std::hex - << [anEvent keyCode] - << "." - << std::endl; + sf::Err() << "This is an unknow key. Virtual key code is 0x" + << std::hex + << [anEvent keyCode] + << "." + << std::endl; } #endif @@ -1012,256 +1000,3 @@ NSUInteger KeepOnlyMaskFromData(NSUInteger data, NSUInteger mask) } -//////////////////////////////////////////////////////// -sf::Keyboard::Key LocalizedKeys(unichar ch) -{ - switch (ch) { - case 'a': - case 'A': return sf::Keyboard::A; - - case 'b': - case 'B': return sf::Keyboard::B; - - case 'c': - case 'C': return sf::Keyboard::C; - - case 'd': - case 'D': return sf::Keyboard::D; - - case 'e': - case 'E': return sf::Keyboard::E; - - case 'f': - case 'F': return sf::Keyboard::F; - - case 'g': - case 'G': return sf::Keyboard::G; - - case 'h': - case 'H': return sf::Keyboard::H; - - case 'i': - case 'I': return sf::Keyboard::I; - - case 'j': - case 'J': return sf::Keyboard::J; - - case 'k': - case 'K': return sf::Keyboard::K; - - case 'l': - case 'L': return sf::Keyboard::L; - - case 'm': - case 'M': return sf::Keyboard::M; - - case 'n': - case 'N': return sf::Keyboard::N; - - case 'o': - case 'O': return sf::Keyboard::O; - - case 'p': - case 'P': return sf::Keyboard::P; - - case 'q': - case 'Q': return sf::Keyboard::Q; - - case 'r': - case 'R': return sf::Keyboard::R; - - case 's': - case 'S': return sf::Keyboard::S; - - case 't': - case 'T': return sf::Keyboard::T; - - case 'u': - case 'U': return sf::Keyboard::U; - - case 'v': - case 'V': return sf::Keyboard::V; - - case 'w': - case 'W': return sf::Keyboard::W; - - case 'x': - case 'X': return sf::Keyboard::X; - - case 'y': - case 'Y': return sf::Keyboard::Y; - - case 'z': - case 'Z': return sf::Keyboard::Z; - - // The kew is not 'localized'. - default: return sf::Keyboard::KeyCount; - } -} - - -//////////////////////////////////////////////////////// -sf::Keyboard::Key NonLocalizedKeys(unsigned short keycode) -{ - // (Some) 0x code based on http://forums.macrumors.com/showthread.php?t=780577 - // Some sf::Keyboard::Key are present twice. - switch (keycode) { - // These cases should not be used but anyway... - case 0x00: return sf::Keyboard::A; - case 0x0b: return sf::Keyboard::B; - case 0x08: return sf::Keyboard::C; - case 0x02: return sf::Keyboard::D; - case 0x0e: return sf::Keyboard::E; - case 0x03: return sf::Keyboard::F; - case 0x05: return sf::Keyboard::G; - case 0x04: return sf::Keyboard::H; - case 0x22: return sf::Keyboard::I; - case 0x26: return sf::Keyboard::J; - case 0x28: return sf::Keyboard::K; - case 0x25: return sf::Keyboard::L; - case 0x2e: return sf::Keyboard::M; - case 0x2d: return sf::Keyboard::N; - case 0x1f: return sf::Keyboard::O; - case 0x23: return sf::Keyboard::P; - case 0x0c: return sf::Keyboard::Q; - case 0x0f: return sf::Keyboard::R; - case 0x01: return sf::Keyboard::S; - case 0x11: return sf::Keyboard::T; - case 0x20: return sf::Keyboard::U; - case 0x09: return sf::Keyboard::V; - case 0x0d: return sf::Keyboard::W; - case 0x07: return sf::Keyboard::X; - case 0x10: return sf::Keyboard::Y; - case 0x06: return sf::Keyboard::Z; - - // These cases should not be used but anyway... - case 0x1d: return sf::Keyboard::Num0; - case 0x12: return sf::Keyboard::Num1; - case 0x13: return sf::Keyboard::Num2; - case 0x14: return sf::Keyboard::Num3; - case 0x15: return sf::Keyboard::Num4; - case 0x17: return sf::Keyboard::Num5; - case 0x16: return sf::Keyboard::Num6; - case 0x1a: return sf::Keyboard::Num7; - case 0x1c: return sf::Keyboard::Num8; - case 0x19: return sf::Keyboard::Num9; - - case 0x35: return sf::Keyboard::Escape; - - // Modifier keys : never happen with keyDown/keyUp methods (?) - case 0x3b: return sf::Keyboard::LControl; - case 0x38: return sf::Keyboard::LShift; - case 0x3a: return sf::Keyboard::LAlt; - case 0x37: return sf::Keyboard::LSystem; - case 0x3e: return sf::Keyboard::RControl; - case 0x3c: return sf::Keyboard::RShift; - case 0x3d: return sf::Keyboard::RAlt; - case 0x36: return sf::Keyboard::RSystem; - - case NSMenuFunctionKey: return sf::Keyboard::Menu; - - case 0x21: return sf::Keyboard::LBracket; - case 0x1e: return sf::Keyboard::RBracket; - case 0x29: return sf::Keyboard::SemiColon; - case 0x2b: return sf::Keyboard::Comma; - case 0x2f: return sf::Keyboard::Period; - case 0x27: return sf::Keyboard::Quote; - case 0x2c: return sf::Keyboard::Slash; - case 0x2a: return sf::Keyboard::BackSlash; - -#warning sf::Keyboard::Tilde might be in conflict with some other key. - // 0x0a is for "Non-US Backslash" according to HID Calibrator, - // a sample provided by Apple. - case 0x0a: return sf::Keyboard::Tilde; - - case 0x18: return sf::Keyboard::Equal; - case 0x32: return sf::Keyboard::Dash; - case 0x31: return sf::Keyboard::Space; - case 0x24: return sf::Keyboard::Return; - case 0x33: return sf::Keyboard::Back; - case 0x30: return sf::Keyboard::Tab; - - // Duplicates (see next §). - case 0x74: return sf::Keyboard::PageUp; - case 0x79: return sf::Keyboard::PageDown; - case 0x77: return sf::Keyboard::End; - case 0x73: return sf::Keyboard::Home; - - case NSPageUpFunctionKey: return sf::Keyboard::PageUp; - case NSPageDownFunctionKey: return sf::Keyboard::PageDown; - case NSEndFunctionKey: return sf::Keyboard::End; - case NSHomeFunctionKey: return sf::Keyboard::Home; - - case NSInsertFunctionKey: return sf::Keyboard::Insert; - case NSDeleteFunctionKey: return sf::Keyboard::Delete; - - case 0x45: return sf::Keyboard::Add; - case 0x4e: return sf::Keyboard::Subtract; - case 0x43: return sf::Keyboard::Multiply; - case 0x4b: return sf::Keyboard::Divide; - - // Duplicates (see next §). - case 0x7b: return sf::Keyboard::Left; - case 0x7c: return sf::Keyboard::Right; - case 0x7e: return sf::Keyboard::Up; - case 0x7d: return sf::Keyboard::Down; - - case NSLeftArrowFunctionKey: return sf::Keyboard::Left; - case NSRightArrowFunctionKey: return sf::Keyboard::Right; - case NSUpArrowFunctionKey: return sf::Keyboard::Up; - case NSDownArrowFunctionKey: return sf::Keyboard::Down; - - case 0x52: return sf::Keyboard::Numpad0; - case 0x53: return sf::Keyboard::Numpad1; - case 0x54: return sf::Keyboard::Numpad2; - case 0x55: return sf::Keyboard::Numpad3; - case 0x56: return sf::Keyboard::Numpad4; - case 0x57: return sf::Keyboard::Numpad5; - case 0x58: return sf::Keyboard::Numpad6; - case 0x59: return sf::Keyboard::Numpad7; - case 0x5b: return sf::Keyboard::Numpad8; - case 0x5c: return sf::Keyboard::Numpad9; - - // Duplicates (see next §). - case 0x7a: return sf::Keyboard::F1; - case 0x78: return sf::Keyboard::F2; - case 0x63: return sf::Keyboard::F3; - case 0x76: return sf::Keyboard::F4; - case 0x60: return sf::Keyboard::F5; - case 0x61: return sf::Keyboard::F6; - case 0x62: return sf::Keyboard::F7; - case 0x64: return sf::Keyboard::F8; - case 0x65: return sf::Keyboard::F9; - case 0x6d: return sf::Keyboard::F10; - case 0x67: return sf::Keyboard::F11; - case 0x6f: return sf::Keyboard::F12; - case 0x69: return sf::Keyboard::F13; - case 0x6b: return sf::Keyboard::F14; - case 0x71: return sf::Keyboard::F15; - - case NSF1FunctionKey: return sf::Keyboard::F1; - case NSF2FunctionKey: return sf::Keyboard::F2; - case NSF3FunctionKey: return sf::Keyboard::F3; - case NSF4FunctionKey: return sf::Keyboard::F4; - case NSF5FunctionKey: return sf::Keyboard::F5; - case NSF6FunctionKey: return sf::Keyboard::F6; - case NSF7FunctionKey: return sf::Keyboard::F7; - case NSF8FunctionKey: return sf::Keyboard::F8; - case NSF9FunctionKey: return sf::Keyboard::F9; - case NSF10FunctionKey: return sf::Keyboard::F10; - case NSF11FunctionKey: return sf::Keyboard::F11; - case NSF12FunctionKey: return sf::Keyboard::F12; - case NSF13FunctionKey: return sf::Keyboard::F13; - case NSF14FunctionKey: return sf::Keyboard::F14; - case NSF15FunctionKey: return sf::Keyboard::F15; - - case NSPauseFunctionKey: return sf::Keyboard::Pause; - -#warning keycode 0x1b is not bound to any key. - // This key is ' on CH-FR, ) on FR and - on US layouts. - - // An unknown key. - default: return sf::Keyboard::KeyCount; - } -} -