@@ -39,6 +39,7 @@ impl KeyEventExtModifierSupplement for KeyEvent {
39
39
}
40
40
}
41
41
42
+ /// Ignores ALL modifiers.
42
43
pub fn get_modifierless_char ( scancode : u16 ) -> Key {
43
44
let mut string = [ 0 ; 16 ] ;
44
45
let input_source;
@@ -97,6 +98,7 @@ pub fn get_modifierless_char(scancode: u16) -> Key {
97
98
Key :: Character ( SmolStr :: new ( chars) )
98
99
}
99
100
101
+ // Ignores all modifiers except for SHIFT (yes, even ALT is ignored).
100
102
fn get_logical_key_char ( ns_event : & NSEvent , modifierless_chars : & str ) -> Key {
101
103
let string = ns_event
102
104
. charactersIgnoringModifiers ( )
@@ -126,6 +128,13 @@ pub(crate) fn create_key_event(
126
128
let mut physical_key =
127
129
key_override. unwrap_or_else ( || PhysicalKey :: from_scancode ( scancode as u32 ) ) ;
128
130
131
+ // NOTE: The logical key should heed both SHIFT and ALT if possible.
132
+ // For instance:
133
+ // * Pressing the A key: logical key should be "a"
134
+ // * Pressing SHIFT A: logical key should be "A"
135
+ // * Pressing CTRL SHIFT A: logical key should also be "A"
136
+ // This is not easy to tease out of `NSEvent`, but we do our best.
137
+
129
138
let text_with_all_modifiers: Option < SmolStr > = if key_override. is_some ( ) {
130
139
None
131
140
} else {
@@ -146,21 +155,29 @@ pub(crate) fn create_key_event(
146
155
147
156
let key_from_code = code_to_key ( physical_key, scancode) ;
148
157
let ( logical_key, key_without_modifiers) = if matches ! ( key_from_code, Key :: Unidentified ( _) ) {
158
+ // `get_modifierless_char/key_without_modifiers` ignores ALL modifiers.
149
159
let key_without_modifiers = get_modifierless_char ( scancode) ;
150
160
151
161
let modifiers = NSEvent :: modifierFlags ( ns_event) ;
152
162
let has_ctrl = modifiers. contains ( NSEventModifierFlags :: NSControlKeyMask ) ;
163
+ let has_cmd = modifiers. contains ( NSEventModifierFlags :: NSCommandKeyMask ) ;
153
164
154
165
let logical_key = match text_with_all_modifiers. as_ref ( ) {
155
- // Only checking for ctrl here, not checking for alt because we DO want to
166
+ // Only checking for ctrl and cmd here, not checking for alt because we DO want to
156
167
// include its effect in the key. For example if -on the Germay layout- one
157
168
// presses alt+8, the logical key should be "{"
158
169
// Also not checking if this is a release event because then this issue would
159
170
// still affect the key release.
160
- Some ( text) if !has_ctrl => Key :: Character ( text. clone ( ) ) ,
171
+ Some ( text) if !has_ctrl && !has_cmd => {
172
+ // Character heeding both SHIFT and ALT.
173
+ Key :: Character ( text. clone ( ) )
174
+ }
175
+
161
176
_ => match key_without_modifiers. as_ref ( ) {
177
+ // Character heeding just SHIFT, ignoring ALT.
162
178
Key :: Character ( ch) => get_logical_key_char ( ns_event, ch) ,
163
- // Don't try to get text for events which likely don't have it.
179
+
180
+ // Character ignoring ALL modifiers.
164
181
_ => key_without_modifiers. clone ( ) ,
165
182
} ,
166
183
} ;
0 commit comments