diff --git a/Cargo.toml b/Cargo.toml index 907f452bb..48ddad8d6 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -42,7 +42,7 @@ required-features = ["render"] bevy = { version = "0.13", default-features = false, features = [ "bevy_asset", ] } -egui = { version = "0.24.0", default-features = false, features = ["bytemuck"] } +egui = { version = "0.26", default-features = false, features = ["bytemuck"] } webbrowser = { version = "0.8.2", optional = true } [target.'cfg(not(any(target_arch = "wasm32", target_os = "android")))'.dependencies] diff --git a/src/systems.rs b/src/systems.rs index 145e04a47..6dd1c7615 100644 --- a/src/systems.rs +++ b/src/systems.rs @@ -9,7 +9,7 @@ use bevy::{ system::{Local, Res, ResMut, SystemParam}, }, input::{ - keyboard::{Key, KeyboardInput}, + keyboard::{Key, KeyCode, KeyboardInput}, mouse::{MouseButton, MouseButtonInput, MouseScrollUnit, MouseWheel}, touch::TouchInput, ButtonState, @@ -275,12 +275,16 @@ pub fn process_input_system( }) { for ev in keyboard_input_events { - if let Some(key) = bevy_to_egui_key(&ev.logical_key) { + if let (Some(key), physical_key) = ( + bevy_to_egui_key(&ev.logical_key), + bevy_to_egui_physical_key(&ev.key_code), + ) { let egui_event = egui::Event::Key { key, pressed: ev.state.is_pressed(), repeat: false, modifiers, + physical_key, }; focused_input.events.push(egui_event); @@ -551,62 +555,150 @@ fn egui_to_winit_cursor_icon(cursor_icon: egui::CursorIcon) -> Option Option { +/// Matches the implementation of https://github.com/emilk/egui/blob/68b3ef7f6badfe893d3bbb1f791b481069d807d9/crates/egui-winit/src/lib.rs#L1005. +pub fn bevy_to_egui_key(key: &Key) -> Option { let key = match key { + Key::Character(str) => return egui::Key::from_name(str.as_str()), + Key::Unidentified(_) | Key::Dead(_) => return None, + + Key::Enter => egui::Key::Enter, + Key::Tab => egui::Key::Tab, + Key::Space => egui::Key::Space, Key::ArrowDown => egui::Key::ArrowDown, Key::ArrowLeft => egui::Key::ArrowLeft, Key::ArrowRight => egui::Key::ArrowRight, Key::ArrowUp => egui::Key::ArrowUp, - Key::Escape => egui::Key::Escape, - Key::Tab => egui::Key::Tab, - Key::Backspace => egui::Key::Backspace, - Key::Enter => egui::Key::Enter, - Key::Space => egui::Key::Space, - Key::Insert => egui::Key::Insert, - Key::Delete => egui::Key::Delete, - Key::Home => egui::Key::Home, Key::End => egui::Key::End, - Key::PageUp => egui::Key::PageUp, + Key::Home => egui::Key::Home, Key::PageDown => egui::Key::PageDown, - Key::Character(c) => match c.to_string().to_lowercase().as_str() { - "0" => egui::Key::Num0, - "1" => egui::Key::Num1, - "2" => egui::Key::Num2, - "3" => egui::Key::Num3, - "4" => egui::Key::Num4, - "5" => egui::Key::Num5, - "6" => egui::Key::Num6, - "7" => egui::Key::Num7, - "8" => egui::Key::Num8, - "9" => egui::Key::Num9, - "a" => egui::Key::A, - "b" => egui::Key::B, - "c" => egui::Key::C, - "d" => egui::Key::D, - "e" => egui::Key::E, - "f" => egui::Key::F, - "g" => egui::Key::G, - "h" => egui::Key::H, - "i" => egui::Key::I, - "j" => egui::Key::J, - "k" => egui::Key::K, - "l" => egui::Key::L, - "m" => egui::Key::M, - "n" => egui::Key::N, - "o" => egui::Key::O, - "p" => egui::Key::P, - "q" => egui::Key::Q, - "r" => egui::Key::R, - "s" => egui::Key::S, - "t" => egui::Key::T, - "u" => egui::Key::U, - "v" => egui::Key::V, - "w" => egui::Key::W, - "x" => egui::Key::X, - "y" => egui::Key::Y, - "z" => egui::Key::Z, - _ => return None, - }, + Key::PageUp => egui::Key::PageUp, + Key::Backspace => egui::Key::Backspace, + Key::Delete => egui::Key::Delete, + Key::Insert => egui::Key::Insert, + Key::Escape => egui::Key::Escape, + Key::F1 => egui::Key::F1, + Key::F2 => egui::Key::F2, + Key::F3 => egui::Key::F3, + Key::F4 => egui::Key::F4, + Key::F5 => egui::Key::F5, + Key::F6 => egui::Key::F6, + Key::F7 => egui::Key::F7, + Key::F8 => egui::Key::F8, + Key::F9 => egui::Key::F9, + Key::F10 => egui::Key::F10, + Key::F11 => egui::Key::F11, + Key::F12 => egui::Key::F12, + Key::F13 => egui::Key::F13, + Key::F14 => egui::Key::F14, + Key::F15 => egui::Key::F15, + Key::F16 => egui::Key::F16, + Key::F17 => egui::Key::F17, + Key::F18 => egui::Key::F18, + Key::F19 => egui::Key::F19, + Key::F20 => egui::Key::F20, + + _ => return None, + }; + Some(key) +} + +/// Matches the implementation of https://github.com/emilk/egui/blob/68b3ef7f6badfe893d3bbb1f791b481069d807d9/crates/egui-winit/src/lib.rs#L1080. +fn bevy_to_egui_physical_key(key: &KeyCode) -> Option { + let key = match key { + KeyCode::ArrowDown => egui::Key::ArrowDown, + KeyCode::ArrowLeft => egui::Key::ArrowLeft, + KeyCode::ArrowRight => egui::Key::ArrowRight, + KeyCode::ArrowUp => egui::Key::ArrowUp, + + KeyCode::Escape => egui::Key::Escape, + KeyCode::Tab => egui::Key::Tab, + KeyCode::Backspace => egui::Key::Backspace, + KeyCode::Enter | KeyCode::NumpadEnter => egui::Key::Enter, + + KeyCode::Insert => egui::Key::Insert, + KeyCode::Delete => egui::Key::Delete, + KeyCode::Home => egui::Key::Home, + KeyCode::End => egui::Key::End, + KeyCode::PageUp => egui::Key::PageUp, + KeyCode::PageDown => egui::Key::PageDown, + + // Punctuation + KeyCode::Space => egui::Key::Space, + KeyCode::Comma => egui::Key::Comma, + KeyCode::Period => egui::Key::Period, + // KeyCode::Colon => egui::Key::Colon, // NOTE: there is no physical colon key on an american keyboard + KeyCode::Semicolon => egui::Key::Semicolon, + KeyCode::Backslash => egui::Key::Backslash, + KeyCode::Slash | KeyCode::NumpadDivide => egui::Key::Slash, + KeyCode::BracketLeft => egui::Key::OpenBracket, + KeyCode::BracketRight => egui::Key::CloseBracket, + KeyCode::Backquote => egui::Key::Backtick, + + KeyCode::Cut => egui::Key::Cut, + KeyCode::Copy => egui::Key::Copy, + KeyCode::Paste => egui::Key::Paste, + KeyCode::Minus | KeyCode::NumpadSubtract => egui::Key::Minus, + KeyCode::NumpadAdd => egui::Key::Plus, + KeyCode::Equal => egui::Key::Equals, + + KeyCode::Digit0 | KeyCode::Numpad0 => egui::Key::Num0, + KeyCode::Digit1 | KeyCode::Numpad1 => egui::Key::Num1, + KeyCode::Digit2 | KeyCode::Numpad2 => egui::Key::Num2, + KeyCode::Digit3 | KeyCode::Numpad3 => egui::Key::Num3, + KeyCode::Digit4 | KeyCode::Numpad4 => egui::Key::Num4, + KeyCode::Digit5 | KeyCode::Numpad5 => egui::Key::Num5, + KeyCode::Digit6 | KeyCode::Numpad6 => egui::Key::Num6, + KeyCode::Digit7 | KeyCode::Numpad7 => egui::Key::Num7, + KeyCode::Digit8 | KeyCode::Numpad8 => egui::Key::Num8, + KeyCode::Digit9 | KeyCode::Numpad9 => egui::Key::Num9, + + KeyCode::KeyA => egui::Key::A, + KeyCode::KeyB => egui::Key::B, + KeyCode::KeyC => egui::Key::C, + KeyCode::KeyD => egui::Key::D, + KeyCode::KeyE => egui::Key::E, + KeyCode::KeyF => egui::Key::F, + KeyCode::KeyG => egui::Key::G, + KeyCode::KeyH => egui::Key::H, + KeyCode::KeyI => egui::Key::I, + KeyCode::KeyJ => egui::Key::J, + KeyCode::KeyK => egui::Key::K, + KeyCode::KeyL => egui::Key::L, + KeyCode::KeyM => egui::Key::M, + KeyCode::KeyN => egui::Key::N, + KeyCode::KeyO => egui::Key::O, + KeyCode::KeyP => egui::Key::P, + KeyCode::KeyQ => egui::Key::Q, + KeyCode::KeyR => egui::Key::R, + KeyCode::KeyS => egui::Key::S, + KeyCode::KeyT => egui::Key::T, + KeyCode::KeyU => egui::Key::U, + KeyCode::KeyV => egui::Key::V, + KeyCode::KeyW => egui::Key::W, + KeyCode::KeyX => egui::Key::X, + KeyCode::KeyY => egui::Key::Y, + KeyCode::KeyZ => egui::Key::Z, + + KeyCode::F1 => egui::Key::F1, + KeyCode::F2 => egui::Key::F2, + KeyCode::F3 => egui::Key::F3, + KeyCode::F4 => egui::Key::F4, + KeyCode::F5 => egui::Key::F5, + KeyCode::F6 => egui::Key::F6, + KeyCode::F7 => egui::Key::F7, + KeyCode::F8 => egui::Key::F8, + KeyCode::F9 => egui::Key::F9, + KeyCode::F10 => egui::Key::F10, + KeyCode::F11 => egui::Key::F11, + KeyCode::F12 => egui::Key::F12, + KeyCode::F13 => egui::Key::F13, + KeyCode::F14 => egui::Key::F14, + KeyCode::F15 => egui::Key::F15, + KeyCode::F16 => egui::Key::F16, + KeyCode::F17 => egui::Key::F17, + KeyCode::F18 => egui::Key::F18, + KeyCode::F19 => egui::Key::F19, + KeyCode::F20 => egui::Key::F20, _ => return None, }; Some(key)