@@ -89,6 +89,7 @@ const u8 _hidReportDescriptor[] = {
8989 0x85 , HID_REPORTID_KEYBOARD, // REPORT_ID (2)
9090 0x05 , 0x07 , // USAGE_PAGE (Keyboard)
9191
92+ // Keyboard Modifiers (shift, alt, ...)
9293 0x19 , 0xe0 , // USAGE_MINIMUM (Keyboard LeftControl)
9394 0x29 , 0xe7 , // USAGE_MAXIMUM (Keyboard Right GUI)
9495 0x15 , 0x00 , // LOGICAL_MINIMUM (0)
@@ -101,14 +102,14 @@ const u8 _hidReportDescriptor[] = {
101102 0x75 , 0x08 , // REPORT_SIZE (8)
102103 0x81 , 0x03 , // INPUT (Cnst,Var,Abs)
103104
105+ // Keyboard keys
104106 0x95 , 0x06 , // REPORT_COUNT (6)
105107 0x75 , 0x08 , // REPORT_SIZE (8)
106108 0x15 , 0x00 , // LOGICAL_MINIMUM (0)
107- 0x25 , 0x65 , // LOGICAL_MAXIMUM (101 )
109+ 0x26 , 0xDF , 0x00 , // LOGICAL_MAXIMUM (239 )
108110 0x05 , 0x07 , // USAGE_PAGE (Keyboard)
109-
110111 0x19 , 0x00 , // USAGE_MINIMUM (Reserved (no event indicated))
111- 0x29 , 0x65 , // USAGE_MAXIMUM (Keyboard Application )
112+ 0x29 , 0xDF , // USAGE_MAXIMUM (Left Control - 1 )
112113 0x81 , 0x00 , // INPUT (Data,Ary,Abs)
113114 0xc0 , // END_COLLECTION
114115
@@ -457,9 +458,33 @@ uint8_t USBPutChar(uint8_t c);
457458// to the persistent key report and sends the report. Because of the way
458459// USB HID works, the host acts like the key remains pressed until we
459460// call release(), releaseAll(), or otherwise clear the report and resend.
460- size_t Keyboard_::press (uint8_t k)
461+ size_t Keyboard_::pressRaw (uint8_t k)
461462{
462463 uint8_t i;
464+ // Add k to the key report only if it's not already present
465+ // and if there is an empty slot.
466+ if (_keyReport.keys [0 ] != k && _keyReport.keys [1 ] != k &&
467+ _keyReport.keys [2 ] != k && _keyReport.keys [3 ] != k &&
468+ _keyReport.keys [4 ] != k && _keyReport.keys [5 ] != k) {
469+
470+ for (i=0 ; i<6 ; i++) {
471+ if (_keyReport.keys [i] == 0x00 ) {
472+ _keyReport.keys [i] = k;
473+ break ;
474+ }
475+ }
476+ if (i == 6 || (k >= 0xE0 )) {
477+ setWriteError ();
478+ return 0 ;
479+ }
480+ }
481+ sendReport (&_keyReport);
482+ return 1 ;
483+ }
484+
485+ // translates ASCII characters to usage
486+ size_t Keyboard_::press (uint8_t k)
487+ {
463488 if (k >= 136 ) { // it's a non-printing key (not a modifier)
464489 k = k - 136 ;
465490 } else if (k >= 128 ) { // it's a modifier key
@@ -476,28 +501,48 @@ size_t Keyboard_::press(uint8_t k)
476501 k &= 0x7F ;
477502 }
478503 }
479-
480- // Add k to the key report only if it's not already present
481- // and if there is an empty slot.
482- if (_keyReport.keys [0 ] != k && _keyReport.keys [1 ] != k &&
483- _keyReport.keys [2 ] != k && _keyReport.keys [3 ] != k &&
484- _keyReport.keys [4 ] != k && _keyReport.keys [5 ] != k) {
485-
486- for (i=0 ; i<6 ; i++) {
487- if (_keyReport.keys [i] == 0x00 ) {
488- _keyReport.keys [i] = k;
489- break ;
490- }
504+ return pressRaw (k);
505+ }
506+
507+ // release() takes the specified key out of the persistent key report and
508+ // sends the report. This tells the OS the key is no longer pressed and that
509+ // it shouldn't be repeated any more.
510+ size_t Keyboard_::releaseRaw (uint8_t k)
511+ {
512+ uint8_t i;
513+ // Test the key report to see if k is present. Clear it if it exists.
514+ // Check all positions in case the key is present more than once (which it shouldn't be)
515+ for (i=0 ; i<6 ; i++) {
516+ if (0 != k && _keyReport.keys [i] == k) {
517+ _keyReport.keys [i] = 0x00 ;
491518 }
492- if (i == 6 ) {
493- setWriteError ();
494- return 0 ;
495- }
496519 }
520+
497521 sendReport (&_keyReport);
498522 return 1 ;
499523}
500524
525+ // translates ASCII characters to usage
526+ size_t Keyboard_::release (uint8_t k)
527+ {
528+ if (k >= 136 ) { // it's a non-printing key (not a modifier)
529+ k = k - 136 ;
530+ } else if (k >= 128 ) { // it's a modifier key
531+ _keyReport.modifiers &= ~(1 <<(k-128 ));
532+ k = 0 ;
533+ } else { // it's a printing key
534+ k = pgm_read_byte (_asciimap + k);
535+ if (!k) {
536+ return 0 ;
537+ }
538+ if (k & 0x80 ) { // it's a capital letter or other character reached with shift
539+ _keyReport.modifiers &= ~(0x02 ); // the left shift modifier
540+ k &= 0x7F ;
541+ }
542+ }
543+ return releaseRaw (k);
544+ }
545+
501546// System Control
502547// k is one of the SYSTEM_CONTROL defines which come from the HID usage table "Generic Desktop Page (0x01)"
503548// in "HID Usage Tables" (HUT1_12v2.pdf)
@@ -530,40 +575,6 @@ size_t Keyboard_::systemControl(uint8_t k)
530575 }
531576}
532577
533- // release() takes the specified key out of the persistent key report and
534- // sends the report. This tells the OS the key is no longer pressed and that
535- // it shouldn't be repeated any more.
536- size_t Keyboard_::release (uint8_t k)
537- {
538- uint8_t i;
539- if (k >= 136 ) { // it's a non-printing key (not a modifier)
540- k = k - 136 ;
541- } else if (k >= 128 ) { // it's a modifier key
542- _keyReport.modifiers &= ~(1 <<(k-128 ));
543- k = 0 ;
544- } else { // it's a printing key
545- k = pgm_read_byte (_asciimap + k);
546- if (!k) {
547- return 0 ;
548- }
549- if (k & 0x80 ) { // it's a capital letter or other character reached with shift
550- _keyReport.modifiers &= ~(0x02 ); // the left shift modifier
551- k &= 0x7F ;
552- }
553- }
554-
555- // Test the key report to see if k is present. Clear it if it exists.
556- // Check all positions in case the key is present more than once (which it shouldn't be)
557- for (i=0 ; i<6 ; i++) {
558- if (0 != k && _keyReport.keys [i] == k) {
559- _keyReport.keys [i] = 0x00 ;
560- }
561- }
562-
563- sendReport (&_keyReport);
564- return 1 ;
565- }
566-
567578void Keyboard_::releaseAll (void )
568579{
569580 _keyReport.keys [0 ] = 0 ;
@@ -576,10 +587,17 @@ void Keyboard_::releaseAll(void)
576587 sendReport (&_keyReport);
577588}
578589
590+ size_t Keyboard_::writeRaw (uint8_t c)
591+ {
592+ uint8_t p = pressRaw (c); // Keydown
593+ releaseRaw (c); // Keyup
594+ return (p); // just return the result of press() since release() almost always returns 1
595+ }
596+
579597size_t Keyboard_::write (uint8_t c)
580598{
581599 uint8_t p = press (c); // Keydown
582- uint8_t r = release (c); // Keyup
600+ release (c); // Keyup
583601 return (p); // just return the result of press() since release() almost always returns 1
584602}
585603
0 commit comments