What are the definitions for LPARAM and WPARAM?
LPARAM
is a typedef for LONG_PTR
which is a long
(signed 32-bit) on win32 and __int64
(signed 64-bit) on x86_64.
WPARAM
is a typedef for UINT_PTR
which is an unsigned int
(unsigned 32-bit) on win32 and unsigned __int64
(unsigned 64-bit) on x86_64.
MSDN link
WPARAM and LPARAM parameters
When sending messages, WPARAM
and LPARAM
parameters have specific interpretations depending on the message. You need to pass those parameters in the way that the message that you are sending expects them to be passed. If you are defining your own message (perhaps via an offset from WM_USER
, WM_APP
, or RegisterWindowMessage
), then you obviously have a bit more latitude.
In the days of 16-bit Windows, a WPARAM
was a 16-bit word, while LPARAM
was a 32-bit long. These distinctions went away in Win32; they both became 32-bit values.
According to this, LPARAM
is defined as LONG_PTR
, which in 64-bit Windows is a signed, 64-bit value. WPARAM
is defined as UINT_PTR
, which in 64-bit Windows is an unsigned, 64-bit value. If you are defining your own message, you might want to assign its parameters accordingly.
What do LRESULT, WPARAM and LPARAM mean?
That's Charles Simonyi, the former head of the Application Software group at Microsoft, the group that developed Word and Excel. He's the one that set identifier naming standards. Since nobody knows how to pronounce his last name, they picked the country he was born in and called it Hungarian notation. The Windows group adopted it as well, but picked the "bad" kind, System Hungarian. Where the first letter(s) of the identifier is chosen to note the type of the variable. As opposed to the "good" kind, Apps Hungarian, which selects the prefix by the logical type name instead of the physical type name. Simonyi's version.
So it is L as in Long, W as in Word. LPCWSTR is a doozy like that, Long Pointer to Constant Wide String. A clear problem with System Hungarian is that it doesn't work so well anymore when the architecture changes. Originally picked for 16-bit operating systems (L=32-bits, W=16-bits), migrated to 32-bit without changing the name (W=32-bits), we're at 64-bit today (L=W=64-bits).
So ignore these prefixes, they're just an historical accident. You really must pick IntPtr for the LRESULT type, it certainly can be a 64-bit value on the 64-bit version of Windows. Very hard to diagnose problems occur when you don't, a common question here.
Off topic, the fuzzy image you see in the background of the photograph is an interesting tidbit about Simonyi as well. Microsoft shared its great success with its employees and turned many of them into multi-millionaires. What you see in the background is a shot of the space shuttle docked to the International Space Station. Simonyi is one of the seven "space tourists" and bought himself a ticket to ISS. The only one to do so twice, set him back $60 million :)
C++ wParam and Lparam confusion
I'm sorry. But the reliable way to know what is being passed in the wParam and lParam of each message is to refer to the documentation.
I read somewhere that wParam is 16 bit and lParam is 32 bit
According to this, WPARAM
is an unsigned (32-bit) int, while LPARAM
is a signed long.
Understanding SendMessage wparam
Per the EN_CHANGE
documentation for standard EDIT controls:
wParam
The LOWORD contains the identifier of the edit control. The HIWORD specifies the notification code.
So, the code is taking the constant EN_CHANGE
, shifting its bits to the left 16 places, and then OR'ing the bits of the control ID. Thus, EN_CHANGE
ends up in bits 16-31, and the control ID ends up in bits 0-15:
WPARAM
-----------------------------------------------------------------
| EN_CHANGE | CtrlID |
-----------------------------------------------------------------
1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0
However, the code should be using the MAKEWPARAM()
macro instead of shifting + OR'ing bits manually, eg:
GetParent()->SendMessage(WM_NOTIFY, MAKEWPARAM(GetDlgCtrlID(), EN_CHANGE), (LPARAM) &pNMHDR);
Now, that being said, a standard EDIT control sends EN_CHANGE
via WM_COMMAND
, not WM_NOTIFY
. But a standard windowless RICHEDIT control sends EN_CHANGE
via WM_NOTIFY
, which carries only the control ID by itself in the wParam
parameter. The command ID is carried in the NMHDR
struct pointed at by the lParam
parameter (except, RICHEDIT uses the CHANGENOTIFY
struct, which is unrelated to NMHDR
).
So, this code's use of EN_CHANGE
is clearly non-standard usage, using a customized parameter scheme.
What does lPram and wParam means and context each time? I am using PostMessage API from C#
The names wParam
and lParam
mean "word parameter" and "long parameter" and are holdovers from Win16, when those parameters actually were 2- and 4-byte values, though both of them are 4-byte integer values in Win32. The exact values needed are specific to the message you are sending. You'll have to look up the messages in the Win32 API documentation to figure it out, for example:
WM_LBUTTONDOWN and WM_LBUTTONUP
In this case, you're lucky in that neither parameter has to be a complex structure, so you just need to construct the proper 32-bit value with your coordinates in them with the & and << operators.
It's not uncommon for one of the parameters to be a pointer to a structure, in which case you'll have to resort to using the Marshal
class (specifically, AllocHGlobal, StructureToPtr, and FreeHGlobal
) to coerce the data into a usable format.
EDIT:
Note that most of the Windows common controls, like ListBox, have special messages that map to the events exposed by .NET. Unfortunately, in this specific case, CheckedListBox isn't a standard Windows API control; I haven't actually checked but I would guess it's an owner-drawn ListBox control. You could probably check/uncheck the items in the control with the LB_SETITEMDATA event, but unless the obvious values for lParam (1/0) actually work, you'd have to do some digging with Spy++ or something similar to figure that out.
The lparam and wparam parameters in this specific sendmessage function?
SendMessage is a method which can be used to send a specified message to a window or windows.
Documentation is here: http://msdn.microsoft.com/en-us/library/windows/desktop/ms644950%28v=vs.85%29.aspx
The first parameter is the "handle" (HWND) to which the message is send. The second parameter is a message id (see http://msdn.microsoft.com/en-us/library/windows/desktop/ms644927(v=vs.85).aspx#system_defined for System-Defined Messages).
The last two parameters can be used to pass more data to the receiver. - Normally both parameters have message dependent meanings.
In your case the WM_APPCOMMAND message (http://msdn.microsoft.com/en-us/library/windows/desktop/ms646275%28v=vs.85%29.aspx) is passed (here it is a keyboard command). I think the first parameter could also be NULL (according to the link above it should be a handle to the window where the user clicked the button or pressed the key), but the second one has to specify the command which should be passed (as an APPCOMMAND). The second parameter is 8 (8=APPCOMMAND_VOLUME_MUTE according to the list on the linked page), however we have to do a bitshift, because the information has to be encoded in the high-order bits of the parameter (i.e., 0x80000 - that's APPCOMMAND_VOLUME_MUTE*&H10000; see lParam section on the page I linked).
Related Topics
What Is the Purpose of Anonymous { } Blocks in C Style Languages
Asp:Fileupload Edit "No File Selected" Message
Understanding Floating Point Problems
How to Read a .Net Guid into a Java Uuid
Refresh Datagridview When Updating Data Source
C# Httpwebrequest Command to Get Directory Listing
When I Post Back to My Controller All Values for My Model Are Null
Parsing Visual Studio Solution Files
Retrying Httpclient Unsuccessful Requests
How to Get Memcached Running on a Windows (X64) 64Bit Environment
How to Use CSS on an HTML.Actionlink in C#
How to Call an ASP.NET C# Method Using JavaScript
When Not to Use Regex in C# (Or Java, C++, etc.)
How to Encrypt Selected Properties When Serializing My Objects