From 59a3ab1596f6c767912ce73e82825d2eb93a4bcf Mon Sep 17 00:00:00 2001 From: Brandon Maier Date: Sat, 25 Jul 2026 16:45:58 -0500 Subject: [PATCH] Map Usb Keycodes to Enum --- src/keyboard.rs | 126 +++++++++++++++++++++++++++++++++++++++++++++--- src/main.rs | 16 +++--- src/usb.rs | 13 ++--- 3 files changed, 131 insertions(+), 24 deletions(-) diff --git a/src/keyboard.rs b/src/keyboard.rs index a4ddaef..166df45 100644 --- a/src/keyboard.rs +++ b/src/keyboard.rs @@ -4,14 +4,126 @@ use embassy_sync::blocking_mutex::raw::RawMutex; use embassy_sync::channel::Sender; use futures_util::stream::{FuturesUnordered, StreamExt}; +#[repr(u8)] +#[derive(Clone, Copy, Debug, PartialEq, Eq)] +#[allow(dead_code)] +pub enum UsbKeycodes { + A = 4, + B, + C, + D, + E, + F, + G, + H, + I, + J, + K, + L, + M, + N, + O, + P, + Q, + R, + S, + T, + U, + V, + W, + X, + Y, + Z, + One, + Two, + Three, + Four, + Five, + Six, + Seven, + Eight, + Nine, + Zero, + Enter, + Escape, + BackSpace, + Tab, + Space, + Hyphen, + Equal, + SquareBracketLeft, + SquareBracketRight, + BackSlash, + + Semicolon = 51, + SingleQuote, + Backtick, + Comma, + Period, + ForwardSlash, + CapsLock, + F1, + F2, + F3, + F4, + F5, + F6, + F7, + F8, + F9, + F10, + F11, + F12, + PrintScreen, + ScrollLock, + Pause, + Insert, + Home, + PageUp, + Delete, + End, + PageDown, + Right, + Left, + Down, + Up, + NumLock, + + F13 = 104, + F14, + F15, + F16, + F17, + F18, + F19, + F20, + F21, + F22, + F23, + F24, + Execute, + Help, + Menu, + Select, + Again, + Undo, + Cut, + Copy, + Paste, + Find, + Mute, + VolumeUp, + VolumeDown, +} + pub struct Key<'a> { button: Input<'a>, - value: char, + value: UsbKeycodes, } impl Key<'_> { #[allow(unused)] - pub async fn set_value(mut self, value: char) { + pub async fn set_value(mut self, value: UsbKeycodes) { self.value = value; } } @@ -34,7 +146,7 @@ impl<'d, const KEY_N: usize> Keyboard<'d, KEY_N> { } } - pub fn add_key(&mut self, button: Input<'d>, value: char) -> Result<(), KeyboardError> { + pub fn add_key(&mut self, button: Input<'d>, value: UsbKeycodes) -> Result<(), KeyboardError> { let key = self .keys .get_mut(self.num_keys) @@ -46,8 +158,10 @@ impl<'d, const KEY_N: usize> Keyboard<'d, KEY_N> { Ok(()) } - pub async fn process<'ch, M, const N: usize>(mut self, sender: Sender<'ch, M, Vec, N>) - where + pub async fn process<'ch, M, const N: usize>( + mut self, + sender: Sender<'ch, M, Vec, N>, + ) where M: RawMutex, { loop { @@ -58,7 +172,7 @@ impl<'d, const KEY_N: usize> Keyboard<'d, KEY_N> { .next() .await; - let mut pressed: Vec = Vec::new(); + let mut pressed: Vec = Vec::new(); for key in self.keys.iter_mut().filter_map(|opt| opt.as_mut()) { if key.button.is_low() { pressed.push(key.value); diff --git a/src/main.rs b/src/main.rs index 3086845..2665341 100644 --- a/src/main.rs +++ b/src/main.rs @@ -7,7 +7,7 @@ mod usb; extern crate alloc; use crate::heartbeat::heartbeat; -use crate::keyboard::Keyboard; +use crate::keyboard::{Keyboard, UsbKeycodes}; use alloc::vec::Vec; use defmt::*; use embassy_executor::Spawner; @@ -39,7 +39,7 @@ async fn main(_spawner: Spawner) { ); } - let keyboard_events: Channel, 64> = Channel::new(); + let keyboard_events: Channel, 64> = Channel::new(); let p = embassy_rp::init(Default::default()); @@ -51,7 +51,7 @@ async fn main(_spawner: Spawner) { let mut signal_pin = Input::new(p.PIN_15, Pull::None); signal_pin.set_schmitt(true); - match keyboard.add_key(signal_pin, 'a') { + match keyboard.add_key(signal_pin, UsbKeycodes::Left) { Ok(()) => info!("Key 'a' registered"), Err(e) => { defmt::panic!("Failed to register key! {:?}", e); @@ -59,7 +59,7 @@ async fn main(_spawner: Spawner) { } let mut signal_pin = Input::new(p.PIN_16, Pull::None); signal_pin.set_schmitt(true); - match keyboard.add_key(signal_pin, 's') { + match keyboard.add_key(signal_pin, UsbKeycodes::Down) { Ok(()) => info!("Key 's' registered"), Err(e) => { defmt::panic!("Failed to register key! {:?}", e); @@ -67,7 +67,7 @@ async fn main(_spawner: Spawner) { } let mut signal_pin = Input::new(p.PIN_17, Pull::None); signal_pin.set_schmitt(true); - match keyboard.add_key(signal_pin, 'x') { + match keyboard.add_key(signal_pin, UsbKeycodes::X) { Ok(()) => info!("Key 'x' registered"), Err(e) => { defmt::panic!("Failed to register key! {:?}", e); @@ -75,7 +75,7 @@ async fn main(_spawner: Spawner) { } let mut signal_pin = Input::new(p.PIN_18, Pull::None); signal_pin.set_schmitt(true); - match keyboard.add_key(signal_pin, 'd') { + match keyboard.add_key(signal_pin, UsbKeycodes::Right) { Ok(()) => info!("Key 'd' registered"), Err(e) => { defmt::panic!("Failed to register key! {:?}", e); @@ -83,7 +83,7 @@ async fn main(_spawner: Spawner) { } let mut signal_pin = Input::new(p.PIN_19, Pull::None); signal_pin.set_schmitt(true); - match keyboard.add_key(signal_pin, 'c') { + match keyboard.add_key(signal_pin, UsbKeycodes::C) { Ok(()) => info!("Key 'c' registered"), Err(e) => { defmt::panic!("Failed to register key! {:?}", e); @@ -91,7 +91,7 @@ async fn main(_spawner: Spawner) { } let mut signal_pin = Input::new(p.PIN_20, Pull::None); signal_pin.set_schmitt(true); - match keyboard.add_key(signal_pin, 'w') { + match keyboard.add_key(signal_pin, UsbKeycodes::Up) { Ok(()) => info!("Key 'w' registered"), Err(e) => { defmt::panic!("Failed to register key! {:?}", e); diff --git a/src/usb.rs b/src/usb.rs index f5146bf..fd7a128 100644 --- a/src/usb.rs +++ b/src/usb.rs @@ -1,3 +1,4 @@ +use crate::keyboard::UsbKeycodes; use alloc::vec::Vec; use core::cell::OnceCell; use core::sync::atomic::{AtomicBool, AtomicU8, Ordering}; @@ -107,7 +108,7 @@ impl<'d> UsbKeyboard<'d> { } } - pub async fn run<'ch, M, const N: usize>(self, receiver: Receiver<'ch, M, Vec, N>) + pub async fn run<'ch, M, const N: usize>(self, receiver: Receiver<'ch, M, Vec, N>) where M: RawMutex, { @@ -130,15 +131,7 @@ impl<'d> UsbKeyboard<'d> { let mut boot_keys = [0, 0, 0, 0, 0, 0, 0, 0]; for (&key, idx) in event.iter().zip(2usize..) { - let boot_key = match key { - 'd' => 79, - 'a' => 80, - 's' => 81, - 'w' => 82, - ('a'..='z') => (key as u8) - b'a' + 4, - _ => defmt::panic!("Not supported key: {}", key), - }; - boot_keys[idx] = boot_key; + boot_keys[idx] = key as u8; } if HID_PROTOCOL_MODE.load(Ordering::Relaxed) == HidProtocolMode::Boot as u8 {