views:

64

answers:

2

As an amateur to anything lower than VB/VBS (C++ WINAPI is a nightmare for someone of my experience) I have no idea how to go about constructing the long lParam for a simple KEYDOWN message in C++ and have probably spent more time looking for a decent explanation than is worth, would someone be able to describe exactly how to go about this?

It seems that almost every response to this question in other forums has been "why" or "use SendInput instead", without actually answering the question; I'm guessing that it's far too elementary for people to explain. Anyway here's the description from msdn, would very much appreciate a decent explanation or link to one, and a worked example if possible:

The repeat count, scan code, extended-key flag, context code, previous key-state flag, and transition-state flag, as shown...

0-15 The repeat count for the current message. The value is the number of times the keystroke is autorepeated as a result of the user holding down the key. If the keystroke is held long enough, multiple messages are sent. However, the repeat count is not cumulative. 16-23 The scan code. The value depends on the OEM.

24 Indicates whether the key is an extended key, such as the right-hand ALT and CTRL keys that appear on an enhanced 101- or 102-key keyboard. The value is 1 if it is an extended key; otherwise, it is 0. 25-28 Reserved; do not use

29 The context code. The value is 1 if the ALT key is down while the key is pressed; it is 0 if the WM_SYSKEYDOWN message is posted to the active window because no window has the keyboard focus.

30 The previous key state. The value is 1 if the key is down before the message is sent, or it is 0 if the key is up.

31 The transition state. The value is always 0 for a WM_SYSKEYDOWN message.

A: 

From the explanation of lParam parameter of WM_KEYDOWN message and Keystroke Message Flags chapter, I would write the following code to deal with the value of lParam:

  iRepeatCount   := LOWORD(lParam);
  iScanCode      := HIWORD(lParam) and $FF;
  iExtendedKey   := (HIWORD(lParam) and KF_EXTENDED) shr 8;
  iContextCode   := (HIWORD(lParam) and KF_ALTDOWN) shr 13;
  iPreviousState := (HIWORD(lParam) and KF_REPEAT) shr 14;
  iKeyDown       := (HIWORD(lParam) and KF_UP) shr 15;

Although it is Delphi implementation, I'm sure you can understand such a simple code. :-)

OK, for your convenience, I google for shr instruction equivalent in VB, and I get this:

  Private Function SHL(ByVal inVal As Long, ByVal inShift As Byte) As Long
     SHL = inVal * (2 ^ inShift) ' Bit shift left
  End Function

  Private Function SHR(ByVal inVal As Long, ByVal inShift As Byte) As Long
     SHR = inVal \ (2 ^ inShift) ' Bit shift right
  End Function

To mimic the LOWORD and HIWORD in VB, see How to Mimic HIWORD, LOWORD, HIBYTE, LOBYTE C Macros in VB.

Vantomex
Thanks, makes sense
Neville Shaun Ng
A: 

http://msdn.microsoft.com/en-us/library/ms646280(VS.85).aspx

The lparam is a 32 bit value; each bit controls a different aspect of the WM_KEYDOWN message. To correctly fill out the lparam, you might try using spy++ to see what real WM_KEYDOWN messages look like.

seand