Report the key that was typed, not the one before Shift
`+` and `*` did nothing useful: iced's `key` is the logical key before modifiers, so on a US layout Shift+'=' arrives as "=" and Shift+'8' as "8". The calculator dutifully did equals and typed an 8. Every unshifted key worked, which is what made it look like those two were unmapped. `modified_key` is what the user actually typed; `key` is still the fallback for named keys, which is where it is right. ABI_VERSION stays 6: no export or signature changed, only behaviour, so bindings built against 0.6.0 still match. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2460321 parent: 1b15fda modified
cosmic_ffi/Cargo.lock +1 -1 | @@ -964,7 +964,7 @@ dependencies = [ | ||
| 964 | 964 | |
| 965 | 965 | [[package]] |
| 966 | 966 | name = "cosmic_ffi" |
| 967 | -version = "0.6.0" | |
| 967 | +version = "0.7.0" | |
| 968 | 968 | dependencies = [ |
| 969 | 969 | "libcosmic", |
| 970 | 970 | ] |
| @@ -964,7 +964,7 @@ dependencies = [ | |||
| 964 | 964 | ||
| 965 | [[package]] | 965 | [[package]] |
| 966 | name = "cosmic_ffi" | 966 | name = "cosmic_ffi" |
| 967 | -version = "0.6.0" | 967 | +version = "0.7.0" |
| 968 | dependencies = [ | 968 | dependencies = [ |
| 969 | "libcosmic", | 969 | "libcosmic", |
| 970 | ] | 970 | ] |
modified
cosmic_ffi/Cargo.toml +1 -1 | @@ -1,6 +1,6 @@ | ||
| 1 | 1 | [package] |
| 2 | 2 | name = "cosmic_ffi" |
| 3 | -version = "0.6.0" | |
| 3 | +version = "0.7.0" | |
| 4 | 4 | edition = "2021" |
| 5 | 5 | |
| 6 | 6 | [lib] |
| @@ -1,6 +1,6 @@ | |||
| 1 | [package] | 1 | [package] |
| 2 | name = "cosmic_ffi" | 2 | name = "cosmic_ffi" |
| 3 | -version = "0.6.0" | 3 | +version = "0.7.0" |
| 4 | edition = "2021" | 4 | edition = "2021" |
| 5 | 5 | ||
| 6 | [lib] | 6 | [lib] |
modified
cosmic_ffi/src/lib.rs +14 -3 | @@ -461,16 +461,27 @@ impl cosmic::Application for App { | ||
| 461 | 461 | fn subscription(&self) -> cosmic::iced::Subscription<Message> { |
| 462 | 462 | use cosmic::iced::{event, keyboard, Event}; |
| 463 | 463 | event::listen_with(|event, _status, _window| { |
| 464 | - let Event::Keyboard(keyboard::Event::KeyPressed { key, .. }) = event else { | |
| 464 | + let Event::Keyboard(keyboard::Event::KeyPressed { | |
| 465 | + key, modified_key, .. | |
| 466 | + }) = event | |
| 467 | + else { | |
| 465 | 468 | return None; |
| 466 | 469 | }; |
| 467 | - let name = match key { | |
| 470 | + // `key` is the key before modifiers, so on a US layout Shift+'=' | |
| 471 | + // arrives as "=" and Shift+'8' as "8" — the host would see equals | |
| 472 | + // and a digit instead of plus and times. `modified_key` is what | |
| 473 | + // was actually typed; fall back only when it says nothing. | |
| 474 | + let typed = match modified_key { | |
| 475 | + keyboard::Key::Character(c) => Some(c.to_string()), | |
| 476 | + _ => None, | |
| 477 | + }; | |
| 478 | + let name = typed.unwrap_or_else(|| match key { | |
| 468 | 479 | keyboard::Key::Character(c) => c.to_string(), |
| 469 | 480 | // Debug gives the variant name, which is exactly the spelling |
| 470 | 481 | // a host wants to match on: "Enter", "Backspace", "ArrowUp". |
| 471 | 482 | keyboard::Key::Named(named) => format!("{named:?}"), |
| 472 | 483 | _ => String::new(), |
| 473 | - }; | |
| 484 | + }); | |
| 474 | 485 | (!name.is_empty()).then_some(Message::Key(name)) |
| 475 | 486 | }) |
| 476 | 487 | } |
| @@ -461,16 +461,27 @@ impl cosmic::Application for App { | |||
| 461 | fn subscription(&self) -> cosmic::iced::Subscription<Message> { | 461 | fn subscription(&self) -> cosmic::iced::Subscription<Message> { |
| 462 | use cosmic::iced::{event, keyboard, Event}; | 462 | use cosmic::iced::{event, keyboard, Event}; |
| 463 | event::listen_with(|event, _status, _window| { | 463 | event::listen_with(|event, _status, _window| { |
| 464 | - let Event::Keyboard(keyboard::Event::KeyPressed { key, .. }) = event else { | 464 | + let Event::Keyboard(keyboard::Event::KeyPressed { |
| 465 | + key, modified_key, .. | ||
| 466 | + }) = event | ||
| 467 | + else { | ||
| 465 | return None; | 468 | return None; |
| 466 | }; | 469 | }; |
| 467 | - let name = match key { | 470 | + // `key` is the key before modifiers, so on a US layout Shift+'=' |
| 471 | + // arrives as "=" and Shift+'8' as "8" — the host would see equals | ||
| 472 | + // and a digit instead of plus and times. `modified_key` is what | ||
| 473 | + // was actually typed; fall back only when it says nothing. | ||
| 474 | + let typed = match modified_key { | ||
| 475 | + keyboard::Key::Character(c) => Some(c.to_string()), | ||
| 476 | + _ => None, | ||
| 477 | + }; | ||
| 478 | + let name = typed.unwrap_or_else(|| match key { | ||
| 468 | keyboard::Key::Character(c) => c.to_string(), | 479 | keyboard::Key::Character(c) => c.to_string(), |
| 469 | // Debug gives the variant name, which is exactly the spelling | 480 | // Debug gives the variant name, which is exactly the spelling |
| 470 | // a host wants to match on: "Enter", "Backspace", "ArrowUp". | 481 | // a host wants to match on: "Enter", "Backspace", "ArrowUp". |
| 471 | keyboard::Key::Named(named) => format!("{named:?}"), | 482 | keyboard::Key::Named(named) => format!("{named:?}"), |
| 472 | _ => String::new(), | 483 | _ => String::new(), |
| 473 | - }; | 484 | + }); |
| 474 | (!name.is_empty()).then_some(Message::Key(name)) | 485 | (!name.is_empty()).then_some(Message::Key(name)) |
| 475 | }) | 486 | }) |
| 476 | } | 487 | } |
modified
cosmicnim.nimble +1 -1 | @@ -1,4 +1,4 @@ | ||
| 1 | -version = "0.6.0" | |
| 1 | +version = "0.7.0" | |
| 2 | 2 | author = "nandi" |
| 3 | 3 | description = "libcosmic behind a C ABI, driven from Nim" |
| 4 | 4 | license = "MIT" |
| @@ -1,4 +1,4 @@ | |||
| 1 | -version = "0.6.0" | 1 | +version = "0.7.0" |
| 2 | author = "nandi" | 2 | author = "nandi" |
| 3 | description = "libcosmic behind a C ABI, driven from Nim" | 3 | description = "libcosmic behind a C ABI, driven from Nim" |
| 4 | license = "MIT" | 4 | license = "MIT" |