From 10795e93145f79a97afce0150d8bacd94d550afa Mon Sep 17 00:00:00 2001 From: MNS26 Date: Fri, 22 Mar 2024 15:28:24 +0100 Subject: [PATCH] Rewrote HID cpde to be dymamic (not perfect yet but works) report struct is no though !!! --- .vscode/settings.json | 11 +- config/common.ini | 66 +- include/HID_Report.hpp | 2 +- include/HID_descriptors.hpp | 374 ++++++----- include/hid.hpp | 1199 ----------------------------------- src/main.cpp | 1009 ++++++++++++++--------------- 6 files changed, 758 insertions(+), 1903 deletions(-) delete mode 100755 include/hid.hpp diff --git a/.vscode/settings.json b/.vscode/settings.json index c910310..07d1bef 100755 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -1,7 +1,6 @@ { "files.associations": { "*.embeddedhtml": "html", - "usi_i2c_slave.c": "cpp", "*.x": "cpp", "mstd_iterator": "cpp", "array": "cpp", @@ -60,18 +59,20 @@ "streambuf": "cpp", "cinttypes": "cpp", "typeinfo": "cpp", - "*.bak": "plaintext", "i2c.pio.h": "c", "pio.h": "c", "*.pio": "pio" }, "C_Cpp.dimInactiveRegions": true, - "editor.insertSpaces": false, + "editor.insertSpaces": true, "editor.wordBasedSuggestions": "matchingDocuments", "editor.suggest.insertMode": "replace", "editor.semanticHighlighting.enabled": true, "editor.tabSize": 2, - "cmake.configureOnOpen": true, + "cmake.configureOnOpen": false, "C_Cpp.errorSquiggles": "enabled", - "python.analysis.typeCheckingMode": "basic", + "python.analysis.typeCheckingMode": "strict", + "C_Cpp.codeAnalysis.runAutomatically": true, + "C_Cpp.clang_format_style": "LLVM", + "debug.disassemblyView.showSourceCode": true, } \ No newline at end of file diff --git a/config/common.ini b/config/common.ini index 0e0a2ed..0c7accc 100644 --- a/config/common.ini +++ b/config/common.ini @@ -7,44 +7,44 @@ board_build.flash_mode = qio monitor_filters = default, colorize monitor_speed = 115200 -;board_build.f_cpu = 40000000L ;40Mhz (custom) -;board_build.f_cpu = 45000000L ;45Mhz (custom) +;board_build.f_cpu = 40000000L ;40Mhz (UC) (custom) +;board_build.f_cpu = 45000000L ;45Mhz (UC) (custom) ;board_build.f_cpu = 50000000L ;50Mhz (default min) -;board_build.f_cpu = 55000000L ;55Mhz (custom) -;board_build.f_cpu = 60000000L ;60Mhz (custom) -;board_build.f_cpu = 65000000L ;65Mhz (custom) -;board_build.f_cpu = 70000000L ;70Mhz (custom) -;board_build.f_cpu = 75000000L ;75Mhz (custom) -;board_build.f_cpu = 80000000L ;80Mhz (custom) -;board_build.f_cpu = 85000000L ;85Mhz (custom) -;board_build.f_cpu = 90000000L ;90Mhz (custom) -;board_build.f_cpu = 95000000L ;95Mhz (custom) -;board_build.f_cpu = 100000000L ;100Mhz (custom) -;board_build.f_cpu = 120000000L ;120Mhz (custom) +;board_build.f_cpu = 55000000L ;55Mhz (UC) (custom) +;board_build.f_cpu = 60000000L ;60Mhz (UC) (custom) +;board_build.f_cpu = 65000000L ;65Mhz (UC) (custom) +;board_build.f_cpu = 70000000L ;70Mhz (UC) (custom) +;board_build.f_cpu = 75000000L ;75Mhz (UC) (custom) +;board_build.f_cpu = 80000000L ;80Mhz (UC) (custom) +;board_build.f_cpu = 85000000L ;85Mhz (UC) (custom) +;board_build.f_cpu = 90000000L ;90Mhz (UC) (custom) +;board_build.f_cpu = 95000000L ;95Mhz (UC) (custom) +;board_build.f_cpu = 100000000L ;100Mhz (UC) (custom) +;board_build.f_cpu = 120000000L ;120Mhz (UC) (custom) ;board_build.f_cpu = 125000000L ;125Mhz (default) ;board_build.f_cpu = 130000000L ;130Mhz (custom) ;board_build.f_cpu = 133000000L ;133Mhz (default) -;board_build.f_cpu = 140000000L ;140Mhz (overclock) (custom) -;board_build.f_cpu = 145000000L ;145Mhz (overclock) (custom) +;board_build.f_cpu = 140000000L ;140Mhz (OC) (custom) +;board_build.f_cpu = 145000000L ;145Mhz (OC) (custom) board_build.f_cpu = 150000000L ;150Mhz (overclock) -;board_build.f_cpu = 155000000L ;155Mhz (overclock) (custom) -;board_build.f_cpu = 160000000L ;160Mhz (overclock) (custom) -;board_build.f_cpu = 165000000L ;165Mhz (overclock) (custom) -;board_build.f_cpu = 170000000L ;170Mhz (overclock) (custom) -;board_build.f_cpu = 175000000L ;175Mhz (overclock) (does not run) -;board_build.f_cpu = 180000000L ;180Mhz (overclock) (custom) -;board_build.f_cpu = 185000000L ;185Mhz (overclock) (custom) -;board_build.f_cpu = 190000000L ;190Mhz (overclock) (custom) -;board_build.f_cpu = 195000000L ;195Mhz (overclock) (custom) -;board_build.f_cpu = 200000000L ;200Mhz (overclock) (custom) -;board_build.f_cpu = 205000000L ;205Mhz (overclock) (custom) -;board_build.f_cpu = 210000000L ;210Mhz (overclock) (custom) -;board_build.f_cpu = 215000000L ;215Mhz (overclock) (custom) -;board_build.f_cpu = 220000000L ;220Mhz (overclock) (custom) -;board_build.f_cpu = 225000000L ;225Mhz (overclock) -;board_build.f_cpu = 240000000L ;240Mhz (overclock) -;board_build.f_cpu = 250000000L ;250Mhz (overclock) -;board_build.f_cpu = 270000000L ;270Mhz (overclock) (custom) +;board_build.f_cpu = 155000000L ;155Mhz (OC) (custom) +;board_build.f_cpu = 160000000L ;160Mhz (OC) (custom) +;board_build.f_cpu = 165000000L ;165Mhz (OC) (custom) +;board_build.f_cpu = 170000000L ;170Mhz (OC) (custom) +;board_build.f_cpu = 175000000L ;175Mhz (OC) (does not run... idk why) +;board_build.f_cpu = 180000000L ;180Mhz (OC) (custom) +;board_build.f_cpu = 185000000L ;185Mhz (OC) (custom) +;board_build.f_cpu = 190000000L ;190Mhz (OC) (custom) +;board_build.f_cpu = 195000000L ;195Mhz (OC) (custom) +;board_build.f_cpu = 200000000L ;200Mhz (OC) (custom) +;board_build.f_cpu = 205000000L ;205Mhz (OC) (custom) +;board_build.f_cpu = 210000000L ;210Mhz (OC) (custom) +;board_build.f_cpu = 215000000L ;215Mhz (OC) (custom) +;board_build.f_cpu = 220000000L ;220Mhz (OC) (custom) +;board_build.f_cpu = 225000000L ;225Mhz (OC) +;board_build.f_cpu = 240000000L ;240Mhz (OC) +;board_build.f_cpu = 250000000L ;250Mhz (OC) +;board_build.f_cpu = 270000000L ;270Mhz (OC) (custom) diff --git a/include/HID_Report.hpp b/include/HID_Report.hpp index 962a574..f5f547b 100755 --- a/include/HID_Report.hpp +++ b/include/HID_Report.hpp @@ -3,7 +3,6 @@ typedef struct TU_ATTR_PACKED { - uint32_t buttons ; ///< Buttons mask for currently pressed buttons int16_t x ; ///< Delta x movement of left analog-stick int16_t y ; ///< Delta y movement of left analog-stick int16_t z ; ///< Delta z movement of analog right trigger @@ -12,6 +11,7 @@ typedef struct TU_ATTR_PACKED int16_t rz ; ///< Delta Rz movement of right analog-joystick int16_t slider ; ///< Delta Ry movement of analog right trigger int16_t dial ; ///< Delta Ry movement of analog right trigger + uint32_t buttons ; ///< Buttons mask for currently pressed buttons uint8_t hat1 :4 ; ///< Buttons mask for currently pressed buttons in the DPad/hat uint8_t hat2 :4 ; ///< Buttons mask for currently pressed buttons in the DPad/hat }hid_Joystick_report_t; diff --git a/include/HID_descriptors.hpp b/include/HID_descriptors.hpp index 0e0b3e2..bcb413a 100755 --- a/include/HID_descriptors.hpp +++ b/include/HID_descriptors.hpp @@ -1,182 +1,220 @@ +uint AddHeader(uint8_t* buff, size_t offset, uint8_t repId) { + + uint8_t usagepage[] = { + HID_USAGE_PAGE ( HID_USAGE_PAGE_DESKTOP ), + HID_USAGE ( HID_USAGE_DESKTOP_JOYSTICK ), + HID_COLLECTION ( HID_COLLECTION_APPLICATION ), + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + + if (repId > 0) { + uint8_t reportid[] = { + HID_REPORT_ID (repId) + }; + memcpy(buff+offset, reportid, sizeof(reportid)); + offset += sizeof(reportid); + } + + uint8_t usagepage2[] = { + HID_USAGE ( HID_USAGE_DESKTOP_POINTER ), + HID_COLLECTION ( HID_COLLECTION_PHYSICAL ), + }; + memcpy(buff+offset, usagepage2, sizeof(usagepage2)); + offset += sizeof(usagepage2); + + return offset; +} -uint8_t HID_AXIS[] = { - HID_USAGE_PAGE ( HID_USAGE_PAGE_DESKTOP ), - HID_USAGE ( HID_USAGE_DESKTOP_X ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), - HID_PHYSICAL_MIN_N( -32768, 2 ), - HID_PHYSICAL_MAX_N( 32767, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( (uint8_t)(8 - HID_AXIS[18]%8) ), - HID_INPUT ( HID_CONSTANT ), -}; -uint8_t HID_BUTTONS[] = { - HID_USAGE_PAGE ( HID_USAGE_PAGE_BUTTON ), - HID_USAGE_MIN ( 1 ), - HID_USAGE_MAX ( 32 ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX ( 1 ), - HID_REPORT_COUNT ( 32 ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( (uint8_t)(8-HID_BUTTONS[11]%8)), - HID_INPUT ( HID_CONSTANT ), -}; -uint8_t HID_DPAD[] = { - - HID_USAGE_PAGE ( HID_USAGE_PAGE_DESKTOP ), - HID_USAGE ( HID_USAGE_DESKTOP_HAT_SWITCH ), - HID_USAGE ( HID_USAGE_DESKTOP_HAT_SWITCH ), - HID_LOGICAL_MIN ( 1 ), - HID_LOGICAL_MAX ( 8 ), - HID_PHYSICAL_MIN ( 0 ), - HID_PHYSICAL_MAX_N( 315, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 4 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( (uint8_t)(8 - HID_DPAD[19]%8) ), - HID_INPUT ( HID_CONSTANT ), -}; - -static const uint8_t HID_JOYSTICK_rep[] = { - HID_USAGE_PAGE ( HID_USAGE_PAGE_DESKTOP ), - HID_USAGE ( HID_USAGE_DESKTOP_JOYSTICK ), - HID_COLLECTION ( HID_COLLECTION_APPLICATION ), - HID_REPORT_ID ( 1 ), - /*HID_USAGE ( HID_USAGE_DESKTOP_POINTER ), - HID_COLLECTION ( HID_COLLECTION_PHYSICAL ),*/ - /* Report ID if any */ - HID_USAGE_PAGE ( HID_USAGE_PAGE_BUTTON ), - HID_USAGE_MIN ( 1 ), - HID_USAGE_MAX ( 32 ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX ( 1 ), - HID_REPORT_COUNT ( 32 ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(32%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), - - HID_USAGE_PAGE ( HID_USAGE_PAGE_DESKTOP ), - HID_USAGE ( HID_USAGE_DESKTOP_X ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), - HID_PHYSICAL_MIN_N( -32768, 2 ), - HID_PHYSICAL_MAX_N( 32767, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(8 - 11%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), - - HID_USAGE ( HID_USAGE_DESKTOP_Y ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), - HID_PHYSICAL_MIN_N( -32768, 2 ), - HID_PHYSICAL_MAX_N( 32767, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(8 - 11%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), - - HID_USAGE ( HID_USAGE_DESKTOP_Z ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), - HID_PHYSICAL_MIN_N( -32768, 2 ), - HID_PHYSICAL_MAX_N( 32767, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(8 - 11%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), - - HID_USAGE ( HID_USAGE_DESKTOP_RX ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), - HID_PHYSICAL_MIN_N( -32768, 2 ), - HID_PHYSICAL_MAX_N( 32767, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(8 - 11%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), - - HID_USAGE ( HID_USAGE_DESKTOP_RY ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), - HID_PHYSICAL_MIN_N( -32768, 2 ), - HID_PHYSICAL_MAX_N( 32767, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(8 - 11%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), +uint8_t AddCollectionEnd(uint8_t* buff, size_t offset) { + uint8_t CollectionEnd[] = { + HID_COLLECTION_END, + HID_COLLECTION_END + }; + memcpy(buff+offset, CollectionEnd, sizeof(CollectionEnd)); + offset += sizeof(CollectionEnd); + return offset; +} - HID_USAGE ( HID_USAGE_DESKTOP_RZ ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), +uint AddAxis(uint8_t* buff, size_t offset, uint8_t usage, uint8_t count, uint8_t bitResolution) { + + if (count > 8) { + count = 8; + } + // Calculate how many bytes this value will be + uint8_t ValueSize = (int)(std::ceil((float)(bitResolution)/8)); + + // Calculate the amount of padding needed to get it byte aligned (fuck you windows for needing this) + // We take the remainder of the mod and subtrack it from 8 (aka 1 byte) + // but since 8 - 0 is still 8 we mod it again so we dont have a extra byte dangling behind it + uint8_t _padding = (8 - (11 % 8)) % 8; + + // Get the maximum input value by shifting a 1 X times and subtacting a 1 to set them all + uint32_t logical_max = (1 << 11) - 1; + + uint8_t usagepage[] = { + HID_USAGE_PAGE ( HID_USAGE_PAGE_DESKTOP ), + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + + for (int i = 0; i < count; i++) { + + uint8_t usagepage[] = { + HID_USAGE ( (uint8_t)(HID_USAGE_DESKTOP_X+i) ), + HID_LOGICAL_MIN( 0 ) + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + + switch (ValueSize) + { + case 1: { + uint8_t usagepage[] = { + HID_LOGICAL_MAX_N ( (uint8_t)logical_max, 1 ), + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + break; + } + case 2: { + uint8_t usagepage[] = { + HID_LOGICAL_MAX_N ( (uint16_t)logical_max, 2 ), + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + break; + } + case 3: + case 4: { + uint8_t usagepage[] = { + HID_LOGICAL_MAX_N ( (uint32_t)logical_max, 3 ), + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + break; + } + default: { + uint8_t usagepage[] = {}; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + break; + } + } + + if (ValueSize > 0) + { + uint8_t usagepage[] ={ HID_PHYSICAL_MIN_N( -32768, 2 ), HID_PHYSICAL_MAX_N( 32767, 2 ), HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), + HID_REPORT_SIZE ( bitResolution ), HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(8 - 11%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + } + + if (_padding > 0) { + uint8_t padding[] ={ + HID_REPORT_COUNT ( 1 ), + HID_REPORT_SIZE ( _padding ), + HID_INPUT ( HID_CONSTANT ), + }; + memcpy(buff+offset, padding, sizeof(padding)); + offset += sizeof(padding); + } + } + + return offset; +}; - HID_USAGE ( HID_USAGE_DESKTOP_SLIDER ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), - HID_PHYSICAL_MIN_N( -32768, 2 ), - HID_PHYSICAL_MAX_N( 32767, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(8 - 11%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), +uint AddButtons(uint8_t* buff, size_t offset, uint8_t count) { + + if (count > 32) { + count = 32; + } + // Calculate the amount of padding needed to get it byte aligned (fuck you windows for needing this) + // We take the remainder of the mod and subtrack it from 8 (aka 1 byte) + // but since 8 - 0 is still 8 we mod it again so we dont have a extra byte dangling behind it + uint8_t _padding = (8 - (count % 8)) % 8; + + uint8_t usagepage[] = { + HID_USAGE_PAGE ( HID_USAGE_PAGE_BUTTON ), + HID_USAGE_MIN ( 1 ), + HID_USAGE_MAX ( count ), + HID_LOGICAL_MIN ( 0 ), + HID_LOGICAL_MAX ( 1 ), + HID_REPORT_COUNT ( count ), + HID_REPORT_SIZE ( 1 ), + HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + + if (_padding > 0) { + uint8_t padding[] ={ + HID_REPORT_COUNT ( 1 ), + HID_REPORT_SIZE ( _padding ), + HID_INPUT ( HID_CONSTANT ), + }; + memcpy(buff+offset, padding, sizeof(padding)); + offset += sizeof(padding); + } + + return offset; +}; - HID_USAGE ( HID_USAGE_DESKTOP_DIAL ), - HID_LOGICAL_MIN ( 0 ), - HID_LOGICAL_MAX_N ( 2047, 2 ), - HID_PHYSICAL_MIN_N( -32768, 2 ), - HID_PHYSICAL_MAX_N( 32767, 2 ), - HID_REPORT_COUNT ( 1 ), - HID_REPORT_SIZE ( 11 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_LINEAR|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - HID_REPORT_COUNT ( (uint8_t)(8 - 11%8) ), - HID_REPORT_SIZE ( 1 ), - HID_INPUT ( HID_CONSTANT ), - - HID_USAGE_PAGE ( HID_USAGE_PAGE_DESKTOP ), - HID_USAGE ( HID_USAGE_DESKTOP_HAT_SWITCH ), - HID_USAGE ( HID_USAGE_DESKTOP_HAT_SWITCH ), - HID_LOGICAL_MIN ( 1 ), - HID_LOGICAL_MAX ( 8 ), - HID_PHYSICAL_MIN ( 0 ), - HID_PHYSICAL_MAX_N( 315, 2 ), - HID_REPORT_COUNT ( 2 ), - HID_REPORT_SIZE ( 4 ), - HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), - /*HID_COLLECTION_END,*/ - HID_COLLECTION_END +uint AddHats(uint8_t* buff, size_t offset, uint8_t count) { + + // Windows only sees maximum 4 hats on one device + if (count > 4) { + count = 4; + } + + // + uint8_t _padding = bitRead(count,0); + + uint8_t usagepage[] = { + HID_USAGE_PAGE ( HID_USAGE_PAGE_DESKTOP ), + }; + memcpy(buff+offset, usagepage, sizeof(usagepage)); + offset += sizeof(usagepage); + + for (int i = 0; i < count; i++) { + uint8_t hat[] = { + HID_USAGE ( HID_USAGE_DESKTOP_HAT_SWITCH) + }; + memcpy(buff+offset, hat, sizeof(hat)); + offset += sizeof(hat); + } + + uint8_t usagepage2[] = { + HID_LOGICAL_MIN ( 1 ), + HID_LOGICAL_MAX ( 8 ), + HID_PHYSICAL_MIN ( 0 ), + HID_PHYSICAL_MAX_N( 315, 2 ), + HID_REPORT_COUNT ( count ), + HID_REPORT_SIZE ( 4 ), + HID_INPUT ( HID_DATA|HID_VARIABLE|HID_ABSOLUTE|HID_WRAP_NO|HID_PREFERRED_STATE|HID_NO_NULL_POSITION ), + }; + memcpy(buff+offset, usagepage2, sizeof(usagepage2)); + offset += sizeof(usagepage2); + + if (_padding) { + uint8_t padding[] = { + HID_REPORT_COUNT ( 1 ), + HID_REPORT_SIZE ( 4 ), + HID_INPUT ( HID_CONSTANT ), + }; + memcpy(buff+offset, padding, sizeof(padding)); + offset += sizeof(padding); + } + + return offset; }; -void setupHidDesc(void* hid_desc,uint axis_count, uint axis_resolution, uint button_count, uint dpad_count) { -} /* bit layout . = padding bits diff --git a/include/hid.hpp b/include/hid.hpp deleted file mode 100755 index 1d1ee8f..0000000 --- a/include/hid.hpp +++ /dev/null @@ -1,1199 +0,0 @@ -/* - * The MIT License (MIT) - * - * Copyright (c) 2019 Ha Thach (tinyusb.org) - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - * - * This file is part of the TinyUSB stack. - */ - -/** \ingroup group_class - * \defgroup ClassDriver_HID Human Interface Device (HID) - * @{ */ - -#ifndef _TUSB_HID_H_ -#define _TUSB_HID_H_ -#include "common/tusb_common.h" - -#ifdef __cplusplus - extern "C" { -#endif - -//--------------------------------------------------------------------+ -// Common Definitions -//--------------------------------------------------------------------+ -/** \defgroup ClassDriver_HID_Common Common Definitions - * @{ */ - -/// USB HID Descriptor -typedef struct TU_ATTR_PACKED -{ - uint8_t bLength; /**< Numeric expression that is the total size of the HID descriptor */ - uint8_t bDescriptorType; /**< Constant name specifying type of HID descriptor. */ - - uint16_t bcdHID; /**< Numeric expression identifying the HID Class Specification release */ - uint8_t bCountryCode; /**< Numeric expression identifying country code of the localized hardware. */ - uint8_t bNumDescriptors; /**< Numeric expression specifying the number of class descriptors */ - - uint8_t bReportType; /**< Type of HID class report. */ - uint16_t wReportLength; /**< the total size of the Report descriptor. */ -} tusb_hid_descriptor_hid_t; - -/// HID Subclass -typedef enum -{ - HID_SUBCLASS_NONE = 0, ///< No Subclass - HID_SUBCLASS_BOOT = 1 ///< Boot Interface Subclass -}hid_subclass_enum_t; - -/// HID Interface Protocol -typedef enum -{ - HID_ITF_PROTOCOL_NONE = 0, ///< None - HID_ITF_PROTOCOL_KEYBOARD = 1, ///< Keyboard - HID_ITF_PROTOCOL_MOUSE = 2 ///< Mouse -}hid_interface_protocol_enum_t; - -/// HID Descriptor Type -typedef enum -{ - HID_DESC_TYPE_HID = 0x21, ///< HID Descriptor - HID_DESC_TYPE_REPORT = 0x22, ///< Report Descriptor - HID_DESC_TYPE_PHYSICAL = 0x23 ///< Physical Descriptor -}hid_descriptor_enum_t; - -/// HID Request Report Type -typedef enum -{ - HID_REPORT_TYPE_INVALID = 0, - HID_REPORT_TYPE_INPUT, ///< Input - HID_REPORT_TYPE_OUTPUT, ///< Output - HID_REPORT_TYPE_FEATURE ///< Feature -}hid_report_type_t; - -/// HID Class Specific Control Request -typedef enum -{ - HID_REQ_CONTROL_GET_REPORT = 0x01, ///< Get Report - HID_REQ_CONTROL_GET_IDLE = 0x02, ///< Get Idle - HID_REQ_CONTROL_GET_PROTOCOL = 0x03, ///< Get Protocol - HID_REQ_CONTROL_SET_REPORT = 0x09, ///< Set Report - HID_REQ_CONTROL_SET_IDLE = 0x0a, ///< Set Idle - HID_REQ_CONTROL_SET_PROTOCOL = 0x0b ///< Set Protocol -}hid_request_enum_t; - -/// HID Local Code -typedef enum -{ - HID_LOCAL_NotSupported = 0 , ///< NotSupported - HID_LOCAL_Arabic , ///< Arabic - HID_LOCAL_Belgian , ///< Belgian - HID_LOCAL_Canadian_Bilingual , ///< Canadian_Bilingual - HID_LOCAL_Canadian_French , ///< Canadian_French - HID_LOCAL_Czech_Republic , ///< Czech_Republic - HID_LOCAL_Danish , ///< Danish - HID_LOCAL_Finnish , ///< Finnish - HID_LOCAL_French , ///< French - HID_LOCAL_German , ///< German - HID_LOCAL_Greek , ///< Greek - HID_LOCAL_Hebrew , ///< Hebrew - HID_LOCAL_Hungary , ///< Hungary - HID_LOCAL_International , ///< International - HID_LOCAL_Italian , ///< Italian - HID_LOCAL_Japan_Katakana , ///< Japan_Katakana - HID_LOCAL_Korean , ///< Korean - HID_LOCAL_Latin_American , ///< Latin_American - HID_LOCAL_Netherlands_Dutch , ///< Netherlands/Dutch - HID_LOCAL_Norwegian , ///< Norwegian - HID_LOCAL_Persian_Farsi , ///< Persian (Farsi) - HID_LOCAL_Poland , ///< Poland - HID_LOCAL_Portuguese , ///< Portuguese - HID_LOCAL_Russia , ///< Russia - HID_LOCAL_Slovakia , ///< Slovakia - HID_LOCAL_Spanish , ///< Spanish - HID_LOCAL_Swedish , ///< Swedish - HID_LOCAL_Swiss_French , ///< Swiss/French - HID_LOCAL_Swiss_German , ///< Swiss/German - HID_LOCAL_Switzerland , ///< Switzerland - HID_LOCAL_Taiwan , ///< Taiwan - HID_LOCAL_Turkish_Q , ///< Turkish-Q - HID_LOCAL_UK , ///< UK - HID_LOCAL_US , ///< US - HID_LOCAL_Yugoslavia , ///< Yugoslavia - HID_LOCAL_Turkish_F ///< Turkish-F -} hid_local_enum_t; - -// HID protocol value used by GetProtocol / SetProtocol -typedef enum -{ - HID_PROTOCOL_BOOT = 0, - HID_PROTOCOL_REPORT = 1 -} hid_protocol_mode_enum_t; - -/** @} */ - -//--------------------------------------------------------------------+ -// GAMEPAD -//--------------------------------------------------------------------+ -/** \addtogroup ClassDriver_HID_Gamepad Gamepad - * @{ */ - -/* From https://www.kernel.org/doc/html/latest/input/gamepad.html - ____________________________ __ - / [__ZL__] [__ZR__] \ | - / [__ TL __] [__ TR __] \ | Front Triggers - __/________________________________\__ __| - / _ \ | - / /\ __ (N) \ | - / || __ |MO| __ _ _ \ | Main Pad - | <===DP===> |SE| |ST| (W) -|- (E) | | - \ || ___ ___ _ / | - /\ \/ / \ / \ (S) /\ __| - / \________ | LS | ____ | RS | ________/ \ | -| / \ \___/ / \ \___/ / \ | | Control Sticks -| / \_____/ \_____/ \ | __| -| / \ | - \_____/ \_____/ - - |________|______| |______|___________| - D-Pad Left Right Action Pad - Stick Stick - - |_____________| - Menu Pad - - Most gamepads have the following features: - - Action-Pad 4 buttons in diamonds-shape (on the right side) NORTH, SOUTH, WEST and EAST. - - D-Pad (Direction-pad) 4 buttons (on the left side) that point up, down, left and right. - - Menu-Pad Different constellations, but most-times 2 buttons: SELECT - START. - - Analog-Sticks provide freely moveable sticks to control directions, Analog-sticks may also - provide a digital button if you press them. - - Triggers are located on the upper-side of the pad in vertical direction. The upper buttons - are normally named Left- and Right-Triggers, the lower buttons Z-Left and Z-Right. - - Rumble Many devices provide force-feedback features. But are mostly just simple rumble motors. - */ - -/// HID Gamepad Protocol Report. -typedef struct TU_ATTR_PACKED -{ - int8_t x; ///< Delta x movement of left analog-stick - int8_t y; ///< Delta y movement of left analog-stick - int8_t z; ///< Delta z movement of right analog-joystick - int8_t rz; ///< Delta Rz movement of right analog-joystick - int8_t rx; ///< Delta Rx movement of analog left trigger - int8_t ry; ///< Delta Ry movement of analog right trigger - uint8_t hat; ///< Buttons mask for currently pressed buttons in the DPad/hat - uint32_t buttons; ///< Buttons mask for currently pressed buttons -}hid_gamepad_report_t; - -#ifndef TU_BIT_L -#define TU_BIT_L(n) (1ULL << (n)) -#endif - -/// Standard Gamepad Buttons Bitmap -typedef enum -{ - GAMEPAD_BUTTON_0 = TU_BIT_L(0), - GAMEPAD_BUTTON_1 = TU_BIT_L(1), - GAMEPAD_BUTTON_2 = TU_BIT_L(2), - GAMEPAD_BUTTON_3 = TU_BIT_L(3), - GAMEPAD_BUTTON_4 = TU_BIT_L(4), - GAMEPAD_BUTTON_5 = TU_BIT_L(5), - GAMEPAD_BUTTON_6 = TU_BIT_L(6), - GAMEPAD_BUTTON_7 = TU_BIT_L(7), - GAMEPAD_BUTTON_8 = TU_BIT_L(8), - GAMEPAD_BUTTON_9 = TU_BIT_L(9), - GAMEPAD_BUTTON_10 = TU_BIT_L(10), - GAMEPAD_BUTTON_11 = TU_BIT_L(11), - GAMEPAD_BUTTON_12 = TU_BIT_L(12), - GAMEPAD_BUTTON_13 = TU_BIT_L(13), - GAMEPAD_BUTTON_14 = TU_BIT_L(14), - GAMEPAD_BUTTON_15 = TU_BIT_L(15), - GAMEPAD_BUTTON_16 = TU_BIT_L(16), - GAMEPAD_BUTTON_17 = TU_BIT_L(17), - GAMEPAD_BUTTON_18 = TU_BIT_L(18), - GAMEPAD_BUTTON_19 = TU_BIT_L(19), - GAMEPAD_BUTTON_20 = TU_BIT_L(20), - GAMEPAD_BUTTON_21 = TU_BIT_L(21), - GAMEPAD_BUTTON_22 = TU_BIT_L(22), - GAMEPAD_BUTTON_23 = TU_BIT_L(23), - GAMEPAD_BUTTON_24 = TU_BIT_L(24), - GAMEPAD_BUTTON_25 = TU_BIT_L(25), - GAMEPAD_BUTTON_26 = TU_BIT_L(26), - GAMEPAD_BUTTON_27 = TU_BIT_L(27), - GAMEPAD_BUTTON_28 = TU_BIT_L(28), - GAMEPAD_BUTTON_29 = TU_BIT_L(29), - GAMEPAD_BUTTON_30 = TU_BIT_L(30), - GAMEPAD_BUTTON_31 = TU_BIT_L(31), - GAMEPAD_BUTTON_32 = TU_BIT_L(32), - GAMEPAD_BUTTON_33 = TU_BIT_L(33), - GAMEPAD_BUTTON_34 = TU_BIT_L(34), - GAMEPAD_BUTTON_35 = TU_BIT_L(35), - GAMEPAD_BUTTON_36 = TU_BIT_L(36), - GAMEPAD_BUTTON_37 = TU_BIT_L(37), - GAMEPAD_BUTTON_38 = TU_BIT_L(38), - GAMEPAD_BUTTON_39 = TU_BIT_L(39), - GAMEPAD_BUTTON_40 = TU_BIT_L(40), - GAMEPAD_BUTTON_41 = TU_BIT_L(41), - GAMEPAD_BUTTON_42 = TU_BIT_L(42), - GAMEPAD_BUTTON_43 = TU_BIT_L(43), - GAMEPAD_BUTTON_44 = TU_BIT_L(44), - GAMEPAD_BUTTON_45 = TU_BIT_L(45), - GAMEPAD_BUTTON_46 = TU_BIT_L(46), - GAMEPAD_BUTTON_47 = TU_BIT_L(47), - GAMEPAD_BUTTON_48 = TU_BIT_L(48), - GAMEPAD_BUTTON_49 = TU_BIT_L(49), - GAMEPAD_BUTTON_50 = TU_BIT_L(50), - GAMEPAD_BUTTON_51 = TU_BIT_L(51), - GAMEPAD_BUTTON_52 = TU_BIT_L(52), - GAMEPAD_BUTTON_53 = TU_BIT_L(53), - GAMEPAD_BUTTON_54 = TU_BIT_L(54), - GAMEPAD_BUTTON_55 = TU_BIT_L(55), - GAMEPAD_BUTTON_56 = TU_BIT_L(56), - GAMEPAD_BUTTON_57 = TU_BIT_L(57), - GAMEPAD_BUTTON_58 = TU_BIT_L(58), - GAMEPAD_BUTTON_59 = TU_BIT_L(59), - GAMEPAD_BUTTON_60 = TU_BIT_L(60), - GAMEPAD_BUTTON_61 = TU_BIT_L(61), - GAMEPAD_BUTTON_62 = TU_BIT_L(62), - GAMEPAD_BUTTON_63 = TU_BIT_L(63), - }hid_gamepad_button_bm_t; - -/// Standard Gamepad Buttons Naming from Linux input event codes -/// https://github.com/torvalds/linux/blob/master/include/uapi/linux/input-event-codes.h -#define GAMEPAD_BUTTON_A GAMEPAD_BUTTON_0 -#define GAMEPAD_BUTTON_SOUTH GAMEPAD_BUTTON_0 - -#define GAMEPAD_BUTTON_B GAMEPAD_BUTTON_1 -#define GAMEPAD_BUTTON_EAST GAMEPAD_BUTTON_1 - -#define GAMEPAD_BUTTON_C GAMEPAD_BUTTON_2 - -#define GAMEPAD_BUTTON_X GAMEPAD_BUTTON_3 -#define GAMEPAD_BUTTON_NORTH GAMEPAD_BUTTON_3 - -#define GAMEPAD_BUTTON_Y GAMEPAD_BUTTON_4 -#define GAMEPAD_BUTTON_WEST GAMEPAD_BUTTON_4 - -#define GAMEPAD_BUTTON_Z GAMEPAD_BUTTON_5 -#define GAMEPAD_BUTTON_TL GAMEPAD_BUTTON_6 -#define GAMEPAD_BUTTON_TR GAMEPAD_BUTTON_7 -#define GAMEPAD_BUTTON_TL2 GAMEPAD_BUTTON_8 -#define GAMEPAD_BUTTON_TR2 GAMEPAD_BUTTON_9 -#define GAMEPAD_BUTTON_SELECT GAMEPAD_BUTTON_10 -#define GAMEPAD_BUTTON_START GAMEPAD_BUTTON_11 -#define GAMEPAD_BUTTON_MODE GAMEPAD_BUTTON_12 -#define GAMEPAD_BUTTON_THUMBL GAMEPAD_BUTTON_13 -#define GAMEPAD_BUTTON_THUMBR GAMEPAD_BUTTON_14 - -/// Standard Gamepad HAT/DPAD Buttons (from Linux input event codes) -typedef enum -{ - GAMEPAD_HAT_CENTERED = 0, ///< DPAD_CENTERED - GAMEPAD_HAT_UP = 1, ///< DPAD_UP - GAMEPAD_HAT_UP_RIGHT = 2, ///< DPAD_UP_RIGHT - GAMEPAD_HAT_RIGHT = 3, ///< DPAD_RIGHT - GAMEPAD_HAT_DOWN_RIGHT = 4, ///< DPAD_DOWN_RIGHT - GAMEPAD_HAT_DOWN = 5, ///< DPAD_DOWN - GAMEPAD_HAT_DOWN_LEFT = 6, ///< DPAD_DOWN_LEFT - GAMEPAD_HAT_LEFT = 7, ///< DPAD_LEFT - GAMEPAD_HAT_UP_LEFT = 8, ///< DPAD_UP_LEFT -}hid_gamepad_hat_t; - -/// @} - -//--------------------------------------------------------------------+ -// MOUSE -//--------------------------------------------------------------------+ -/** \addtogroup ClassDriver_HID_Mouse Mouse - * @{ */ - -/// Standard HID Boot Protocol Mouse Report. -typedef struct TU_ATTR_PACKED -{ - uint8_t buttons; /**< buttons mask for currently pressed buttons in the mouse. */ - int8_t x; /**< Current delta x movement of the mouse. */ - int8_t y; /**< Current delta y movement on the mouse. */ - int8_t wheel; /**< Current delta wheel movement on the mouse. */ - int8_t pan; // using AC Pan -} hid_mouse_report_t; - -/// Standard Mouse Buttons Bitmap -typedef enum -{ - MOUSE_BUTTON_LEFT = TU_BIT(0), ///< Left button - MOUSE_BUTTON_RIGHT = TU_BIT(1), ///< Right button - MOUSE_BUTTON_MIDDLE = TU_BIT(2), ///< Middle button - MOUSE_BUTTON_BACKWARD = TU_BIT(3), ///< Backward button, - MOUSE_BUTTON_FORWARD = TU_BIT(4), ///< Forward button, -}hid_mouse_button_bm_t; - -/// @} - -//--------------------------------------------------------------------+ -// Keyboard -//--------------------------------------------------------------------+ -/** \addtogroup ClassDriver_HID_Keyboard Keyboard - * @{ */ - -/// Standard HID Boot Protocol Keyboard Report. -typedef struct TU_ATTR_PACKED -{ - uint8_t modifier; /**< Keyboard modifier (KEYBOARD_MODIFIER_* masks). */ - uint8_t reserved; /**< Reserved for OEM use, always set to 0. */ - uint8_t keycode[6]; /**< Key codes of the currently pressed keys. */ -} hid_keyboard_report_t; - -/// Keyboard modifier codes bitmap -typedef enum -{ - KEYBOARD_MODIFIER_LEFTCTRL = TU_BIT(0), ///< Left Control - KEYBOARD_MODIFIER_LEFTSHIFT = TU_BIT(1), ///< Left Shift - KEYBOARD_MODIFIER_LEFTALT = TU_BIT(2), ///< Left Alt - KEYBOARD_MODIFIER_LEFTGUI = TU_BIT(3), ///< Left Window - KEYBOARD_MODIFIER_RIGHTCTRL = TU_BIT(4), ///< Right Control - KEYBOARD_MODIFIER_RIGHTSHIFT = TU_BIT(5), ///< Right Shift - KEYBOARD_MODIFIER_RIGHTALT = TU_BIT(6), ///< Right Alt - KEYBOARD_MODIFIER_RIGHTGUI = TU_BIT(7) ///< Right Window -}hid_keyboard_modifier_bm_t; - -typedef enum -{ - KEYBOARD_LED_NUMLOCK = TU_BIT(0), ///< Num Lock LED - KEYBOARD_LED_CAPSLOCK = TU_BIT(1), ///< Caps Lock LED - KEYBOARD_LED_SCROLLLOCK = TU_BIT(2), ///< Scroll Lock LED - KEYBOARD_LED_COMPOSE = TU_BIT(3), ///< Composition Mode - KEYBOARD_LED_KANA = TU_BIT(4) ///< Kana mode -}hid_keyboard_led_bm_t; - -/// @} - -//--------------------------------------------------------------------+ -// HID KEYCODE -//--------------------------------------------------------------------+ -#define HID_KEY_NONE 0x00 -#define HID_KEY_A 0x04 -#define HID_KEY_B 0x05 -#define HID_KEY_C 0x06 -#define HID_KEY_D 0x07 -#define HID_KEY_E 0x08 -#define HID_KEY_F 0x09 -#define HID_KEY_G 0x0A -#define HID_KEY_H 0x0B -#define HID_KEY_I 0x0C -#define HID_KEY_J 0x0D -#define HID_KEY_K 0x0E -#define HID_KEY_L 0x0F -#define HID_KEY_M 0x10 -#define HID_KEY_N 0x11 -#define HID_KEY_O 0x12 -#define HID_KEY_P 0x13 -#define HID_KEY_Q 0x14 -#define HID_KEY_R 0x15 -#define HID_KEY_S 0x16 -#define HID_KEY_T 0x17 -#define HID_KEY_U 0x18 -#define HID_KEY_V 0x19 -#define HID_KEY_W 0x1A -#define HID_KEY_X 0x1B -#define HID_KEY_Y 0x1C -#define HID_KEY_Z 0x1D -#define HID_KEY_1 0x1E -#define HID_KEY_2 0x1F -#define HID_KEY_3 0x20 -#define HID_KEY_4 0x21 -#define HID_KEY_5 0x22 -#define HID_KEY_6 0x23 -#define HID_KEY_7 0x24 -#define HID_KEY_8 0x25 -#define HID_KEY_9 0x26 -#define HID_KEY_0 0x27 -#define HID_KEY_ENTER 0x28 -#define HID_KEY_ESCAPE 0x29 -#define HID_KEY_BACKSPACE 0x2A -#define HID_KEY_TAB 0x2B -#define HID_KEY_SPACE 0x2C -#define HID_KEY_MINUS 0x2D -#define HID_KEY_EQUAL 0x2E -#define HID_KEY_BRACKET_LEFT 0x2F -#define HID_KEY_BRACKET_RIGHT 0x30 -#define HID_KEY_BACKSLASH 0x31 -#define HID_KEY_EUROPE_1 0x32 -#define HID_KEY_SEMICOLON 0x33 -#define HID_KEY_APOSTROPHE 0x34 -#define HID_KEY_GRAVE 0x35 -#define HID_KEY_COMMA 0x36 -#define HID_KEY_PERIOD 0x37 -#define HID_KEY_SLASH 0x38 -#define HID_KEY_CAPS_LOCK 0x39 -#define HID_KEY_F1 0x3A -#define HID_KEY_F2 0x3B -#define HID_KEY_F3 0x3C -#define HID_KEY_F4 0x3D -#define HID_KEY_F5 0x3E -#define HID_KEY_F6 0x3F -#define HID_KEY_F7 0x40 -#define HID_KEY_F8 0x41 -#define HID_KEY_F9 0x42 -#define HID_KEY_F10 0x43 -#define HID_KEY_F11 0x44 -#define HID_KEY_F12 0x45 -#define HID_KEY_PRINT_SCREEN 0x46 -#define HID_KEY_SCROLL_LOCK 0x47 -#define HID_KEY_PAUSE 0x48 -#define HID_KEY_INSERT 0x49 -#define HID_KEY_HOME 0x4A -#define HID_KEY_PAGE_UP 0x4B -#define HID_KEY_DELETE 0x4C -#define HID_KEY_END 0x4D -#define HID_KEY_PAGE_DOWN 0x4E -#define HID_KEY_ARROW_RIGHT 0x4F -#define HID_KEY_ARROW_LEFT 0x50 -#define HID_KEY_ARROW_DOWN 0x51 -#define HID_KEY_ARROW_UP 0x52 -#define HID_KEY_NUM_LOCK 0x53 -#define HID_KEY_KEYPAD_DIVIDE 0x54 -#define HID_KEY_KEYPAD_MULTIPLY 0x55 -#define HID_KEY_KEYPAD_SUBTRACT 0x56 -#define HID_KEY_KEYPAD_ADD 0x57 -#define HID_KEY_KEYPAD_ENTER 0x58 -#define HID_KEY_KEYPAD_1 0x59 -#define HID_KEY_KEYPAD_2 0x5A -#define HID_KEY_KEYPAD_3 0x5B -#define HID_KEY_KEYPAD_4 0x5C -#define HID_KEY_KEYPAD_5 0x5D -#define HID_KEY_KEYPAD_6 0x5E -#define HID_KEY_KEYPAD_7 0x5F -#define HID_KEY_KEYPAD_8 0x60 -#define HID_KEY_KEYPAD_9 0x61 -#define HID_KEY_KEYPAD_0 0x62 -#define HID_KEY_KEYPAD_DECIMAL 0x63 -#define HID_KEY_EUROPE_2 0x64 -#define HID_KEY_APPLICATION 0x65 -#define HID_KEY_POWER 0x66 -#define HID_KEY_KEYPAD_EQUAL 0x67 -#define HID_KEY_F13 0x68 -#define HID_KEY_F14 0x69 -#define HID_KEY_F15 0x6A -#define HID_KEY_F16 0x6B -#define HID_KEY_F17 0x6C -#define HID_KEY_F18 0x6D -#define HID_KEY_F19 0x6E -#define HID_KEY_F20 0x6F -#define HID_KEY_F21 0x70 -#define HID_KEY_F22 0x71 -#define HID_KEY_F23 0x72 -#define HID_KEY_F24 0x73 -#define HID_KEY_EXECUTE 0x74 -#define HID_KEY_HELP 0x75 -#define HID_KEY_MENU 0x76 -#define HID_KEY_SELECT 0x77 -#define HID_KEY_STOP 0x78 -#define HID_KEY_AGAIN 0x79 -#define HID_KEY_UNDO 0x7A -#define HID_KEY_CUT 0x7B -#define HID_KEY_COPY 0x7C -#define HID_KEY_PASTE 0x7D -#define HID_KEY_FIND 0x7E -#define HID_KEY_MUTE 0x7F -#define HID_KEY_VOLUME_UP 0x80 -#define HID_KEY_VOLUME_DOWN 0x81 -#define HID_KEY_LOCKING_CAPS_LOCK 0x82 -#define HID_KEY_LOCKING_NUM_LOCK 0x83 -#define HID_KEY_LOCKING_SCROLL_LOCK 0x84 -#define HID_KEY_KEYPAD_COMMA 0x85 -#define HID_KEY_KEYPAD_EQUAL_SIGN 0x86 -#define HID_KEY_KANJI1 0x87 -#define HID_KEY_KANJI2 0x88 -#define HID_KEY_KANJI3 0x89 -#define HID_KEY_KANJI4 0x8A -#define HID_KEY_KANJI5 0x8B -#define HID_KEY_KANJI6 0x8C -#define HID_KEY_KANJI7 0x8D -#define HID_KEY_KANJI8 0x8E -#define HID_KEY_KANJI9 0x8F -#define HID_KEY_LANG1 0x90 -#define HID_KEY_LANG2 0x91 -#define HID_KEY_LANG3 0x92 -#define HID_KEY_LANG4 0x93 -#define HID_KEY_LANG5 0x94 -#define HID_KEY_LANG6 0x95 -#define HID_KEY_LANG7 0x96 -#define HID_KEY_LANG8 0x97 -#define HID_KEY_LANG9 0x98 -#define HID_KEY_ALTERNATE_ERASE 0x99 -#define HID_KEY_SYSREQ_ATTENTION 0x9A -#define HID_KEY_CANCEL 0x9B -#define HID_KEY_CLEAR 0x9C -#define HID_KEY_PRIOR 0x9D -#define HID_KEY_RETURN 0x9E -#define HID_KEY_SEPARATOR 0x9F -#define HID_KEY_OUT 0xA0 -#define HID_KEY_OPER 0xA1 -#define HID_KEY_CLEAR_AGAIN 0xA2 -#define HID_KEY_CRSEL_PROPS 0xA3 -#define HID_KEY_EXSEL 0xA4 -// RESERVED 0xA5-DF -#define HID_KEY_CONTROL_LEFT 0xE0 -#define HID_KEY_SHIFT_LEFT 0xE1 -#define HID_KEY_ALT_LEFT 0xE2 -#define HID_KEY_GUI_LEFT 0xE3 -#define HID_KEY_CONTROL_RIGHT 0xE4 -#define HID_KEY_SHIFT_RIGHT 0xE5 -#define HID_KEY_ALT_RIGHT 0xE6 -#define HID_KEY_GUI_RIGHT 0xE7 - - -//--------------------------------------------------------------------+ -// REPORT DESCRIPTOR -//--------------------------------------------------------------------+ - -//------------- ITEM & TAG -------------// -#define HID_REPORT_DATA_0(data) -#define HID_REPORT_DATA_1(data) , data -#define HID_REPORT_DATA_2(data) , U16_TO_U8S_LE(data) -#define HID_REPORT_DATA_3(data) , U32_TO_U8S_LE(data) - -#define HID_REPORT_ITEM(data, tag, type, size) \ - (((tag) << 4) | ((type) << 2) | (size)) HID_REPORT_DATA_##size(data) - -// Report Item Types -enum { - RI_TYPE_MAIN = 0, - RI_TYPE_GLOBAL = 1, - RI_TYPE_LOCAL = 2 -}; - -//------------- Main Items - HID 1.11 section 6.2.2.4 -------------// - -// Report Item Main group -enum { - RI_MAIN_INPUT = 8, - RI_MAIN_OUTPUT = 9, - RI_MAIN_COLLECTION = 10, - RI_MAIN_FEATURE = 11, - RI_MAIN_COLLECTION_END = 12 -}; - -#define HID_INPUT(x) HID_REPORT_ITEM(x, RI_MAIN_INPUT , RI_TYPE_MAIN, 1) -#define HID_OUTPUT(x) HID_REPORT_ITEM(x, RI_MAIN_OUTPUT , RI_TYPE_MAIN, 1) -#define HID_COLLECTION(x) HID_REPORT_ITEM(x, RI_MAIN_COLLECTION , RI_TYPE_MAIN, 1) -#define HID_FEATURE(x) HID_REPORT_ITEM(x, RI_MAIN_FEATURE , RI_TYPE_MAIN, 1) -#define HID_COLLECTION_END HID_REPORT_ITEM(x, RI_MAIN_COLLECTION_END, RI_TYPE_MAIN, 0) - -//------------- Input, Output, Feature - HID 1.11 section 6.2.2.5 -------------// -#define HID_DATA (0<<0) -#define HID_CONSTANT (1<<0) - -#define HID_ARRAY (0<<1) -#define HID_VARIABLE (1<<1) - -#define HID_ABSOLUTE (0<<2) -#define HID_RELATIVE (1<<2) - -#define HID_WRAP_NO (0<<3) -#define HID_WRAP (1<<3) - -#define HID_LINEAR (0<<4) -#define HID_NONLINEAR (1<<4) - -#define HID_PREFERRED_STATE (0<<5) -#define HID_PREFERRED_NO (1<<5) - -#define HID_NO_NULL_POSITION (0<<6) -#define HID_NULL_STATE (1<<6) - -#define HID_NON_VOLATILE (0<<7) -#define HID_VOLATILE (1<<7) - -#define HID_BITFIELD (0<<8) -#define HID_BUFFERED_BYTES (1<<8) - -//------------- Collection Item - HID 1.11 section 6.2.2.6 -------------// -enum { - HID_COLLECTION_PHYSICAL = 0, - HID_COLLECTION_APPLICATION, - HID_COLLECTION_LOGICAL, - HID_COLLECTION_REPORT, - HID_COLLECTION_NAMED_ARRAY, - HID_COLLECTION_USAGE_SWITCH, - HID_COLLECTION_USAGE_MODIFIER -}; - -//------------- Global Items - HID 1.11 section 6.2.2.7 -------------// - -// Report Item Global group -enum { - RI_GLOBAL_USAGE_PAGE = 0, - RI_GLOBAL_LOGICAL_MIN = 1, - RI_GLOBAL_LOGICAL_MAX = 2, - RI_GLOBAL_PHYSICAL_MIN = 3, - RI_GLOBAL_PHYSICAL_MAX = 4, - RI_GLOBAL_UNIT_EXPONENT = 5, - RI_GLOBAL_UNIT = 6, - RI_GLOBAL_REPORT_SIZE = 7, - RI_GLOBAL_REPORT_ID = 8, - RI_GLOBAL_REPORT_COUNT = 9, - RI_GLOBAL_PUSH = 10, - RI_GLOBAL_POP = 11 -}; - -#define HID_USAGE_PAGE(x) HID_REPORT_ITEM(x, RI_GLOBAL_USAGE_PAGE, RI_TYPE_GLOBAL, 1) -#define HID_USAGE_PAGE_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_USAGE_PAGE, RI_TYPE_GLOBAL, n) - -#define HID_LOGICAL_MIN(x) HID_REPORT_ITEM(x, RI_GLOBAL_LOGICAL_MIN, RI_TYPE_GLOBAL, 1) -#define HID_LOGICAL_MIN_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_LOGICAL_MIN, RI_TYPE_GLOBAL, n) - -#define HID_LOGICAL_MAX(x) HID_REPORT_ITEM(x, RI_GLOBAL_LOGICAL_MAX, RI_TYPE_GLOBAL, 1) -#define HID_LOGICAL_MAX_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_LOGICAL_MAX, RI_TYPE_GLOBAL, n) - -#define HID_PHYSICAL_MIN(x) HID_REPORT_ITEM(x, RI_GLOBAL_PHYSICAL_MIN, RI_TYPE_GLOBAL, 1) -#define HID_PHYSICAL_MIN_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_PHYSICAL_MIN, RI_TYPE_GLOBAL, n) - -#define HID_PHYSICAL_MAX(x) HID_REPORT_ITEM(x, RI_GLOBAL_PHYSICAL_MAX, RI_TYPE_GLOBAL, 1) -#define HID_PHYSICAL_MAX_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_PHYSICAL_MAX, RI_TYPE_GLOBAL, n) - -#define HID_UNIT_EXPONENT(x) HID_REPORT_ITEM(x, RI_GLOBAL_UNIT_EXPONENT, RI_TYPE_GLOBAL, 1) -#define HID_UNIT_EXPONENT_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_UNIT_EXPONENT, RI_TYPE_GLOBAL, n) - -#define HID_UNIT(x) HID_REPORT_ITEM(x, RI_GLOBAL_UNIT, RI_TYPE_GLOBAL, 1) -#define HID_UNIT_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_UNIT, RI_TYPE_GLOBAL, n) - -#define HID_REPORT_SIZE(x) HID_REPORT_ITEM(x, RI_GLOBAL_REPORT_SIZE, RI_TYPE_GLOBAL, 1) -#define HID_REPORT_SIZE_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_REPORT_SIZE, RI_TYPE_GLOBAL, n) - -#define HID_REPORT_ID(x) HID_REPORT_ITEM(x, RI_GLOBAL_REPORT_ID, RI_TYPE_GLOBAL, 1), -#define HID_REPORT_ID_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_REPORT_ID, RI_TYPE_GLOBAL, n), - -#define HID_REPORT_COUNT(x) HID_REPORT_ITEM(x, RI_GLOBAL_REPORT_COUNT, RI_TYPE_GLOBAL, 1) -#define HID_REPORT_COUNT_N(x, n) HID_REPORT_ITEM(x, RI_GLOBAL_REPORT_COUNT, RI_TYPE_GLOBAL, n) - -#define HID_PUSH HID_REPORT_ITEM(x, RI_GLOBAL_PUSH, RI_TYPE_GLOBAL, 0) -#define HID_POP HID_REPORT_ITEM(x, RI_GLOBAL_POP, RI_TYPE_GLOBAL, 0) - -//------------- LOCAL ITEMS 6.2.2.8 -------------// - -enum { - RI_LOCAL_USAGE = 0, - RI_LOCAL_USAGE_MIN = 1, - RI_LOCAL_USAGE_MAX = 2, - RI_LOCAL_DESIGNATOR_INDEX = 3, - RI_LOCAL_DESIGNATOR_MIN = 4, - RI_LOCAL_DESIGNATOR_MAX = 5, - // 6 is reserved - RI_LOCAL_STRING_INDEX = 7, - RI_LOCAL_STRING_MIN = 8, - RI_LOCAL_STRING_MAX = 9, - RI_LOCAL_DELIMITER = 10, -}; - -#define HID_USAGE(x) HID_REPORT_ITEM(x, RI_LOCAL_USAGE, RI_TYPE_LOCAL, 1) -#define HID_USAGE_N(x, n) HID_REPORT_ITEM(x, RI_LOCAL_USAGE, RI_TYPE_LOCAL, n) - -#define HID_USAGE_MIN(x) HID_REPORT_ITEM(x, RI_LOCAL_USAGE_MIN, RI_TYPE_LOCAL, 1) -#define HID_USAGE_MIN_N(x, n) HID_REPORT_ITEM(x, RI_LOCAL_USAGE_MIN, RI_TYPE_LOCAL, n) - -#define HID_USAGE_MAX(x) HID_REPORT_ITEM(x, RI_LOCAL_USAGE_MAX, RI_TYPE_LOCAL, 1) -#define HID_USAGE_MAX_N(x, n) HID_REPORT_ITEM(x, RI_LOCAL_USAGE_MAX, RI_TYPE_LOCAL, n) - -//--------------------------------------------------------------------+ -// Usage Table -//--------------------------------------------------------------------+ - -/// HID Usage Table - Table 1: Usage Page Summary -enum { - HID_USAGE_PAGE_DESKTOP = 0x01, - HID_USAGE_PAGE_SIMULATE = 0x02, - HID_USAGE_PAGE_VIRTUAL_REALITY = 0x03, - HID_USAGE_PAGE_SPORT = 0x04, - HID_USAGE_PAGE_GAME = 0x05, - HID_USAGE_PAGE_GENERIC_DEVICE = 0x06, - HID_USAGE_PAGE_KEYBOARD = 0x07, - HID_USAGE_PAGE_LED = 0x08, - HID_USAGE_PAGE_BUTTON = 0x09, - HID_USAGE_PAGE_ORDINAL = 0x0a, - HID_USAGE_PAGE_TELEPHONY = 0x0b, - HID_USAGE_PAGE_CONSUMER = 0x0c, - HID_USAGE_PAGE_DIGITIZER = 0x0d, - HID_USAGE_PAGE_PID = 0x0f, - HID_USAGE_PAGE_UNICODE = 0x10, - HID_USAGE_PAGE_ALPHA_DISPLAY = 0x14, - HID_USAGE_PAGE_MEDICAL = 0x40, - HID_USAGE_PAGE_MONITOR = 0x80, //0x80 - 0x83 - HID_USAGE_PAGE_POWER = 0x84, // 0x084 - 0x87 - HID_USAGE_PAGE_BARCODE_SCANNER = 0x8c, - HID_USAGE_PAGE_SCALE = 0x8d, - HID_USAGE_PAGE_MSR = 0x8e, - HID_USAGE_PAGE_CAMERA = 0x90, - HID_USAGE_PAGE_ARCADE = 0x91, - HID_USAGE_PAGE_VENDOR = 0xFF00 // 0xFF00 - 0xFFFF -}; - -/// HID Usage Table - Table 6: Generic Desktop Page -enum { - HID_USAGE_DESKTOP_POINTER = 0x01, - HID_USAGE_DESKTOP_MOUSE = 0x02, - HID_USAGE_DESKTOP_JOYSTICK = 0x04, - HID_USAGE_DESKTOP_GAMEPAD = 0x05, - HID_USAGE_DESKTOP_KEYBOARD = 0x06, - HID_USAGE_DESKTOP_KEYPAD = 0x07, - HID_USAGE_DESKTOP_MULTI_AXIS_CONTROLLER = 0x08, - HID_USAGE_DESKTOP_TABLET_PC_SYSTEM = 0x09, - - HID_USAGE_DESKTOP_X = 0x30, - HID_USAGE_DESKTOP_Y = 0x31, - HID_USAGE_DESKTOP_Z = 0x32, - HID_USAGE_DESKTOP_RX = 0x33, - HID_USAGE_DESKTOP_RY = 0x34, - HID_USAGE_DESKTOP_RZ = 0x35, - HID_USAGE_DESKTOP_SLIDER = 0x36, - HID_USAGE_DESKTOP_DIAL = 0x37, - HID_USAGE_DESKTOP_WHEEL = 0x38, - HID_USAGE_DESKTOP_HAT_SWITCH = 0x39, - HID_USAGE_DESKTOP_COUNTED_BUFFER = 0x3a, - HID_USAGE_DESKTOP_BYTE_COUNT = 0x3b, - HID_USAGE_DESKTOP_MOTION_WAKEUP = 0x3c, - HID_USAGE_DESKTOP_START = 0x3d, - HID_USAGE_DESKTOP_SELECT = 0x3e, - HID_USAGE_DESKTOP_VX = 0x40, - HID_USAGE_DESKTOP_VY = 0x41, - HID_USAGE_DESKTOP_VZ = 0x42, - HID_USAGE_DESKTOP_VBRX = 0x43, - HID_USAGE_DESKTOP_VBRY = 0x44, - HID_USAGE_DESKTOP_VBRZ = 0x45, - HID_USAGE_DESKTOP_VNO = 0x46, - - HID_USAGE_DESKTOP_FEATURE_NOTIFICATION = 0x47, - HID_USAGE_DESKTOP_RESOLUTION_MULTIPLIER = 0x48, - HID_USAGE_DESKTOP_SYSTEM_CONTROL = 0x80, - HID_USAGE_DESKTOP_SYSTEM_POWER_DOWN = 0x81, - HID_USAGE_DESKTOP_SYSTEM_SLEEP = 0x82, - HID_USAGE_DESKTOP_SYSTEM_WAKE_UP = 0x83, - HID_USAGE_DESKTOP_SYSTEM_CONTEXT_MENU = 0x84, - HID_USAGE_DESKTOP_SYSTEM_MAIN_MENU = 0x85, - HID_USAGE_DESKTOP_SYSTEM_APP_MENU = 0x86, - HID_USAGE_DESKTOP_SYSTEM_MENU_HELP = 0x87, - HID_USAGE_DESKTOP_SYSTEM_MENU_EXIT = 0x88, - HID_USAGE_DESKTOP_SYSTEM_MENU_SELECT = 0x89, - HID_USAGE_DESKTOP_SYSTEM_MENU_RIGHT = 0x8A, - HID_USAGE_DESKTOP_SYSTEM_MENU_LEFT = 0x8B, - HID_USAGE_DESKTOP_SYSTEM_MENU_UP = 0x8C, - HID_USAGE_DESKTOP_SYSTEM_MENU_DOWN = 0x8D, - HID_USAGE_DESKTOP_SYSTEM_COLD_RESTART = 0x8E, - HID_USAGE_DESKTOP_SYSTEM_WARM_RESTART = 0x8F, - - HID_USAGE_DESKTOP_DPAD_UP = 0x90, - HID_USAGE_DESKTOP_DPAD_DOWN = 0x91, - HID_USAGE_DESKTOP_DPAD_RIGHT = 0x92, - HID_USAGE_DESKTOP_DPAD_LEFT = 0x93, - - HID_USAGE_DESKTOP_SYSTEM_DOCK = 0xA0, - HID_USAGE_DESKTOP_SYSTEM_UNDOCK = 0xA1, - HID_USAGE_DESKTOP_SYSTEM_SETUP = 0xA2, - HID_USAGE_DESKTOP_SYSTEM_BREAK = 0xA3, - HID_USAGE_DESKTOP_SYSTEM_DEBUGGER_BREAK = 0xA4, - - HID_USAGE_DESKTOP_APPLICATION_BREAK = 0xA5, - HID_USAGE_DESKTOP_APPLICATION_DEBUGGER_BREAK = 0xA6, - - HID_USAGE_DESKTOP_SYSTEM_SPEAKER_MUTE = 0xA7, - HID_USAGE_DESKTOP_SYSTEM_HIBERNATE = 0xA8, - HID_USAGE_DESKTOP_SYSTEM_DISPLAY_INVERT = 0xB0, - HID_USAGE_DESKTOP_SYSTEM_DISPLAY_INTERNAL = 0xB1, - HID_USAGE_DESKTOP_SYSTEM_DISPLAY_EXTERNAL = 0xB2, - HID_USAGE_DESKTOP_SYSTEM_DISPLAY_BOTH = 0xB3, - HID_USAGE_DESKTOP_SYSTEM_DISPLAY_DUAL = 0xB4, - HID_USAGE_DESKTOP_SYSTEM_DISPLAY_TOGGLE_INT_EXT = 0xB5, - HID_USAGE_DESKTOP_SYSTEM_DISPLAY_SWAP_PRIMARY_SECONDARY = 0xB6, - HID_USAGE_DESKTOP_SYSTEM_DISPLAY_LCD_AUTOSCALE = 0xB7 -}; - -/// HID Usage Table - Table 8: Game controls Page -enum -{ - HID_USAGE_GAME_UNDEFINED = 0x00, - HID_USAGE_GAME_3D_CONTROLLER = 0x01, - HID_USAGE_GAME_PINBAL_DEVICE = 0x02, - HID_USAGE_GAME_GUN_DEVICE = 0x03, - /* 04-1f RESERVED*/ - HID_USAGE_GAME_POINT_OF_VIEW = 0x20, - HID_USAGE_GAME_TURN_LR = 0x21, - HID_USAGE_GAME_PITCH_FB = 0x22, - HID_USAGE_GAME_ROLL_LR = 0x23, - HID_USAGE_GAME_MOVE_LR = 0x24, - HID_USAGE_GAME_MOVE_FB = 0x25, - HID_USAGE_GAME_MOVE_UD = 0x26, - HID_USAGE_GAME_LEAN_RL = 0x27, - HID_USAGE_GAME_LEAN_FB = 0x28, - HID_USAGE_GAME_HEIGHT_POV = 0x29, - HID_USAGE_GAME_FLIPPER = 0x2A, - HID_USAGE_GAME_SECONDARY_FLIPPER = 0x2B, - HID_USAGE_GAME_BUMP = 0x2C, - HID_USAGE_GAME_NEW_GAME = 0x2D, - HID_USAGE_GAME_SHOOT_BALL = 0x2E, - HID_USAGE_GAME_PLAYER = 0x2F, - HID_USAGE_GAME_GUN_BOLT = 0x30, - HID_USAGE_GAME_GUN_CLIP = 0x31, - HID_USAGE_GAME_GUN_SELECTOR = 0x32, - HID_USAGE_GAME_GUN_SINGLE_SHOT = 0x33, - HID_USAGE_GAME_GUN_BURST = 0x34, - HID_USAGE_GAME_GUN_AUTOMATIC = 0x35, - HID_USAGE_GAME_GUN_SAFETY = 0x36, - HID_USAGE_GAME_GAMEPAD_FIRE_JUMP = 0x37, - /* NO 39 */ - HID_USAGE_GAME_GAMEPAD_TRIGGER = 0x39 - /* 3A-FFFF RESERVED*/ -}; - -/// HID Usage Table: Consumer Page (0x0C) -/// Only contains controls that supported by Windows (whole list is too long) -enum -{ - // Generic Control - HID_USAGE_CONSUMER_CONTROL = 0x0001, - - // Power Control - HID_USAGE_CONSUMER_POWER = 0x0030, - HID_USAGE_CONSUMER_RESET = 0x0031, - HID_USAGE_CONSUMER_SLEEP = 0x0032, - - // Screen Brightness - HID_USAGE_CONSUMER_BRIGHTNESS_INCREMENT = 0x006F, - HID_USAGE_CONSUMER_BRIGHTNESS_DECREMENT = 0x0070, - - // These HID usages operate only on mobile systems (battery powered) and - // require Windows 8 (build 8302 or greater). - HID_USAGE_CONSUMER_WIRELESS_RADIO_CONTROLS = 0x000C, - HID_USAGE_CONSUMER_WIRELESS_RADIO_BUTTONS = 0x00C6, - HID_USAGE_CONSUMER_WIRELESS_RADIO_LED = 0x00C7, - HID_USAGE_CONSUMER_WIRELESS_RADIO_SLIDER_SWITCH = 0x00C8, - - // Media Control - HID_USAGE_CONSUMER_PLAY_PAUSE = 0x00CD, - HID_USAGE_CONSUMER_SCAN_NEXT = 0x00B5, - HID_USAGE_CONSUMER_SCAN_PREVIOUS = 0x00B6, - HID_USAGE_CONSUMER_STOP = 0x00B7, - HID_USAGE_CONSUMER_VOLUME = 0x00E0, - HID_USAGE_CONSUMER_MUTE = 0x00E2, - HID_USAGE_CONSUMER_BASS = 0x00E3, - HID_USAGE_CONSUMER_TREBLE = 0x00E4, - HID_USAGE_CONSUMER_BASS_BOOST = 0x00E5, - HID_USAGE_CONSUMER_VOLUME_INCREMENT = 0x00E9, - HID_USAGE_CONSUMER_VOLUME_DECREMENT = 0x00EA, - HID_USAGE_CONSUMER_BASS_INCREMENT = 0x0152, - HID_USAGE_CONSUMER_BASS_DECREMENT = 0x0153, - HID_USAGE_CONSUMER_TREBLE_INCREMENT = 0x0154, - HID_USAGE_CONSUMER_TREBLE_DECREMENT = 0x0155, - - // Application Launcher - HID_USAGE_CONSUMER_AL_CONSUMER_CONTROL_CONFIGURATION = 0x0183, - HID_USAGE_CONSUMER_AL_EMAIL_READER = 0x018A, - HID_USAGE_CONSUMER_AL_CALCULATOR = 0x0192, - HID_USAGE_CONSUMER_AL_LOCAL_BROWSER = 0x0194, - - // Browser/Explorer Specific - HID_USAGE_CONSUMER_AC_SEARCH = 0x0221, - HID_USAGE_CONSUMER_AC_HOME = 0x0223, - HID_USAGE_CONSUMER_AC_BACK = 0x0224, - HID_USAGE_CONSUMER_AC_FORWARD = 0x0225, - HID_USAGE_CONSUMER_AC_STOP = 0x0226, - HID_USAGE_CONSUMER_AC_REFRESH = 0x0227, - HID_USAGE_CONSUMER_AC_BOOKMARKS = 0x022A, - - // Mouse Horizontal scroll - HID_USAGE_CONSUMER_AC_PAN = 0x0238, -}; - -/*-------------------------------------------------------------------- - * ASCII to KEYCODE Conversion - * Expand to array of [128][2] (shift, keycode) - * - * Usage: example to convert input chr into keyboard report (modifier + keycode) - * - * uint8_t const conv_table[128][2] = { HID_ASCII_TO_KEYCODE }; - * - * uint8_t keycode[6] = { 0 }; - * uint8_t modifier = 0; - * - * if ( conv_table[chr][0] ) modifier = KEYBOARD_MODIFIER_LEFTSHIFT; - * keycode[0] = conv_table[chr][1]; - * tud_hid_keyboard_report(report_id, modifier, keycode); - * - *--------------------------------------------------------------------*/ -#define HID_ASCII_TO_KEYCODE \ - {0, 0 }, /* 0x00 Null */ \ - {0, 0 }, /* 0x01 */ \ - {0, 0 }, /* 0x02 */ \ - {0, 0 }, /* 0x03 */ \ - {0, 0 }, /* 0x04 */ \ - {0, 0 }, /* 0x05 */ \ - {0, 0 }, /* 0x06 */ \ - {0, 0 }, /* 0x07 */ \ - {0, HID_KEY_BACKSPACE }, /* 0x08 Backspace */ \ - {0, HID_KEY_TAB }, /* 0x09 Tab */ \ - {0, HID_KEY_ENTER }, /* 0x0A Line Feed */ \ - {0, 0 }, /* 0x0B */ \ - {0, 0 }, /* 0x0C */ \ - {0, HID_KEY_ENTER }, /* 0x0D CR */ \ - {0, 0 }, /* 0x0E */ \ - {0, 0 }, /* 0x0F */ \ - {0, 0 }, /* 0x10 */ \ - {0, 0 }, /* 0x11 */ \ - {0, 0 }, /* 0x12 */ \ - {0, 0 }, /* 0x13 */ \ - {0, 0 }, /* 0x14 */ \ - {0, 0 }, /* 0x15 */ \ - {0, 0 }, /* 0x16 */ \ - {0, 0 }, /* 0x17 */ \ - {0, 0 }, /* 0x18 */ \ - {0, 0 }, /* 0x19 */ \ - {0, 0 }, /* 0x1A */ \ - {0, HID_KEY_ESCAPE }, /* 0x1B Escape */ \ - {0, 0 }, /* 0x1C */ \ - {0, 0 }, /* 0x1D */ \ - {0, 0 }, /* 0x1E */ \ - {0, 0 }, /* 0x1F */ \ - \ - {0, HID_KEY_SPACE }, /* 0x20 */ \ - {1, HID_KEY_1 }, /* 0x21 ! */ \ - {1, HID_KEY_APOSTROPHE }, /* 0x22 " */ \ - {1, HID_KEY_3 }, /* 0x23 # */ \ - {1, HID_KEY_4 }, /* 0x24 $ */ \ - {1, HID_KEY_5 }, /* 0x25 % */ \ - {1, HID_KEY_7 }, /* 0x26 & */ \ - {0, HID_KEY_APOSTROPHE }, /* 0x27 ' */ \ - {1, HID_KEY_9 }, /* 0x28 ( */ \ - {1, HID_KEY_0 }, /* 0x29 ) */ \ - {1, HID_KEY_8 }, /* 0x2A * */ \ - {1, HID_KEY_EQUAL }, /* 0x2B + */ \ - {0, HID_KEY_COMMA }, /* 0x2C , */ \ - {0, HID_KEY_MINUS }, /* 0x2D - */ \ - {0, HID_KEY_PERIOD }, /* 0x2E . */ \ - {0, HID_KEY_SLASH }, /* 0x2F / */ \ - {0, HID_KEY_0 }, /* 0x30 0 */ \ - {0, HID_KEY_1 }, /* 0x31 1 */ \ - {0, HID_KEY_2 }, /* 0x32 2 */ \ - {0, HID_KEY_3 }, /* 0x33 3 */ \ - {0, HID_KEY_4 }, /* 0x34 4 */ \ - {0, HID_KEY_5 }, /* 0x35 5 */ \ - {0, HID_KEY_6 }, /* 0x36 6 */ \ - {0, HID_KEY_7 }, /* 0x37 7 */ \ - {0, HID_KEY_8 }, /* 0x38 8 */ \ - {0, HID_KEY_9 }, /* 0x39 9 */ \ - {1, HID_KEY_SEMICOLON }, /* 0x3A : */ \ - {0, HID_KEY_SEMICOLON }, /* 0x3B ; */ \ - {1, HID_KEY_COMMA }, /* 0x3C < */ \ - {0, HID_KEY_EQUAL }, /* 0x3D = */ \ - {1, HID_KEY_PERIOD }, /* 0x3E > */ \ - {1, HID_KEY_SLASH }, /* 0x3F ? */ \ - \ - {1, HID_KEY_2 }, /* 0x40 @ */ \ - {1, HID_KEY_A }, /* 0x41 A */ \ - {1, HID_KEY_B }, /* 0x42 B */ \ - {1, HID_KEY_C }, /* 0x43 C */ \ - {1, HID_KEY_D }, /* 0x44 D */ \ - {1, HID_KEY_E }, /* 0x45 E */ \ - {1, HID_KEY_F }, /* 0x46 F */ \ - {1, HID_KEY_G }, /* 0x47 G */ \ - {1, HID_KEY_H }, /* 0x48 H */ \ - {1, HID_KEY_I }, /* 0x49 I */ \ - {1, HID_KEY_J }, /* 0x4A J */ \ - {1, HID_KEY_K }, /* 0x4B K */ \ - {1, HID_KEY_L }, /* 0x4C L */ \ - {1, HID_KEY_M }, /* 0x4D M */ \ - {1, HID_KEY_N }, /* 0x4E N */ \ - {1, HID_KEY_O }, /* 0x4F O */ \ - {1, HID_KEY_P }, /* 0x50 P */ \ - {1, HID_KEY_Q }, /* 0x51 Q */ \ - {1, HID_KEY_R }, /* 0x52 R */ \ - {1, HID_KEY_S }, /* 0x53 S */ \ - {1, HID_KEY_T }, /* 0x55 T */ \ - {1, HID_KEY_U }, /* 0x55 U */ \ - {1, HID_KEY_V }, /* 0x56 V */ \ - {1, HID_KEY_W }, /* 0x57 W */ \ - {1, HID_KEY_X }, /* 0x58 X */ \ - {1, HID_KEY_Y }, /* 0x59 Y */ \ - {1, HID_KEY_Z }, /* 0x5A Z */ \ - {0, HID_KEY_BRACKET_LEFT }, /* 0x5B [ */ \ - {0, HID_KEY_BACKSLASH }, /* 0x5C '\' */ \ - {0, HID_KEY_BRACKET_RIGHT }, /* 0x5D ] */ \ - {1, HID_KEY_6 }, /* 0x5E ^ */ \ - {1, HID_KEY_MINUS }, /* 0x5F _ */ \ - \ - {0, HID_KEY_GRAVE }, /* 0x60 ` */ \ - {0, HID_KEY_A }, /* 0x61 a */ \ - {0, HID_KEY_B }, /* 0x62 b */ \ - {0, HID_KEY_C }, /* 0x63 c */ \ - {0, HID_KEY_D }, /* 0x66 d */ \ - {0, HID_KEY_E }, /* 0x65 e */ \ - {0, HID_KEY_F }, /* 0x66 f */ \ - {0, HID_KEY_G }, /* 0x67 g */ \ - {0, HID_KEY_H }, /* 0x68 h */ \ - {0, HID_KEY_I }, /* 0x69 i */ \ - {0, HID_KEY_J }, /* 0x6A j */ \ - {0, HID_KEY_K }, /* 0x6B k */ \ - {0, HID_KEY_L }, /* 0x6C l */ \ - {0, HID_KEY_M }, /* 0x6D m */ \ - {0, HID_KEY_N }, /* 0x6E n */ \ - {0, HID_KEY_O }, /* 0x6F o */ \ - {0, HID_KEY_P }, /* 0x70 p */ \ - {0, HID_KEY_Q }, /* 0x71 q */ \ - {0, HID_KEY_R }, /* 0x72 r */ \ - {0, HID_KEY_S }, /* 0x73 s */ \ - {0, HID_KEY_T }, /* 0x75 t */ \ - {0, HID_KEY_U }, /* 0x75 u */ \ - {0, HID_KEY_V }, /* 0x76 v */ \ - {0, HID_KEY_W }, /* 0x77 w */ \ - {0, HID_KEY_X }, /* 0x78 x */ \ - {0, HID_KEY_Y }, /* 0x79 y */ \ - {0, HID_KEY_Z }, /* 0x7A z */ \ - {1, HID_KEY_BRACKET_LEFT }, /* 0x7B { */ \ - {1, HID_KEY_BACKSLASH }, /* 0x7C | */ \ - {1, HID_KEY_BRACKET_RIGHT }, /* 0x7D } */ \ - {1, HID_KEY_GRAVE }, /* 0x7E ~ */ \ - {0, HID_KEY_DELETE } /* 0x7F Delete */ \ - -/*-------------------------------------------------------------------- - * KEYCODE to Ascii Conversion - * Expand to array of [128][2] (ascii without shift, ascii with shift) - * - * Usage: example to convert ascii from keycode (key) and shift modifier (shift). - * Here we assume key < 128 ( printable ) - * - * uint8_t const conv_table[128][2] = { HID_KEYCODE_TO_ASCII }; - * char ch = shift ? conv_table[chr][1] : conv_table[chr][0]; - * - *--------------------------------------------------------------------*/ -#define HID_KEYCODE_TO_ASCII \ - {0 , 0 }, /* 0x00 */ \ - {0 , 0 }, /* 0x01 */ \ - {0 , 0 }, /* 0x02 */ \ - {0 , 0 }, /* 0x03 */ \ - {'a' , 'A' }, /* 0x04 */ \ - {'b' , 'B' }, /* 0x05 */ \ - {'c' , 'C' }, /* 0x06 */ \ - {'d' , 'D' }, /* 0x07 */ \ - {'e' , 'E' }, /* 0x08 */ \ - {'f' , 'F' }, /* 0x09 */ \ - {'g' , 'G' }, /* 0x0a */ \ - {'h' , 'H' }, /* 0x0b */ \ - {'i' , 'I' }, /* 0x0c */ \ - {'j' , 'J' }, /* 0x0d */ \ - {'k' , 'K' }, /* 0x0e */ \ - {'l' , 'L' }, /* 0x0f */ \ - {'m' , 'M' }, /* 0x10 */ \ - {'n' , 'N' }, /* 0x11 */ \ - {'o' , 'O' }, /* 0x12 */ \ - {'p' , 'P' }, /* 0x13 */ \ - {'q' , 'Q' }, /* 0x14 */ \ - {'r' , 'R' }, /* 0x15 */ \ - {'s' , 'S' }, /* 0x16 */ \ - {'t' , 'T' }, /* 0x17 */ \ - {'u' , 'U' }, /* 0x18 */ \ - {'v' , 'V' }, /* 0x19 */ \ - {'w' , 'W' }, /* 0x1a */ \ - {'x' , 'X' }, /* 0x1b */ \ - {'y' , 'Y' }, /* 0x1c */ \ - {'z' , 'Z' }, /* 0x1d */ \ - {'1' , '!' }, /* 0x1e */ \ - {'2' , '@' }, /* 0x1f */ \ - {'3' , '#' }, /* 0x20 */ \ - {'4' , '$' }, /* 0x21 */ \ - {'5' , '%' }, /* 0x22 */ \ - {'6' , '^' }, /* 0x23 */ \ - {'7' , '&' }, /* 0x24 */ \ - {'8' , '*' }, /* 0x25 */ \ - {'9' , '(' }, /* 0x26 */ \ - {'0' , ')' }, /* 0x27 */ \ - {'\r' , '\r' }, /* 0x28 */ \ - {'\x1b', '\x1b' }, /* 0x29 */ \ - {'\b' , '\b' }, /* 0x2a */ \ - {'\t' , '\t' }, /* 0x2b */ \ - {' ' , ' ' }, /* 0x2c */ \ - {'-' , '_' }, /* 0x2d */ \ - {'=' , '+' }, /* 0x2e */ \ - {'[' , '{' }, /* 0x2f */ \ - {']' , '}' }, /* 0x30 */ \ - {'\\' , '|' }, /* 0x31 */ \ - {'#' , '~' }, /* 0x32 */ \ - {';' , ':' }, /* 0x33 */ \ - {'\'' , '\"' }, /* 0x34 */ \ - {'`' , '~' }, /* 0x35 */ \ - {',' , '<' }, /* 0x36 */ \ - {'.' , '>' }, /* 0x37 */ \ - {'/' , '?' }, /* 0x38 */ \ - \ - {0 , 0 }, /* 0x39 */ \ - {0 , 0 }, /* 0x3a */ \ - {0 , 0 }, /* 0x3b */ \ - {0 , 0 }, /* 0x3c */ \ - {0 , 0 }, /* 0x3d */ \ - {0 , 0 }, /* 0x3e */ \ - {0 , 0 }, /* 0x3f */ \ - {0 , 0 }, /* 0x40 */ \ - {0 , 0 }, /* 0x41 */ \ - {0 , 0 }, /* 0x42 */ \ - {0 , 0 }, /* 0x43 */ \ - {0 , 0 }, /* 0x44 */ \ - {0 , 0 }, /* 0x45 */ \ - {0 , 0 }, /* 0x46 */ \ - {0 , 0 }, /* 0x47 */ \ - {0 , 0 }, /* 0x48 */ \ - {0 , 0 }, /* 0x49 */ \ - {0 , 0 }, /* 0x4a */ \ - {0 , 0 }, /* 0x4b */ \ - {0 , 0 }, /* 0x4c */ \ - {0 , 0 }, /* 0x4d */ \ - {0 , 0 }, /* 0x4e */ \ - {0 , 0 }, /* 0x4f */ \ - {0 , 0 }, /* 0x50 */ \ - {0 , 0 }, /* 0x51 */ \ - {0 , 0 }, /* 0x52 */ \ - {0 , 0 }, /* 0x53 */ \ - \ - {'/' , '/' }, /* 0x54 */ \ - {'*' , '*' }, /* 0x55 */ \ - {'-' , '-' }, /* 0x56 */ \ - {'+' , '+' }, /* 0x57 */ \ - {'\r' , '\r' }, /* 0x58 */ \ - {'1' , 0 }, /* 0x59 */ \ - {'2' , 0 }, /* 0x5a */ \ - {'3' , 0 }, /* 0x5b */ \ - {'4' , 0 }, /* 0x5c */ \ - {'5' , '5' }, /* 0x5d */ \ - {'6' , 0 }, /* 0x5e */ \ - {'7' , 0 }, /* 0x5f */ \ - {'8' , 0 }, /* 0x60 */ \ - {'9' , 0 }, /* 0x61 */ \ - {'0' , 0 }, /* 0x62 */ \ - {'.' , 0 }, /* 0x63 */ \ - {0 , 0 }, /* 0x64 */ \ - {0 , 0 }, /* 0x65 */ \ - {0 , 0 }, /* 0x66 */ \ - {'=' , '=' }, /* 0x67 */ \ - - -#ifdef __cplusplus - } -#endif - -#endif /* _TUSB_HID_H__ */ - -/// @} diff --git a/src/main.cpp b/src/main.cpp index 0eff99f..d4dbb09 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -17,10 +17,15 @@ Adafruit_NeoPixel pixel; bool enableMouseAndKeyboard = 0; -uint8_t JS_COUNT; +uint8_t DeviceCountJoystick = 0; +uint8_t DeviceCountButtons = 0; +uint8_t DeviceCountHat = 0; +uint8_t DeviceCount = 0; int COLLECTIONS = MAX_COLLECTIONS; -int AXIS_COUNT = 5; +int AXIS_COUNT = 8; +int BUTTON_COUNT = 32; +int HAT_COUNT= 2; hid_Joystick_report_t* jr = nullptr; hid_Joystick_report_t* jr_old = nullptr; @@ -31,17 +36,17 @@ uint16_t _hidKBMReportDescSize = 0; // Report ID enum RID{ - RID_JOYSTICK1 = 1, - RID_JOYSTICK2, + RID_JOYSTICK1 = 1, + RID_JOYSTICK2, }; //DATA TYPE enum { - Axis = 1, - Buttons, - Hat, - Padding, + Axis = 1, + Buttons, + Hat, + Padding, }; // HID report descriptor using TinyUSB's template @@ -51,7 +56,6 @@ uint8_t const desc_hid_report[] = { }; -//Adafruit_USBD_HID hid(desc_hid_report, sizeof(desc_hid_report),HID_ITF_PROTOCOL_NONE,2,true); Adafruit_USBD_HID hid_joystick; Adafruit_USBD_HID hid_kbm; @@ -65,290 +69,317 @@ volatile Command* command; template T map_clamped(T x, T in_min, T in_max, T out_min, T out_max) { - if (x > in_max) - x = in_max; - if (x < in_min) - x = in_min; - return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min; + if (x > in_max) + x = in_max; + if (x < in_min) + x = in_min; + return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min; } uint32_t rainbow(uint16_t _hue, uint8_t saturation, uint8_t brightness, bool gammify) { - uint32_t color = pixel.ColorHSV(_hue, saturation, brightness); + uint32_t color = pixel.ColorHSV(_hue, saturation, brightness); if (gammify) color = pixel.gamma32(color); - return color; + return color; } /* - ============= - Callbacks - ============= + ============= + Callbacks + ============= */ // Invoked when received GET_REPORT control request // Application must fill buffer report's content and return its length. // Return zero will cause the stack to STALL request uint16_t get_report_callback (uint8_t report_id, hid_report_type_t report_type, uint8_t* buffer, uint16_t reqlen) { - switch (report_type) - { - case (hid_report_type_t)HID_REPORT_TYPE_INVALID: - case (hid_report_type_t)HID_REPORT_TYPE_OUTPUT: - break; - - case (hid_report_type_t)HID_REPORT_TYPE_INPUT: - case (hid_report_type_t)HID_REPORT_TYPE_FEATURE: - { - Serial.print("get_report type: "); - Serial.println((int)report_type); - Serial.print("get_report id: "); - Serial.println((int)report_id); - - //for (int i = 0; i( std::ceil( static_cast(AXIS_COUNT)/8 ) ); - - if (_hidKBMReportDesc == nullptr) { - _hidKBMReportDesc = (uint8_t*)malloc(150); - memset(_hidKBMReportDesc, 0, 150); - } - if (_hidJoystickReportDesc == nullptr) { - _hidJoystickReportDesc = (uint8_t*)malloc(MAX_HID_REPORTDESC_SIZE); - memset(_hidJoystickReportDesc, 0, MAX_HID_REPORTDESC_SIZE); - } - if ( i2cBuff == nullptr ) { - i2cBuff = (uint8_t*)malloc(i2cBuffSize); - command = (struct Command*)i2cBuff; - } - - - jr = new hid_Joystick_report_t[JS_COUNT]; - jr_old = new hid_Joystick_report_t[JS_COUNT]; - memset(jr, 0, sizeof(jr)); - memset(jr_old, 0, sizeof(jr_old)); - - for (int i = 0; i 0) { + _hidJoystickReportDescSize = AddAxis(_hidJoystickReportDesc, _hidJoystickReportDescSize, HID_USAGE_DESKTOP_X, AXIS_COUNT, 11); + AXIS_COUNT -= 8; + if (AXIS_COUNT < 0) {AXIS_COUNT = 0;} + } + if (BUTTON_COUNT > 0) { + _hidJoystickReportDescSize = AddButtons(_hidJoystickReportDesc, _hidJoystickReportDescSize, BUTTON_COUNT); + BUTTON_COUNT -= 32; + if (BUTTON_COUNT < 0) {BUTTON_COUNT = 0;} + } + if (HAT_COUNT > 0) { + _hidJoystickReportDescSize = AddHats(_hidJoystickReportDesc, _hidJoystickReportDescSize, HAT_COUNT); + HAT_COUNT-= 4; + if (HAT_COUNT < 0) {HAT_COUNT = 0;} + } + _hidJoystickReportDescSize = AddCollectionEnd(_hidJoystickReportDesc, _hidJoystickReportDescSize); + } + + + jr = new hid_Joystick_report_t[DeviceCount]; + jr_old = new hid_Joystick_report_t[DeviceCount]; + memset(jr, 0, sizeof(jr)); + memset(jr_old, 0, sizeof(jr_old)); + + //if (enable_keyboard) { + // // Jank but works... couldnt find another way that worked + // uint8_t const desc_hid_report1[] = {TUD_HID_REPORT_DESC_KEYBOARD(VA_HID_REPORT_ID(JS_COUNT+1))}; + // memcpy(_hidKBMReportDesc+_hidKBMReportDescSize, desc_hid_report1, sizeof(desc_hid_report1)); + // //_hidKBMReportDesc[_hidKBMReportDescSize+7] = 1; + // _hidKBMReportDescSize += sizeof(desc_hid_report1); + //} + + //if (enable_mouse) { + // // Jank but works... couldnt find another way that worked + // uint8_t const desc_hid_report2[] = {TUD_HID_REPORT_DESC_MOUSE(VA_HID_REPORT_ID(JS_COUNT+1))}; + // memcpy(_hidKBMReportDesc+_hidKBMReportDescSize, desc_hid_report2, sizeof(desc_hid_report2)); + // //_hidKBMReportDesc[_hidKBMReportDescSize+7] = 2; + // _hidKBMReportDescSize += sizeof(desc_hid_report2); + //} #if defined(ARDUINO_ARCH_MBED) && defined(ARDUINO_ARCH_RP2040) - // Manual begin() is required on core without built-in support for TinyUSB such as - // - mbed rp2040 - TinyUSB_Device_Init(0); + // Manual begin() is required on core without built-in support for TinyUSB such as + // - mbed rp2040 + TinyUSB_Device_Init(0); #endif - SerialTinyUSB.begin(115200); - TinyUSBDevice.setID(VID,PID); - TinyUSBDevice.setManufacturerDescriptor("Raspberry Pi"); - TinyUSBDevice.setProductDescriptor("RP2040-HOTAS"); - - // start the USB device - USBDevice.attach(); - - if (JS_COUNT > 0) { - hid_joystick.setPollInterval(2); - hid_joystick.setBootProtocol(HID_ITF_PROTOCOL_NONE); - //hid_joystick.setStringDescriptor("TinyUSB Joystick"); - hid_joystick.setReportDescriptor(_hidJoystickReportDesc, _hidJoystickReportDescSize); - hid_joystick.setReportCallback(get_report_callback, set_report_callback); - hid_joystick.begin(); - } - if (enableMouseAndKeyboard) { - hid_kbm.setStringDescriptor("TinyUSB Keyboard/Mouse"); - hid_kbm.setReportDescriptor(desc_hid_report, sizeof(desc_hid_report)); - hid_kbm.begin(); - } - // wait until device mounted - //while (!TinyUSBDevice.mounted()){ delay(1); } - //delay(100); - - #if defined(ARDUINO_RASPBERRY_PI_PICO) - pinMode(23,OUTPUT); - digitalWrite(23,HIGH); // this forces the switch mode power supply into pwm mode (less efficient but also less noise) + SerialTinyUSB.begin(115200); + TinyUSBDevice.setID(VID,PID); + TinyUSBDevice.setManufacturerDescriptor("Raspberry Pi"); + TinyUSBDevice.setProductDescriptor("RP2040-HOTAS"); + + // start the USB device + USBDevice.attach(); + + if (DeviceCount > 0) { + hid_joystick.setPollInterval(2); + hid_joystick.setBootProtocol(HID_ITF_PROTOCOL_NONE); + //hid_joystick.setStringDescriptor("TinyUSB Joystick"); + hid_joystick.setReportDescriptor(_hidJoystickReportDesc, _hidJoystickReportDescSize); + hid_joystick.setReportCallback(get_report_callback, set_report_callback); + hid_joystick.begin(); + } + if (enableMouseAndKeyboard) { + hid_kbm.setStringDescriptor("TinyUSB Keyboard/Mouse"); + hid_kbm.setReportDescriptor(desc_hid_report, sizeof(desc_hid_report)); + hid_kbm.begin(); + } + // wait until device mounted + //while (!TinyUSBDevice.mounted()){ delay(1); } + //delay(100); + + #if defined(ARDUINO_RASPBERRY_PI_PICO) + pinMode(23,OUTPUT); + digitalWrite(23,HIGH); // this forces the switch mode power supply into pwm mode (less efficient but also less noise) #endif - pinMode(A0,INPUT); - pinMode(A1,INPUT); - pinMode(A2,INPUT); - pinMode(D0, INPUT_PULLUP); - pinMode(D1, INPUT_PULLUP); - Wire.setTimeout(100); - Wire.setSDA(D0); - Wire.setSCL(D1); - Wire.setClock(100000); - Wire.begin(); - - analogReadResolution(11); + pinMode(A0,INPUT); + pinMode(A1,INPUT); + pinMode(A2,INPUT); + pinMode(D0, INPUT_PULLUP); + pinMode(D1, INPUT_PULLUP); + Wire.setTimeout(100); + Wire.setSDA(D0); + Wire.setSCL(D1); + Wire.setClock(100000); + Wire.begin(); + + analogReadResolution(11); } @@ -366,126 +397,127 @@ int report = 0; static char buff[100]; /* - ======== - Loop - ======== + ======== + Loop + ======== */ void loop() { - if(TinyUSBDevice.ready()) { - if (micros() - lastTime > 100000) { - lastTime = micros(); - LED += speed; - if (LED > 31 || LED < 0) - speed = -speed; - if (LED > 31) - LED = 31; - if (LED < 0) - LED = 0; - } - - //led.R = 0; led.G = LED; led.B = 0; - - } else if (TinyUSBDevice.suspended()) - { - //led.r = 0; led.g = 0; led.b = 0; - LED = 0; - } else { - LED = 1; - //led.r = LED; led.g = 0; led.b = 0; - } - hue+=25; - if (hue >= UINT16_MAX) - hue = 0; - //if(!TinyUSBDevice.ready() ) { return; } - //if (millis() - 10 > timed2) { - - for (int p = 0; p < 3; p++) { - uint16_t _hue = hue + (p * 2 * 65536) / 3; - uint32_t _pixel = rainbow(_hue, 255, 255*map_clamped(31,0,31,0,1), true); - auto buffsize = sizeof(command->command_type+command->id); - buffsize += sizeof(_pixel); - command->command_type = SET_LED; - command->id = p; - command->data = (uint32_t*)_pixel; - Wire.beginTransmission(0x21); - Wire.write((byte *)i2cBuff, buffsize); - Wire.endTransmission(); - //delay(100); - } - //} - - Serial.println("Reqiest LED 0 data\n\r"); - command->command_type = GET_LED; - command->id = 0; - size_t size = sizeof(command->command_type+command->id); // only sending command and id (led) - Wire.beginTransmission(0x21); - Wire.write((byte*)i2cBuff, size); - Wire.endTransmission(); - size += sizeof(uint32_t); //add RGB(W) value from WS2812 to the request - - // Read from the slave and print out - Wire.requestFrom(0x21, size); - i2cBuffSizeFree = i2cBuffSize - Wire.readBytes((byte*)i2cBuff, size); - led.raw = (uint32_t)command->data; - Serial.print("Buff size used: "); - Serial.println(i2cBuffSize - i2cBuffSizeFree); - Serial.print("LED W: "); - Serial.println(led.W); - Serial.print("LED R: "); - Serial.println(led.R); - Serial.print("LED G: "); - Serial.println(led.G); - Serial.print("LED B: "); - Serial.println(led.B); - // Wake up host if we are in suspend mode - // and REMOTE_WAKEUP feature is enabled by host - //if (TinyUSBDevice.suspended() && BOOTSEL) - //{ - // TinyUSBDevice.remoteWakeup(); - //} - - - - - jr[0].rx = jr[1].rx = map_clamped(analogRead(A0), 200, 1800, 2047, 0); - if (micros() - 2000 > update_cooldown) { - update_cooldown = micros(); - if ( jr[report].x != jr_old[report].x || - jr[report].y != jr_old[report].y || - jr[report].z != jr_old[report].z || - jr[report].rx != jr_old[report].rx || - jr[report].ry != jr_old[report].ry || - jr[report].rz != jr_old[report].rz || - jr[report].slider != jr_old[report].slider || - jr[report].dial != jr_old[report].dial || - jr[report].hat1 != jr_old[report].hat1 || - jr[report].hat2 != jr_old[report].hat2 || - jr[report].buttons != jr_old[report].buttons) { - if( TinyUSBDevice.ready()) { - hid_joystick.sendReport(report+1, &jr[report], sizeof(jr[report])); - jr_old[report] = jr[report]; - } - if (TinyUSBDevice.suspended()) { - TinyUSBDevice.remoteWakeup(); - } - } - report++; - if (report > JS_COUNT) - report = 0; - } - - - - //if (millis() - timed1 > 1000) - //{ - // timed1 = millis(); - // i2cScanner(); - //} + if(TinyUSBDevice.ready()) { + if (micros() - lastTime > 100000) { + lastTime = micros(); + LED += speed; + if (LED > 31 || LED < 0) + speed = -speed; + if (LED > 31) + LED = 31; + if (LED < 0) + LED = 0; + } + + //led.R = 0; led.G = LED; led.B = 0; + + } else if (TinyUSBDevice.suspended()) + { + //led.r = 0; led.g = 0; led.b = 0; + LED = 0; + } else { + LED = 1; + //led.r = LED; led.g = 0; led.b = 0; + } + hue+=25; + if (hue >= UINT16_MAX) + hue = 0; + //if(!TinyUSBDevice.ready() ) { return; } + //if (millis() - 10 > timed2) { + + for (int p = 0; p < 3; p++) { + uint16_t _hue = hue + (p * 2 * 65536) / 3; + uint32_t _pixel = rainbow(_hue, 255, 255*map_clamped(LED,0,31,0,1), true); + auto buffsize = sizeof(command->command_type+command->id); + buffsize += sizeof(_pixel); + command->command_type = SET_LED; + command->id = p; + command->data = (uint32_t*)_pixel; + Wire.beginTransmission(0x21); + Wire.write((byte *)i2cBuff, buffsize); + Wire.endTransmission(); + //delay(100); + } + //} + + //Serial.println("Reqiest LED 0 data\n\r"); + //command->command_type = GET_LED; + //command->id = 0; + //size_t size = sizeof(command->command_type+command->id); // only sending command and id (led) + //Wire.beginTransmission(0x21); + //Wire.write((byte*)i2cBuff, size); + //Wire.endTransmission(); + //size += sizeof(uint32_t); //add RGB(W) value from WS2812 to the request + //// Read from the slave and print out + //Wire.requestFrom(0x21, size); + //i2cBuffSizeFree = i2cBuffSize - Wire.readBytes((byte*)i2cBuff, size); + //led.raw = (uint32_t)command->data; + //Serial.print("Buff size used: "); + //Serial.println(i2cBuffSize - i2cBuffSizeFree); + //Serial.print("LED W: "); + //Serial.println(led.W); + //Serial.print("LED R: "); + //Serial.println(led.R); + //Serial.print("LED G: "); + //Serial.println(led.G); + //Serial.print("LED B: "); + //Serial.println(led.B); + // Wake up host if we are in suspend mode + // and REMOTE_WAKEUP feature is enabled by host + //if (TinyUSBDevice.suspended() && BOOTSEL) + //{ + // TinyUSBDevice.remoteWakeup(); + //} + + + + + jr[0].rx = jr[1].rx = map_clamped(analogRead(A0), 200, 1800, 2047, 0); + if (micros() - 2000 > update_cooldown) { + update_cooldown = micros(); + if ( jr[report].x != jr_old[report].x || + jr[report].y != jr_old[report].y || + jr[report].z != jr_old[report].z || + jr[report].rx != jr_old[report].rx || + jr[report].ry != jr_old[report].ry || + jr[report].rz != jr_old[report].rz || + jr[report].slider != jr_old[report].slider || + jr[report].dial != jr_old[report].dial || + jr[report].hat1 != jr_old[report].hat1 || + jr[report].hat2 != jr_old[report].hat2 || + jr[report].buttons != jr_old[report].buttons) { + if( TinyUSBDevice.ready()) { + hid_joystick.sendReport(report+1, &jr[report], sizeof(jr[report])); + jr_old[report] = jr[report]; + } + if (TinyUSBDevice.suspended()) { + TinyUSBDevice.remoteWakeup(); + } + } + report++; + if (report > DeviceCountJoystick) + report = 0; + } + + Wire.clearWriteError(); + + + //if (millis() - timed1 > 1000) + //{ + // timed1 = millis(); + // i2cScanner(); + //} } +// this is here since the joystick still works and doesnt need to be replaced (it will be gutted after throttle is properly done) #define X52_BUSY_WAIT 0 #define X52_PRO_IMPROVED_JOYSTICK_CLIENT_DESYNC_DETECTION 1 @@ -503,155 +535,138 @@ void serial_log_joystick_state(const x52::pro::JoystickState& state); void setup1() { - joystick_client.Setup(); + joystick_client.Setup(); #if MAX_UPDATES_PER_SECOND - static x52::util::RateLimiter rate_limiter; + static x52::util::RateLimiter rate_limiter; #endif } void loop1() { - // Calling PrepareForPoll is optional (this firmware works without it) - // but it eliminates almost all jitter from the timing of the updates. - // With PrepareForPoll we ask the joystick to prepare for the next - // update so it can serve our PollJoystickState call immediately - // after the delay introduced by the rate limiter. - // Without PrepareForPoll it can take up to 1500ms for the joystick - // to respond to our PollJoystickState call. - joystick_client.PrepareForPoll(); + // Calling PrepareForPoll is optional (this firmware works without it) + // but it eliminates almost all jitter from the timing of the updates. + // With PrepareForPoll we ask the joystick to prepare for the next + // update so it can serve our PollJoystickState call immediately + // after the delay introduced by the rate limiter. + // Without PrepareForPoll it can take up to 1500ms for the joystick + // to respond to our PollJoystickState call. + joystick_client.PrepareForPoll(); #if MAX_UPDATES_PER_SECOND - static x52::util::RateLimiter rate_limiter; - unsigned long d = rate_limiter.MicrosTillNextUpdate(); - if (d == 0) { + static x52::util::RateLimiter rate_limiter; + unsigned long d = rate_limiter.MicrosTillNextUpdate(); + if (d == 0) { #endif - // Query the state of the X52 Pro joystick via the PS/2 connection and send it to - // the PC as the state of the USB joystick emulated by the Arduino-compatible board. - x52::pro::JoystickConfig cfg; - x52::pro::JoystickState state; - cfg.led_brightness = LED; - - //if(TinyUSBDevice.ready()) { - // if (cfg.led_brightness != x52::pro::JoystickConfig::MAX_LED_BRIGHTNESS / 2) { - //cfg.led_brightness = x52::pro::JoystickConfig::MAX_LED_BRIGHTNESS / 2; - // } - //} else if (TinyUSBDevice.mounted()) - //{ - // if (cfg.led_brightness != 0) { - // cfg.led_brightness = 0; - // } - //} else { - // if (cfg.led_brightness != 0) { - // cfg.led_brightness = 0; - // } - //} - - - // TODO: set other JoystickConfig values if you want - - auto timeout_micros = joystick_client.PollJoystickState(state, cfg); - if (timeout_micros) { - X52DebugPrintln("PollJoystickState failed"); - delayMicroseconds(timeout_micros); - return; - } - bool empty = false; - - jr[0].x = map_clamped(state.x, 0,1023,0,2046); - jr[0].y = map_clamped(state.y, 0,1023,0,2046); - jr[0].z = map_clamped(state.z, 0,1023,0,2046); - - bool p2u = bool(state.pov_2 & x52::Up); - bool p2d = bool(state.pov_2 & x52::Down); - bool p2l = bool(state.pov_2 & x52::Left); - bool p2r = bool(state.pov_2 & x52::Right); - - bool M1 = 0; - bool M2 = 0; - bool M3 = 0; + // Query the state of the X52 Pro joystick via the PS/2 connection and send it to + // the PC as the state of the USB joystick emulated by the Arduino-compatible board. + x52::pro::JoystickConfig cfg; + x52::pro::JoystickState state; + cfg.led_brightness = LED; + + + auto timeout_micros = joystick_client.PollJoystickState(state, cfg); + if (timeout_micros) { + X52DebugPrintln("PollJoystickState failed"); + delayMicroseconds(timeout_micros); + return; + } + bool empty = false; + + jr[0].x = map_clamped(state.x, 0,1023,0,2046); + jr[0].y = map_clamped(state.y, 0,1023,0,2046); + jr[0].z = map_clamped(state.z, 0,1023,0,2046); + + bool p2u = bool(state.pov_2 & x52::Up); + bool p2d = bool(state.pov_2 & x52::Down); + bool p2l = bool(state.pov_2 & x52::Left); + bool p2r = bool(state.pov_2 & x52::Right); + + bool M1 = 0; + bool M2 = 0; + bool M3 = 0; switch (state.mode) { - case x52::ModeUndefined: - M1 = 0; - M2 = 0; - M3 = 0; - break; - case x52::Mode1: - M1 = 1; - M2 = 0; - M3 = 0; - break; - case x52::Mode2: - M1 = 0; - M2 = 1; - M3 = 0; - break; - case x52::Mode3: - M1 = 0; - M2 = 0; - M3 = 1; - break; - } + case x52::ModeUndefined: + M1 = 0; + M2 = 0; + M3 = 0; + break; + case x52::Mode1: + M1 = 1; + M2 = 0; + M3 = 0; + break; + case x52::Mode2: + M1 = 0; + M2 = 1; + M3 = 0; + break; + case x52::Mode3: + M1 = 0; + M2 = 0; + M3 = 1; + break; + } switch (state.pov_1) { - case 0b0001: jr[0].hat1 = 0b0011; break; - case 0b0011: jr[0].hat1 = 0b0100; break; - case 0b0010: jr[0].hat1 = 0b0101; break; - case 0b0110: jr[0].hat1 = 0b0110; break; - case 0b0100: jr[0].hat1 = 0b0111; break; - case 0b1100: jr[0].hat1 = 0b1000; break; - case 0b1000: jr[0].hat1 = 0b0001; break; - case 0b1001: jr[0].hat1 = 0b0010; break; - default: jr[0].hat1 = 0b0000; break; + case 0b0001: jr[0].hat1 = 0b0011; break; + case 0b0011: jr[0].hat1 = 0b0100; break; + case 0b0010: jr[0].hat1 = 0b0101; break; + case 0b0110: jr[0].hat1 = 0b0110; break; + case 0b0100: jr[0].hat1 = 0b0111; break; + case 0b1100: jr[0].hat1 = 0b1000; break; + case 0b1000: jr[0].hat1 = 0b0001; break; + case 0b1001: jr[0].hat1 = 0b0010; break; + default: jr[0].hat1 = 0b0000; break; } switch (state.pov_2) { - case 0b0001: jr[0].hat2 = 0b0011; break; - case 0b0011: jr[0].hat2 = 0b0100; break; - case 0b0010: jr[0].hat2 = 0b0101; break; - case 0b0110: jr[0].hat2 = 0b0110; break; - case 0b0100: jr[0].hat2 = 0b0111; break; - case 0b1100: jr[0].hat2 = 0b1000; break; - case 0b1000: jr[0].hat2 = 0b0001; break; - case 0b1001: jr[0].hat2 = 0b0010; break; - default: jr[0].hat2 = 0b0000; break; + case 0b0001: jr[0].hat2 = 0b0011; break; + case 0b0011: jr[0].hat2 = 0b0100; break; + case 0b0010: jr[0].hat2 = 0b0101; break; + case 0b0110: jr[0].hat2 = 0b0110; break; + case 0b0100: jr[0].hat2 = 0b0111; break; + case 0b1100: jr[0].hat2 = 0b1000; break; + case 0b1000: jr[0].hat2 = 0b0001; break; + case 0b1001: jr[0].hat2 = 0b0010; break; + default: jr[0].hat2 = 0b0000; break; } - bitWrite(jr[0].buttons, 0, state.trigger_stage_1); - bitWrite(jr[0].buttons, 1, state.button_fire); - bitWrite(jr[0].buttons, 2, state.button_a); - bitWrite(jr[0].buttons, 3, state.button_b); - bitWrite(jr[0].buttons, 4, state.button_c); - bitWrite(jr[0].buttons, 5, state.pinkie_switch); - bitWrite(jr[0].buttons, 6, empty); - bitWrite(jr[0].buttons, 7, empty); - bitWrite(jr[0].buttons, 8, state.button_t1); - bitWrite(jr[0].buttons, 9, state.button_t2); - bitWrite(jr[0].buttons, 10, state.button_t3); - bitWrite(jr[0].buttons, 11, state.button_t4); - bitWrite(jr[0].buttons, 12, state.button_t5); - bitWrite(jr[0].buttons, 13, state.button_t6); - bitWrite(jr[0].buttons, 14, state.trigger_stage_2); - bitWrite(jr[0].buttons, 15, empty); - bitWrite(jr[0].buttons, 16, empty); - bitWrite(jr[0].buttons, 17, empty); - bitWrite(jr[0].buttons, 18, empty); - bitWrite(jr[0].buttons, 19, p2u); - bitWrite(jr[0].buttons, 20, p2r); - bitWrite(jr[0].buttons, 21, p2d); - bitWrite(jr[0].buttons, 22, p2l); - bitWrite(jr[0].buttons, 23, empty); - bitWrite(jr[0].buttons, 24, empty); - bitWrite(jr[0].buttons, 25, empty); - bitWrite(jr[0].buttons, 26, empty); - bitWrite(jr[0].buttons, 27, M1); - bitWrite(jr[0].buttons, 28, M2); - bitWrite(jr[0].buttons, 29, M3); - bitWrite(jr[0].buttons, 30, empty); - bitWrite(jr[0].buttons, 31, empty); + bitWrite(jr[0].buttons, 0, state.trigger_stage_1); + bitWrite(jr[0].buttons, 1, state.button_fire); + bitWrite(jr[0].buttons, 2, state.button_a); + bitWrite(jr[0].buttons, 3, state.button_b); + bitWrite(jr[0].buttons, 4, state.button_c); + bitWrite(jr[0].buttons, 5, state.pinkie_switch); + bitWrite(jr[0].buttons, 6, empty); + bitWrite(jr[0].buttons, 7, empty); + bitWrite(jr[0].buttons, 8, state.button_t1); + bitWrite(jr[0].buttons, 9, state.button_t2); + bitWrite(jr[0].buttons, 10, state.button_t3); + bitWrite(jr[0].buttons, 11, state.button_t4); + bitWrite(jr[0].buttons, 12, state.button_t5); + bitWrite(jr[0].buttons, 13, state.button_t6); + bitWrite(jr[0].buttons, 14, state.trigger_stage_2); + bitWrite(jr[0].buttons, 15, empty); + bitWrite(jr[0].buttons, 16, empty); + bitWrite(jr[0].buttons, 17, empty); + bitWrite(jr[0].buttons, 18, empty); + bitWrite(jr[0].buttons, 19, p2u); + bitWrite(jr[0].buttons, 20, p2r); + bitWrite(jr[0].buttons, 21, p2d); + bitWrite(jr[0].buttons, 22, p2l); + bitWrite(jr[0].buttons, 23, empty); + bitWrite(jr[0].buttons, 24, empty); + bitWrite(jr[0].buttons, 25, empty); + bitWrite(jr[0].buttons, 26, empty); + bitWrite(jr[0].buttons, 27, M1); + bitWrite(jr[0].buttons, 28, M2); + bitWrite(jr[0].buttons, 29, M3); + bitWrite(jr[0].buttons, 30, empty); + bitWrite(jr[0].buttons, 31, empty); #if MAX_UPDATES_PER_SECOND - } + } #endif }