by Michael S. Kaplan, published on 2005/12/01 00:01 -08:00, original URI: http://blogs.msdn.com/michkap/archive/2005/12/01/498775.aspx
It was just yesterday when someone sent the following question to various people inside of Microsoft:
We have a small problem regarding the correct VK representation of the semicolon. Under the standard US KB the virtual key is VK_OEM_1 (0xba) but this may not be true for other languages. I suggested to simply use the ASCII char key (0x3b) for semicolon for all other case but I’m not that sure about it.
The use is very straightforward.
We handle the WM_KEYDOWN message in some point and want to catch the semicolon key press.
Simply check the message wParam (wParam == ‘;’) doesn’t work.
The reason is that the char ‘;’ is not sent within the wParam and instead what is sent is VK_OEM_1.
This is fine, but according the MSDN the code VK_OEM_1 works only for US standard KB.
So what is going to happen under different keyboards layout and/or other languages settings?
Which VK should we use to catch the semicolon?
Since I found no other choices, I simply trap for both VK_OEM_1 and the char ‘;’ but that might be an incomplete solution.
Do you have any idea what the correct code might be?
The answer of course is that there is no one code for the semicolon that spans all of the keyboard layouts.
But I do not blame people for the misunderstanding, at all.
It was over a year ago that I listed out Some Keyboarding Terms, in particular:
If you look at the red text in the VK definition, it hints at the problem that causes the confusion.
I mean, since there is a VK_A that represents the letter A, why wouldn't we expect there to be a VK_SEMICIOLON to represent the semicolon, right?
Of course, there are lots of problems with such a model. For example, that semicolon key is also a colon key. Who would win the contest?
And since not every keyboard pairs up the same characters in the various shift states, how would you find the character that was not used for the name?
The real problem is that when a WNDPROC receives a WM_KEYDOWN message with the virtual key VK_OEM1, it has not received a semicolon. At all. It has received notification that a parrticular key was pressed, and nothing else. When it receives a VK_A, there is no difference; it is a notification that a key has been pressed. Now the keyboard layout has been asked what is the virtual key, but it has not yet been asked what is the character (and it quite possibly may never be asked).
If that WNDPROC passes the message to the DefWindowProcIf you call the TranslateMessage function, then the keyboard will be asked what is the character based on all of the information about the current keyboard buffer and the shift state, and a subsequent WM_CHAR message will be sent, which will contain the ";" or the "A" or whatever.
The fact that the values for VK_A through VK_Z are identical to the code points for the letters A - Z is an unfortunate accident since it raises such unrealistic expectations for other characters....
In the end, we are left with two possible options to solve the original problem:
This post brought to you by ";" (U+003b, a.k.a. SEMICOLON)
# orcmid on Thursday, December 01, 2005 10:36 AM:
# Mike Dimmick on Thursday, December 01, 2005 2:35 PM:
# Michael S. Kaplan on Thursday, December 01, 2005 3:30 PM:
referenced by
2006/07/13 IME + .NET = Input Madness Editor?