-
-
Save houmei/2ad9f7a713f46149e72f to your computer and use it in GitHub Desktop.
USB HID rawkeyboard library for Arduino IDE 1.0.1/1.0.5 modify HID.cpp can send Usage code >101
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* Copyright (c) 2011, Peter Barrett | |
** | |
** Permission to use, copy, modify, and/or distribute this software for | |
** any purpose with or without fee is hereby granted, provided that the | |
** above copyright notice and this permission notice appear in all copies. | |
** | |
** THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL | |
** WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED | |
** WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR | |
** BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES | |
** OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, | |
** WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, | |
** ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS | |
** SOFTWARE. | |
*/ | |
#include "Platform.h" | |
#include "USBAPI.h" | |
#include "USBDesc.h" | |
#if defined(USBCON) | |
#ifdef HID_ENABLED | |
//#define RAWHID_ENABLED | |
// Singletons for mouse and keyboard | |
Mouse_ Mouse; | |
Keyboard_ Keyboard; | |
//================================================================================ | |
//================================================================================ | |
// HID report descriptor | |
#define LSB(_x) ((_x) & 0xFF) | |
#define MSB(_x) ((_x) >> 8) | |
#define RAWHID_USAGE_PAGE 0xFFC0 | |
#define RAWHID_USAGE 0x0C00 | |
#define RAWHID_TX_SIZE 64 | |
#define RAWHID_RX_SIZE 64 | |
extern const u8 _hidReportDescriptor[] PROGMEM; | |
const u8 _hidReportDescriptor[] = { | |
// Mouse | |
0x05, 0x01, // USAGE_PAGE (Generic Desktop) // 54 | |
0x09, 0x02, // USAGE (Mouse) | |
0xa1, 0x01, // COLLECTION (Application) | |
0x09, 0x01, // USAGE (Pointer) | |
0xa1, 0x00, // COLLECTION (Physical) | |
0x85, 0x01, // REPORT_ID (1) | |
0x05, 0x09, // USAGE_PAGE (Button) | |
0x19, 0x01, // USAGE_MINIMUM (Button 1) | |
0x29, 0x03, // USAGE_MAXIMUM (Button 3) | |
0x15, 0x00, // LOGICAL_MINIMUM (0) | |
0x25, 0x01, // LOGICAL_MAXIMUM (1) | |
0x95, 0x03, // REPORT_COUNT (3) | |
0x75, 0x01, // REPORT_SIZE (1) | |
0x81, 0x02, // INPUT (Data,Var,Abs) | |
0x95, 0x01, // REPORT_COUNT (1) | |
0x75, 0x05, // REPORT_SIZE (5) | |
0x81, 0x03, // INPUT (Cnst,Var,Abs) | |
0x05, 0x01, // USAGE_PAGE (Generic Desktop) | |
0x09, 0x30, // USAGE (X) | |
0x09, 0x31, // USAGE (Y) | |
0x09, 0x38, // USAGE (Wheel) | |
0x15, 0x81, // LOGICAL_MINIMUM (-127) | |
0x25, 0x7f, // LOGICAL_MAXIMUM (127) | |
0x75, 0x08, // REPORT_SIZE (8) | |
0x95, 0x03, // REPORT_COUNT (3) | |
0x81, 0x06, // INPUT (Data,Var,Rel) | |
0xc0, // END_COLLECTION | |
0xc0, // END_COLLECTION | |
// Keyboard | |
0x05, 0x01, // USAGE_PAGE (Generic Desktop) // 47 | |
0x09, 0x06, // USAGE (Keyboard) | |
0xa1, 0x01, // COLLECTION (Application) | |
0x85, 0x02, // REPORT_ID (2) | |
0x05, 0x07, // USAGE_PAGE (Keyboard) | |
0x19, 0xe0, // USAGE_MINIMUM (Keyboard LeftControl) | |
0x29, 0xe7, // USAGE_MAXIMUM (Keyboard Right GUI) | |
0x15, 0x00, // LOGICAL_MINIMUM (0) | |
0x25, 0x01, // LOGICAL_MAXIMUM (1) | |
0x75, 0x01, // REPORT_SIZE (1) | |
0x95, 0x08, // REPORT_COUNT (8) | |
0x81, 0x02, // INPUT (Data,Var,Abs) | |
0x95, 0x01, // REPORT_COUNT (1) | |
0x75, 0x08, // REPORT_SIZE (8) | |
0x81, 0x03, // INPUT (Cnst,Var,Abs) | |
0x95, 0x06, // REPORT_COUNT (6) | |
0x75, 0x08, // REPORT_SIZE (8) | |
0x15, 0x00, // LOGICAL_MINIMUM (0) | |
0x25, 0xFE, // LOGICAL_MAXIMUM (101) @0x65->0xFE | |
0x05, 0x07, // USAGE_PAGE (Keyboard) | |
0x19, 0x00, // USAGE_MINIMUM (Reserved (no event indicated)) | |
0x29, 0xFE, // USAGE_MAXIMUM (Keyboard Application) @0x65->0xFE | |
0x81, 0x00, // INPUT (Data,Ary,Abs) | |
0xc0, // END_COLLECTION | |
#if RAWHID_ENABLED | |
// RAW HID | |
0x06, LSB(RAWHID_USAGE_PAGE), MSB(RAWHID_USAGE_PAGE), // 30 | |
0x0A, LSB(RAWHID_USAGE), MSB(RAWHID_USAGE), | |
0xA1, 0x01, // Collection 0x01 | |
0x85, 0x03, // REPORT_ID (3) | |
0x75, 0x08, // report size = 8 bits | |
0x15, 0x00, // logical minimum = 0 | |
0x26, 0xFF, 0x00, // logical maximum = 255 | |
0x95, 64, // report count TX | |
0x09, 0x01, // usage | |
0x81, 0x02, // Input (array) | |
0x95, 64, // report count RX | |
0x09, 0x02, // usage | |
0x91, 0x02, // Output (array) | |
0xC0 // end collection | |
#endif | |
}; | |
extern const HIDDescriptor _hidInterface PROGMEM; | |
const HIDDescriptor _hidInterface = | |
{ | |
D_INTERFACE(HID_INTERFACE,1,3,0,0), | |
D_HIDREPORT(sizeof(_hidReportDescriptor)), | |
D_ENDPOINT(USB_ENDPOINT_IN (HID_ENDPOINT_INT),USB_ENDPOINT_TYPE_INTERRUPT,0x40,0x01) | |
}; | |
//================================================================================ | |
//================================================================================ | |
// Driver | |
u8 _hid_protocol = 1; | |
u8 _hid_idle = 1; | |
#define WEAK __attribute__ ((weak)) | |
int WEAK HID_GetInterface(u8* interfaceNum) | |
{ | |
interfaceNum[0] += 1; // uses 1 | |
return USB_SendControl(TRANSFER_PGM,&_hidInterface,sizeof(_hidInterface)); | |
} | |
int WEAK HID_GetDescriptor(int i) | |
{ | |
return USB_SendControl(TRANSFER_PGM,_hidReportDescriptor,sizeof(_hidReportDescriptor)); | |
} | |
void WEAK HID_SendReport(u8 id, const void* data, int len) | |
{ | |
USB_Send(HID_TX, &id, 1); | |
USB_Send(HID_TX | TRANSFER_RELEASE,data,len); | |
} | |
bool WEAK HID_Setup(Setup& setup) | |
{ | |
u8 r = setup.bRequest; | |
u8 requestType = setup.bmRequestType; | |
if (REQUEST_DEVICETOHOST_CLASS_INTERFACE == requestType) | |
{ | |
if (HID_GET_REPORT == r) | |
{ | |
//HID_GetReport(); | |
return true; | |
} | |
if (HID_GET_PROTOCOL == r) | |
{ | |
//Send8(_hid_protocol); // TODO | |
return true; | |
} | |
} | |
if (REQUEST_HOSTTODEVICE_CLASS_INTERFACE == requestType) | |
{ | |
if (HID_SET_PROTOCOL == r) | |
{ | |
_hid_protocol = setup.wValueL; | |
return true; | |
} | |
if (HID_SET_IDLE == r) | |
{ | |
_hid_idle = setup.wValueL; | |
return true; | |
} | |
} | |
return false; | |
} | |
//================================================================================ | |
//================================================================================ | |
// Mouse | |
Mouse_::Mouse_(void) : _buttons(0) | |
{ | |
} | |
void Mouse_::begin(void) | |
{ | |
} | |
void Mouse_::end(void) | |
{ | |
} | |
void Mouse_::click(uint8_t b) | |
{ | |
_buttons = b; | |
move(0,0,0); | |
_buttons = 0; | |
move(0,0,0); | |
} | |
void Mouse_::move(signed char x, signed char y, signed char wheel) | |
{ | |
u8 m[4]; | |
m[0] = _buttons; | |
m[1] = x; | |
m[2] = y; | |
m[3] = wheel; | |
HID_SendReport(1,m,4); | |
} | |
void Mouse_::buttons(uint8_t b) | |
{ | |
if (b != _buttons) | |
{ | |
_buttons = b; | |
move(0,0,0); | |
} | |
} | |
void Mouse_::press(uint8_t b) | |
{ | |
buttons(_buttons | b); | |
} | |
void Mouse_::release(uint8_t b) | |
{ | |
buttons(_buttons & ~b); | |
} | |
bool Mouse_::isPressed(uint8_t b) | |
{ | |
if ((b & _buttons) > 0) | |
return true; | |
return false; | |
} | |
//================================================================================ | |
//================================================================================ | |
// Keyboard | |
Keyboard_::Keyboard_(void) | |
{ | |
} | |
void Keyboard_::begin(void) | |
{ | |
} | |
void Keyboard_::end(void) | |
{ | |
} | |
void Keyboard_::sendReport(KeyReport* keys) | |
{ | |
HID_SendReport(2,keys,sizeof(KeyReport)); | |
} | |
extern | |
const uint8_t _asciimap[128] PROGMEM; | |
#define SHIFT 0x80 | |
const uint8_t _asciimap[128] = | |
{ | |
0x00, // NUL | |
0x00, // SOH | |
0x00, // STX | |
0x00, // ETX | |
0x00, // EOT | |
0x00, // ENQ | |
0x00, // ACK | |
0x00, // BEL | |
0x2a, // BS Backspace | |
0x2b, // TAB Tab | |
0x28, // LF Enter | |
0x00, // VT | |
0x00, // FF | |
0x00, // CR | |
0x00, // SO | |
0x00, // SI | |
0x00, // DEL | |
0x00, // DC1 | |
0x00, // DC2 | |
0x00, // DC3 | |
0x00, // DC4 | |
0x00, // NAK | |
0x00, // SYN | |
0x00, // ETB | |
0x00, // CAN | |
0x00, // EM | |
0x00, // SUB | |
0x00, // ESC | |
0x00, // FS | |
0x00, // GS | |
0x00, // RS | |
0x00, // US | |
0x2c, // ' ' | |
0x1e|SHIFT, // ! | |
0x34|SHIFT, // " | |
0x20|SHIFT, // # | |
0x21|SHIFT, // $ | |
0x22|SHIFT, // % | |
0x24|SHIFT, // & | |
0x34, // ' | |
0x26|SHIFT, // ( | |
0x27|SHIFT, // ) | |
0x25|SHIFT, // * | |
0x2e|SHIFT, // + | |
0x36, // , | |
0x2d, // - | |
0x37, // . | |
0x38, // / | |
0x27, // 0 | |
0x1e, // 1 | |
0x1f, // 2 | |
0x20, // 3 | |
0x21, // 4 | |
0x22, // 5 | |
0x23, // 6 | |
0x24, // 7 | |
0x25, // 8 | |
0x26, // 9 | |
0x33|SHIFT, // : | |
0x33, // ; | |
0x36|SHIFT, // < | |
0x2e, // = | |
0x37|SHIFT, // > | |
0x38|SHIFT, // ? | |
0x1f|SHIFT, // @ | |
0x04|SHIFT, // A | |
0x05|SHIFT, // B | |
0x06|SHIFT, // C | |
0x07|SHIFT, // D | |
0x08|SHIFT, // E | |
0x09|SHIFT, // F | |
0x0a|SHIFT, // G | |
0x0b|SHIFT, // H | |
0x0c|SHIFT, // I | |
0x0d|SHIFT, // J | |
0x0e|SHIFT, // K | |
0x0f|SHIFT, // L | |
0x10|SHIFT, // M | |
0x11|SHIFT, // N | |
0x12|SHIFT, // O | |
0x13|SHIFT, // P | |
0x14|SHIFT, // Q | |
0x15|SHIFT, // R | |
0x16|SHIFT, // S | |
0x17|SHIFT, // T | |
0x18|SHIFT, // U | |
0x19|SHIFT, // V | |
0x1a|SHIFT, // W | |
0x1b|SHIFT, // X | |
0x1c|SHIFT, // Y | |
0x1d|SHIFT, // Z | |
0x2f, // [ | |
0x31, // bslash | |
0x30, // ] | |
0x23|SHIFT, // ^ | |
0x2d|SHIFT, // _ | |
0x35, // ` | |
0x04, // a | |
0x05, // b | |
0x06, // c | |
0x07, // d | |
0x08, // e | |
0x09, // f | |
0x0a, // g | |
0x0b, // h | |
0x0c, // i | |
0x0d, // j | |
0x0e, // k | |
0x0f, // l | |
0x10, // m | |
0x11, // n | |
0x12, // o | |
0x13, // p | |
0x14, // q | |
0x15, // r | |
0x16, // s | |
0x17, // t | |
0x18, // u | |
0x19, // v | |
0x1a, // w | |
0x1b, // x | |
0x1c, // y | |
0x1d, // z | |
0x2f|SHIFT, // | |
0x31|SHIFT, // | | |
0x30|SHIFT, // } | |
0x35|SHIFT, // ~ | |
0 // DEL | |
}; | |
uint8_t USBPutChar(uint8_t c); | |
// press() adds the specified key (printing, non-printing, or modifier) | |
// to the persistent key report and sends the report. Because of the way | |
// USB HID works, the host acts like the key remains pressed until we | |
// call release(), releaseAll(), or otherwise clear the report and resend. | |
size_t Keyboard_::press(uint8_t k) | |
{ | |
uint8_t i; | |
if (k >= 136) { // it's a non-printing key (not a modifier) | |
k = k - 136; | |
} else if (k >= 128) { // it's a modifier key | |
_keyReport.modifiers |= (1<<(k-128)); | |
k = 0; | |
} else { // it's a printing key | |
k = pgm_read_byte(_asciimap + k); | |
if (!k) { | |
setWriteError(); | |
return 0; | |
} | |
if (k & 0x80) { // it's a capital letter or other character reached with shift | |
_keyReport.modifiers |= 0x02; // the left shift modifier | |
k &= 0x7F; | |
} | |
} | |
// Add k to the key report only if it's not already present | |
// and if there is an empty slot. | |
if (_keyReport.keys[0] != k && _keyReport.keys[1] != k && | |
_keyReport.keys[2] != k && _keyReport.keys[3] != k && | |
_keyReport.keys[4] != k && _keyReport.keys[5] != k) { | |
for (i=0; i<6; i++) { | |
if (_keyReport.keys[i] == 0x00) { | |
_keyReport.keys[i] = k; | |
break; | |
} | |
} | |
if (i == 6) { | |
setWriteError(); | |
return 0; | |
} | |
} | |
sendReport(&_keyReport); | |
return 1; | |
} | |
// release() takes the specified key out of the persistent key report and | |
// sends the report. This tells the OS the key is no longer pressed and that | |
// it shouldn't be repeated any more. | |
size_t Keyboard_::release(uint8_t k) | |
{ | |
uint8_t i; | |
if (k >= 136) { // it's a non-printing key (not a modifier) | |
k = k - 136; | |
} else if (k >= 128) { // it's a modifier key | |
_keyReport.modifiers &= ~(1<<(k-128)); | |
k = 0; | |
} else { // it's a printing key | |
k = pgm_read_byte(_asciimap + k); | |
if (!k) { | |
return 0; | |
} | |
if (k & 0x80) { // it's a capital letter or other character reached with shift | |
_keyReport.modifiers &= ~(0x02); // the left shift modifier | |
k &= 0x7F; | |
} | |
} | |
// Test the key report to see if k is present. Clear it if it exists. | |
// Check all positions in case the key is present more than once (which it shouldn't be) | |
for (i=0; i<6; i++) { | |
if (0 != k && _keyReport.keys[i] == k) { | |
_keyReport.keys[i] = 0x00; | |
} | |
} | |
sendReport(&_keyReport); | |
return 1; | |
} | |
void Keyboard_::releaseAll(void) | |
{ | |
_keyReport.keys[0] = 0; | |
_keyReport.keys[1] = 0; | |
_keyReport.keys[2] = 0; | |
_keyReport.keys[3] = 0; | |
_keyReport.keys[4] = 0; | |
_keyReport.keys[5] = 0; | |
_keyReport.modifiers = 0; | |
sendReport(&_keyReport); | |
} | |
size_t Keyboard_::write(uint8_t c) | |
{ | |
uint8_t p = press(c); // Keydown | |
uint8_t r = release(c); // Keyup | |
return (p); // just return the result of press() since release() almost always returns 1 | |
} | |
#endif | |
#endif /* if defined(USBCON) */ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <USBrawkeyboard.h> | |
USBrawkeyboard rawkybd; | |
int r; | |
void setup() { | |
Keyboard.begin(); // Arduino Leonardo only | |
rawkybd.begin() ; | |
delay(1000); | |
} | |
void test1() { | |
for(int i=0x04; i<=0x27;i++) { // a-z0-9 | |
rawkybd.press(i); | |
rawkybd.release(i); | |
} | |
for(int i=0x2d; i<=0x31;i++) { // -=[]¥ (US layout) | |
rawkybd.press(i);rawkybd.release(i); | |
} | |
for(int i=0x33; i<=0x38;i++) { // ;'`,./ | |
if(i==0x35) continue; // skip ` | |
rawkybd.press(i);rawkybd.release(i); | |
} | |
rawkybd.press(0x32);rawkybd.release(0x32); // Europe1 | |
rawkybd.press(0x64);rawkybd.release(0x64); // Europe2 | |
rawkybd.press(0x89);rawkybd.release(0x89); // YEN | |
rawkybd.press(0x87);rawkybd.release(0x87); // Ro | |
} | |
void loop() { | |
test1();delay(10000); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// USB 1-key | |
// 20140804 @houmei | |
// | |
#include <USBrawkeyboard.h> | |
USBrawkeyboard rawkybd; | |
#define BUTTON 4 | |
#define LED 13 | |
void setup() { | |
pinMode(BUTTON,INPUT_PULLUP); | |
pinMode(LED,OUTPUT); | |
} | |
int pressed; // BUTTON | |
int prev; // previous pressed | |
// int keycode=0x04; // 'a' | |
// int keycode=0x46; // 'PRINT SCREEN' | |
int keycode=0x35; // Zenkaku/Hankaku(JP Keyboard)/(~` US keyboard) | |
// int keycode=0x89; // Yen -> need HID.cpp patch | |
void loop() { | |
pressed=!digitalRead(BUTTON); // 1..press 0..release | |
if (pressed==prev) { | |
digitalWrite(LED,pressed); | |
if (pressed==1) { | |
rawkybd.press(keycode); | |
} else { | |
rawkybd.release(keycode); | |
} | |
} | |
prev=pressed; | |
delay(50); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
http://arduino.cc/playground/Main/PS2Keyboard | |
http://arduino.cc/playground/Main/PS2KeyboardExt2 | |
http://msdn.microsoft.com/en-us/library/windows/hardware/gg463446.aspx | |
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - | |
This library is free software; you can redistribute it and/or | |
modify it under the terms of the GNU Lesser General Public | |
License as published by the Free Software Foundation; either | |
version 2.1 of the License, or (at your option) any later version. | |
This library is distributed in the hope that it will be useful, | |
but WITHOUT ANY WARRANTY; without even the implied warranty of | |
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
Lesser General Public License for more details. | |
You should have received a copy of the GNU Lesser General Public | |
License along with this library; if not, write to the Free Software | |
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | |
*/ | |
#include "USBrawkeyboard.h" | |
#define HID_USAGEPAGE 0x0700 | |
Keyboard_ usbkybd; | |
USBrawkeyboard::USBrawkeyboard() { | |
// nothing to do here | |
} | |
// Low level key report: up to 6 keys and shift, ctrl etc at once | |
/* | |
typedef struct | |
{ | |
uint8_t modifiers; | |
uint8_t reserved; | |
uint8_t keys[6]; | |
} KeyReport; | |
*/ | |
KeyReport _keyReport; | |
// void sendReport(KeyReport* keys) { | |
// HID_SendReport(2,keys,sizeof(KeyReport)); | |
// } | |
void localsendReport(KeyReport* keys) | |
{ | |
HID_SendReport(2,keys,sizeof(KeyReport)); | |
} | |
void USBrawkeyboard::begin() { | |
// nothing do here | |
} | |
uint8_t USBrawkeyboard::press(uint8_t k) { | |
uint8_t i; | |
if (!k) { | |
// setWriteError(); | |
return 0; | |
} | |
// Add k to the key report only if it's not already present | |
// and if there is an empty slot. | |
if (_keyReport.keys[0] != k && _keyReport.keys[1] != k && | |
_keyReport.keys[2] != k && _keyReport.keys[3] != k && | |
_keyReport.keys[4] != k && _keyReport.keys[5] != k) { | |
for (i=0; i<6; i++) { | |
if (_keyReport.keys[i] == 0x00) { | |
_keyReport.keys[i] = k; | |
break; | |
} | |
} | |
if (i == 6) { | |
// setWriteError(); | |
return 0; | |
} | |
} | |
localsendReport(&_keyReport); | |
return 1; | |
} | |
uint8_t USBrawkeyboard::release(uint8_t k) { | |
uint8_t i; | |
if (!k) { | |
return 0; | |
} | |
// Test the key report to see if k is present. Clear it if it exists. | |
// Check all positions in case the key is present more than once (which it shouldn't be) | |
for (i=0; i<6; i++) { | |
if (0 != k && _keyReport.keys[i] == k) { | |
_keyReport.keys[i] = 0x00; | |
} | |
} | |
localsendReport(&_keyReport); | |
return 1; | |
} | |
void USBrawkeyboard::releaseAll(void) { | |
_keyReport.keys[0] = 0; | |
_keyReport.keys[1] = 0; | |
_keyReport.keys[2] = 0; | |
_keyReport.keys[3] = 0; | |
_keyReport.keys[4] = 0; | |
_keyReport.keys[5] = 0; | |
_keyReport.modifiers = 0; | |
localsendReport(&_keyReport); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#ifndef USBrawkeyboard_h | |
#define USBrawkeyboard_h | |
#include "Arduino.h" | |
// for Arduino Leonardo IDE1.0.1 | |
// Purpose: raw access to USB HID Keyboard | |
// Author: Katunori Takesita 2012.10.05 | |
class USBrawkeyboard { | |
public: | |
// This constructor does basically nothing. | |
USBrawkeyboard(); | |
void begin(); | |
uint8_t press(uint8_t k); | |
uint8_t release(uint8_t k); | |
void releaseAll(); | |
}; | |
#endif |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment