use super::{
DecodeState, Error, KeyCode, KeyEvent, KeyState, ScancodeSet, EXTENDED_KEY_CODE,
KEY_RELEASE_CODE,
};
pub struct ScancodeSet1;
impl ScancodeSet for ScancodeSet1 {
fn advance_state(state: &mut DecodeState, code: u8) -> Result<Option<KeyEvent>, Error> {
match *state {
DecodeState::Start => {
match code {
EXTENDED_KEY_CODE => {
*state = DecodeState::Extended;
Ok(None)
}
0x80..=0xFF => {
Ok(Some(KeyEvent::new(
Self::map_scancode(code - 0x80)?,
KeyState::Up,
)))
}
_ => {
Ok(Some(KeyEvent::new(
Self::map_scancode(code)?,
KeyState::Down,
)))
}
}
}
DecodeState::Extended => {
*state = DecodeState::Start;
match code {
0x80..=0xFF => {
Ok(Some(KeyEvent::new(
Self::map_extended_scancode(code - 0x80)?,
KeyState::Up,
)))
}
_ => {
Ok(Some(KeyEvent::new(
Self::map_extended_scancode(code)?,
KeyState::Down,
)))
}
}
}
_ => {
unimplemented!();
}
}
}
fn map_scancode(code: u8) -> Result<KeyCode, Error> {
match code {
0x01 => Ok(KeyCode::Escape),
0x02 => Ok(KeyCode::Key1),
0x03 => Ok(KeyCode::Key2),
0x04 => Ok(KeyCode::Key3),
0x05 => Ok(KeyCode::Key4),
0x06 => Ok(KeyCode::Key5),
0x07 => Ok(KeyCode::Key6),
0x08 => Ok(KeyCode::Key7),
0x09 => Ok(KeyCode::Key8),
0x0A => Ok(KeyCode::Key9),
0x0B => Ok(KeyCode::Key0),
0x0C => Ok(KeyCode::Minus),
0x0D => Ok(KeyCode::Equals),
0x0E => Ok(KeyCode::Backspace),
0x0F => Ok(KeyCode::Tab),
0x10 => Ok(KeyCode::Q),
0x11 => Ok(KeyCode::W),
0x12 => Ok(KeyCode::E),
0x13 => Ok(KeyCode::R),
0x14 => Ok(KeyCode::T),
0x15 => Ok(KeyCode::Y),
0x16 => Ok(KeyCode::U),
0x17 => Ok(KeyCode::I),
0x18 => Ok(KeyCode::O),
0x19 => Ok(KeyCode::P),
0x1A => Ok(KeyCode::BracketSquareLeft),
0x1B => Ok(KeyCode::BracketSquareRight),
0x1C => Ok(KeyCode::Enter),
0x1D => Ok(KeyCode::ControlLeft),
0x1E => Ok(KeyCode::A),
0x1F => Ok(KeyCode::S),
0x20 => Ok(KeyCode::D),
0x21 => Ok(KeyCode::F),
0x22 => Ok(KeyCode::G),
0x23 => Ok(KeyCode::H),
0x24 => Ok(KeyCode::J),
0x25 => Ok(KeyCode::K),
0x26 => Ok(KeyCode::L),
0x27 => Ok(KeyCode::SemiColon),
0x28 => Ok(KeyCode::Quote),
0x29 => Ok(KeyCode::BackTick),
0x2A => Ok(KeyCode::ShiftLeft),
0x2B => Ok(KeyCode::BackSlash),
0x2C => Ok(KeyCode::Z),
0x2D => Ok(KeyCode::X),
0x2E => Ok(KeyCode::C),
0x2F => Ok(KeyCode::V),
0x30 => Ok(KeyCode::B),
0x31 => Ok(KeyCode::N),
0x32 => Ok(KeyCode::M),
0x33 => Ok(KeyCode::Comma),
0x34 => Ok(KeyCode::Fullstop),
0x35 => Ok(KeyCode::Slash),
0x36 => Ok(KeyCode::ShiftRight),
0x37 => Ok(KeyCode::NumpadStar),
0x38 => Ok(KeyCode::AltLeft),
0x39 => Ok(KeyCode::Spacebar),
0x3A => Ok(KeyCode::CapsLock),
0x3B => Ok(KeyCode::F1),
0x3C => Ok(KeyCode::F2),
0x3D => Ok(KeyCode::F3),
0x3E => Ok(KeyCode::F4),
0x3F => Ok(KeyCode::F5),
0x40 => Ok(KeyCode::F6),
0x41 => Ok(KeyCode::F7),
0x42 => Ok(KeyCode::F8),
0x43 => Ok(KeyCode::F9),
0x44 => Ok(KeyCode::F10),
0x45 => Ok(KeyCode::NumpadLock),
0x46 => Ok(KeyCode::ScrollLock),
0x47 => Ok(KeyCode::Numpad7),
0x48 => Ok(KeyCode::Numpad8),
0x49 => Ok(KeyCode::Numpad9),
0x4A => Ok(KeyCode::NumpadMinus),
0x4B => Ok(KeyCode::Numpad4),
0x4C => Ok(KeyCode::Numpad5),
0x4D => Ok(KeyCode::Numpad6),
0x4E => Ok(KeyCode::NumpadPlus),
0x4F => Ok(KeyCode::Numpad1),
0x50 => Ok(KeyCode::Numpad2),
0x51 => Ok(KeyCode::Numpad3),
0x52 => Ok(KeyCode::Numpad0),
0x53 => Ok(KeyCode::NumpadPeriod),
0x57 => Ok(KeyCode::F11),
0x58 => Ok(KeyCode::F12),
0x81..=0xD8 => Ok(Self::map_scancode(code - 0x80)?),
_ => Err(Error::UnknownKeyCode),
}
}
fn map_extended_scancode(code: u8) -> Result<KeyCode, Error> {
match code {
0x10 => Ok(KeyCode::PrevTrack),
0x19 => Ok(KeyCode::NextTrack),
0x1C => Ok(KeyCode::NumpadEnter),
0x1D => Ok(KeyCode::ControlRight),
0x20 => Ok(KeyCode::Mute),
0x21 => Ok(KeyCode::Calculator),
0x22 => Ok(KeyCode::Play),
0x24 => Ok(KeyCode::Stop),
0x2E => Ok(KeyCode::VolumeDown),
0x30 => Ok(KeyCode::VolumeUp),
0x32 => Ok(KeyCode::WWWHome),
0x35 => Ok(KeyCode::NumpadSlash),
0x38 => Ok(KeyCode::AltRight),
0x47 => Ok(KeyCode::Home),
0x48 => Ok(KeyCode::ArrowUp),
0x49 => Ok(KeyCode::PageUp),
0x4B => Ok(KeyCode::ArrowLeft),
0x4D => Ok(KeyCode::ArrowRight),
0x4F => Ok(KeyCode::End),
0x50 => Ok(KeyCode::ArrowDown),
0x51 => Ok(KeyCode::PageDown),
0x52 => Ok(KeyCode::Insert),
0x53 => Ok(KeyCode::Delete),
0x90..=0xED => Ok(Self::map_extended_scancode(code - 0x80)?),
_ => Err(Error::UnknownKeyCode),
}
}
}
pub struct ScancodeSet2;
impl ScancodeSet for ScancodeSet2 {
fn advance_state(state: &mut DecodeState, code: u8) -> Result<Option<KeyEvent>, Error> {
match *state {
DecodeState::Start => match code {
EXTENDED_KEY_CODE => {
*state = DecodeState::Extended;
Ok(None)
}
KEY_RELEASE_CODE => {
*state = DecodeState::Release;
Ok(None)
}
_ => Ok(Some(KeyEvent::new(
Self::map_scancode(code)?,
KeyState::Down,
))),
},
DecodeState::Release => {
*state = DecodeState::Start;
Ok(Some(KeyEvent::new(Self::map_scancode(code)?, KeyState::Up)))
}
DecodeState::Extended => match code {
KEY_RELEASE_CODE => {
*state = DecodeState::ExtendedRelease;
Ok(None)
}
_ => {
*state = DecodeState::Start;
Ok(Some(KeyEvent::new(
Self::map_extended_scancode(code)?,
KeyState::Down,
)))
}
},
DecodeState::ExtendedRelease => {
*state = DecodeState::Start;
Ok(Some(KeyEvent::new(
Self::map_extended_scancode(code)?,
KeyState::Up,
)))
}
}
}
fn map_scancode(code: u8) -> Result<KeyCode, Error> {
match code {
0x01 => Ok(KeyCode::F9),
0x03 => Ok(KeyCode::F5),
0x04 => Ok(KeyCode::F3),
0x05 => Ok(KeyCode::F1),
0x06 => Ok(KeyCode::F2),
0x07 => Ok(KeyCode::F12),
0x09 => Ok(KeyCode::F10),
0x0A => Ok(KeyCode::F8),
0x0B => Ok(KeyCode::F6),
0x0C => Ok(KeyCode::F4),
0x0D => Ok(KeyCode::Tab),
0x0E => Ok(KeyCode::BackTick),
0x11 => Ok(KeyCode::AltLeft),
0x12 => Ok(KeyCode::ShiftLeft),
0x14 => Ok(KeyCode::ControlLeft),
0x15 => Ok(KeyCode::Q),
0x16 => Ok(KeyCode::Key1),
0x1A => Ok(KeyCode::Z),
0x1B => Ok(KeyCode::S),
0x1C => Ok(KeyCode::A),
0x1D => Ok(KeyCode::W),
0x1e => Ok(KeyCode::Key2),
0x21 => Ok(KeyCode::C),
0x22 => Ok(KeyCode::X),
0x23 => Ok(KeyCode::D),
0x24 => Ok(KeyCode::E),
0x25 => Ok(KeyCode::Key4),
0x26 => Ok(KeyCode::Key3),
0x29 => Ok(KeyCode::Spacebar),
0x2A => Ok(KeyCode::V),
0x2B => Ok(KeyCode::F),
0x2C => Ok(KeyCode::T),
0x2D => Ok(KeyCode::R),
0x2E => Ok(KeyCode::Key5),
0x31 => Ok(KeyCode::N),
0x32 => Ok(KeyCode::B),
0x33 => Ok(KeyCode::H),
0x34 => Ok(KeyCode::G),
0x35 => Ok(KeyCode::Y),
0x36 => Ok(KeyCode::Key6),
0x3A => Ok(KeyCode::M),
0x3B => Ok(KeyCode::J),
0x3C => Ok(KeyCode::U),
0x3D => Ok(KeyCode::Key7),
0x3E => Ok(KeyCode::Key8),
0x41 => Ok(KeyCode::Comma),
0x42 => Ok(KeyCode::K),
0x43 => Ok(KeyCode::I),
0x44 => Ok(KeyCode::O),
0x45 => Ok(KeyCode::Key0),
0x46 => Ok(KeyCode::Key9),
0x49 => Ok(KeyCode::Fullstop),
0x4A => Ok(KeyCode::Slash),
0x4B => Ok(KeyCode::L),
0x4C => Ok(KeyCode::SemiColon),
0x4D => Ok(KeyCode::P),
0x4E => Ok(KeyCode::Minus),
0x52 => Ok(KeyCode::Quote),
0x54 => Ok(KeyCode::BracketSquareLeft),
0x55 => Ok(KeyCode::Equals),
0x58 => Ok(KeyCode::CapsLock),
0x59 => Ok(KeyCode::ShiftRight),
0x5A => Ok(KeyCode::Enter),
0x5B => Ok(KeyCode::BracketSquareRight),
0x5D => Ok(KeyCode::HashTilde),
0x61 => Ok(KeyCode::BackSlash),
0x66 => Ok(KeyCode::Backspace),
0x69 => Ok(KeyCode::Numpad1),
0x6B => Ok(KeyCode::Numpad4),
0x6C => Ok(KeyCode::Numpad7),
0x70 => Ok(KeyCode::Numpad0),
0x71 => Ok(KeyCode::NumpadPeriod),
0x72 => Ok(KeyCode::Numpad2),
0x73 => Ok(KeyCode::Numpad5),
0x74 => Ok(KeyCode::Numpad6),
0x75 => Ok(KeyCode::Numpad8),
0x76 => Ok(KeyCode::Escape),
0x77 => Ok(KeyCode::NumpadLock),
0x78 => Ok(KeyCode::F11),
0x79 => Ok(KeyCode::NumpadPlus),
0x7A => Ok(KeyCode::Numpad3),
0x7B => Ok(KeyCode::NumpadMinus),
0x7C => Ok(KeyCode::NumpadStar),
0x7D => Ok(KeyCode::Numpad9),
0x7E => Ok(KeyCode::ScrollLock),
0x83 => Ok(KeyCode::F7),
0xAA => Ok(KeyCode::PowerOnTestOk),
_ => Err(Error::UnknownKeyCode),
}
}
fn map_extended_scancode(code: u8) -> Result<KeyCode, Error> {
match code {
0x11 => Ok(KeyCode::AltRight),
0x14 => Ok(KeyCode::ControlRight),
0x1F => Ok(KeyCode::WindowsLeft),
0x27 => Ok(KeyCode::WindowsRight),
0x2F => Ok(KeyCode::Menus),
0x4A => Ok(KeyCode::NumpadSlash),
0x5A => Ok(KeyCode::NumpadEnter),
0x69 => Ok(KeyCode::End),
0x6B => Ok(KeyCode::ArrowLeft),
0x6C => Ok(KeyCode::Home),
0x70 => Ok(KeyCode::Insert),
0x71 => Ok(KeyCode::Delete),
0x72 => Ok(KeyCode::ArrowDown),
0x74 => Ok(KeyCode::ArrowRight),
0x75 => Ok(KeyCode::ArrowUp),
0x7A => Ok(KeyCode::PageDown),
0x7D => Ok(KeyCode::PageUp),
_ => Err(Error::UnknownKeyCode),
}
}
}