use keyboard_codes::{
current_platform, parse_shortcut_with_aliases, Key, KeyCodeMapper, Modifier, Platform, Shortcut,
};
use std::collections::HashMap;
#[derive(Debug, Clone, Copy, PartialEq)]
enum AppCommand {
NewFile,
OpenFile,
Save,
SaveAs,
CloseTab,
Undo,
Redo,
Cut,
Copy,
Paste,
SelectAll,
Find,
Replace,
Quit,
Preferences,
}
struct ShortcutManager {
platform: Platform,
shortcuts: HashMap<Shortcut, AppCommand>,
}
impl ShortcutManager {
fn new(platform: Platform) -> Self {
let mut shortcuts = HashMap::new();
Self::add_shortcut(&mut shortcuts, "ctrl+n", AppCommand::NewFile);
Self::add_shortcut(&mut shortcuts, "ctrl+o", AppCommand::OpenFile);
Self::add_shortcut(&mut shortcuts, "ctrl+s", AppCommand::Save);
Self::add_shortcut(&mut shortcuts, "ctrl+shift+s", AppCommand::SaveAs);
Self::add_shortcut(&mut shortcuts, "ctrl+w", AppCommand::CloseTab);
Self::add_shortcut(&mut shortcuts, "ctrl+z", AppCommand::Undo);
Self::add_shortcut(&mut shortcuts, "ctrl+y", AppCommand::Redo);
Self::add_shortcut(&mut shortcuts, "ctrl+x", AppCommand::Cut);
Self::add_shortcut(&mut shortcuts, "ctrl+c", AppCommand::Copy);
Self::add_shortcut(&mut shortcuts, "ctrl+v", AppCommand::Paste);
Self::add_shortcut(&mut shortcuts, "ctrl+a", AppCommand::SelectAll);
Self::add_shortcut(&mut shortcuts, "ctrl+f", AppCommand::Find);
Self::add_shortcut(&mut shortcuts, "ctrl+h", AppCommand::Replace);
if platform == Platform::MacOS {
Self::add_shortcut(&mut shortcuts, "cmd+q", AppCommand::Quit);
Self::add_shortcut(&mut shortcuts, "cmd+p", AppCommand::Preferences);
} else {
Self::add_shortcut(&mut shortcuts, "alt+f4", AppCommand::Quit);
Self::add_shortcut(&mut shortcuts, "ctrl+p", AppCommand::Preferences);
}
Self {
platform,
shortcuts,
}
}
fn add_shortcut(
shortcuts: &mut HashMap<Shortcut, AppCommand>,
input: &str,
command: AppCommand,
) {
match parse_shortcut_with_aliases(input) {
Ok(shortcut) => {
shortcuts.insert(shortcut, command);
}
Err(e) => {
eprintln!("警告: 无法解析快捷键 '{}': {}", input, e);
}
}
}
fn get_command(&self, modifier_vks: &[usize], key_vk: usize) -> Option<AppCommand> {
let modifiers: Vec<Modifier> = modifier_vks
.iter()
.filter_map(|&code| Modifier::from_code(code, self.platform))
.collect();
if let Some(key) = Key::from_code(key_vk, self.platform) {
let shortcut = Shortcut::new(modifiers, key);
return self.shortcuts.get(&shortcut).copied();
}
None
}
fn print_shortcut_reference(&self) {
println!("快捷键参考表:");
println!("{:-<40}", "");
let mut commands: Vec<(&Shortcut, &AppCommand)> = self.shortcuts.iter().collect();
commands.sort_by_key(|(_, cmd)| format!("{:?}", cmd));
for (shortcut, command) in commands {
println!(" {:20} -> {:?}", shortcut, command);
}
}
}
fn main() {
println!("=== GUI 应用快捷键系统示例 ===\n");
let platform = current_platform();
let shortcut_manager = ShortcutManager::new(platform);
shortcut_manager.print_shortcut_reference();
println!("\n模拟快捷键处理:");
let test_combinations = [
(vec![0x11], 0x53), (vec![0x11], 0x43), (vec![0x11, 0x10], 0x53), ];
for (modifiers, key) in test_combinations {
if let Some(command) = shortcut_manager.get_command(&modifiers, key) {
println!(" {:02X?} + {:02X} -> {:?}", modifiers, key, command);
} else {
println!(" {:02X?} + {:02X} -> 无匹配命令", modifiers, key);
}
}
}