1 // Copyright 2019 The ChromiumOS Authors 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 mod data; 6 7 use std::collections::HashMap; 8 9 use data::MapEntry; 10 use data::KEYCODE_MAP; 11 12 /// Specifies which type of scancode to convert *from* in the KeycodeTranslator. 13 #[allow(dead_code)] 14 pub enum KeycodeTypes { 15 XkbScancode, 16 WindowsScancode, 17 MacScancode, 18 } 19 20 /// Translates scancodes of a particular type into Linux keycodes. 21 #[cfg_attr(windows, allow(dead_code))] 22 pub struct KeycodeTranslator { 23 keycode_map: HashMap<u32, MapEntry>, 24 } 25 26 #[cfg_attr(windows, allow(dead_code))] 27 impl KeycodeTranslator { 28 /// Create a new KeycodeTranslator that translates from the `from_type` type to Linux keycodes. new(from_type: KeycodeTypes) -> KeycodeTranslator29 pub fn new(from_type: KeycodeTypes) -> KeycodeTranslator { 30 let mut kcm: HashMap<u32, MapEntry> = HashMap::new(); 31 for entry in KEYCODE_MAP.iter() { 32 kcm.insert( 33 match from_type { 34 KeycodeTypes::XkbScancode => entry.xkb, 35 KeycodeTypes::WindowsScancode => entry.win, 36 KeycodeTypes::MacScancode => entry.mac, 37 }, 38 *entry, 39 ); 40 } 41 KeycodeTranslator { keycode_map: kcm } 42 } 43 44 /// Translates the scancode in `from_code` into a Linux keycode. translate(&self, from_code: u32) -> Option<u16>45 pub fn translate(&self, from_code: u32) -> Option<u16> { 46 Some(self.keycode_map.get(&from_code)?.linux_keycode) 47 } 48 } 49 50 #[cfg(test)] 51 mod tests { 52 use crate::keycode_converter::KeycodeTranslator; 53 use crate::keycode_converter::KeycodeTypes; 54 55 #[test] test_translate_win_lin()56 fn test_translate_win_lin() { 57 let translator = KeycodeTranslator::new(KeycodeTypes::WindowsScancode); 58 let translated_code = translator.translate(0x47); 59 assert!(translated_code.is_some()); 60 assert_eq!(translated_code.unwrap(), 71); 61 } 62 63 #[test] test_translate_missing_entry()64 fn test_translate_missing_entry() { 65 let translator = KeycodeTranslator::new(KeycodeTypes::WindowsScancode); 66 67 // No keycodes are this large. 68 let translated_code = translator.translate(0x9999999); 69 assert!(translated_code.is_none()); 70 } 71 } 72