New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
win32 encoding: fix more inconsistencies #2235
Conversation
I'm not opposed to adding something like a wezterm/wezterm-input-types/src/lib.rs Lines 1076 to 1078 in d7fa541
to hold what we get from However!
|
The last commits are my shot at implementing this. Some notes:
All in all, these changes make the win32 encoding a lot more accurate. There's still a few differences, mainly regarding dead key handling, but I'm not sure fixing those is worth the effort. |
This field is populated by calling ToUnicode with an unmodified keystate. It will be used to fix edge cases in the win32 keyboard encoding in an upcoming commit.
This allows us to remove a lot of manual edge case handling and fixes multiple encoding bugs.
Shift normalization removes the shift modifier from an event. This modifier still needs to be encoded when using win32 keyboard encoding. Luckily we can fall back on using the individual left and right shift modifiers, since the win32 keyboard encoding doesn't distinguish those.
This lets both keys be encoded with the win32 keyboard encoding if an invalid dead key combination is pressed. Before this change, the first key was always sent with normal terminal encoding. This change also works around a race condition that would frequently occur when using win32 encoding where the first key of an invalid combination would appear after the second. Furthermore, pressing any two dead keys will now immediately emit both of them. This is the same behaviour as in conhost.
This pulls in almost all of the original PR in #2235. I skipped a dead key case that I recall being tricky: I didn't want to break the non win32-input mode version of that. I'd be happy to have that case re-evaluated in a smaller PR where we can focus on its details. Co-authored-by: Dominik Kreutzer <kreudom@gmail.com>
Thanks for your patience with this; I manually merged this, except for one dead key case that I recall as being important for the non-win32 input mode. We can follow up on that in a separate PR if that still causes problems! |
While looking into #2196 I was able to find some more inconsistencies in the win32 encoding. I discovered the following differences:
CTRL + ALT + key
combinations should be sent with the same character code that would be generated byAltGr + key
, i.e. either\x00
or a character depending on the current layout. I fixed the first case for now, which should fix win32 input mode: not processing Ctrl + Alt keyboard combinations properly #2196 in most cases.AltGr + key
should be sent with character code\x00
like above if that combination has no associated character. Right now wezterm falls back on the character code ofkey
.SHIFT + ascii_letter
sends the correct character, but misses the SHIFT flag. This is caused by thenormalize_shift
function. I don't know if this is intentional behaviour for non-windows systems, so I didn't want to change that for now.Raw test data here
While we could try to implement all these different cases, I did some testing and realized the
ToUnicode
function would actually return the correct character in all these cases if the control keys weren't manually removed from the key set before, as it currently happens here:wezterm/window/src/os/windows/window.rs
Lines 2143 to 2153 in d5060ec
However, this would change the KeyEvents wezterm generates, possibly breaking existing configurations and keyboard encoding for
allow_win32_input_mode = false
.One possible idea would be to add a new optional field to the KeyEvent structure which is only used when using the win32 encoding. What's your opinion on all this?