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