question

Salavat-ssh avatar image
0 Votes"
Salavat-ssh asked RLWA32-6355 commented

Using HIWORD and LOWORD in Win32 API. How does the system work?

Hello!
While studying the API, I ran into the problem of understanding what the upper and lower words are.
Below is an example of a window procedure. Two buttons are created in the WM_CREATE message (both handles are declared in a header file not shown). Further, in the WM_COMMAND message I catch the button presses. I looked at this example on one forum, but I just can't figure out at what stage the button descriptor is assigned to the lParam parameter and what happens when the left mouse button is pressed. When I turn on the debug mode, when the mouse button is pressed, the lParam parameter has already been assigned a handle to one of the buttons on the working surface. If I click on the Exit menu button (see the switch (LOWORD (wParam)) part of the code), it turns out that the wParam parameter has already been assigned the ID_FILE_EXIT number in the resources, defined through "define". When I looked at what HIWORD and LOWORD are practically everywhere "magic words" pop up :) that these are the upper and lower words. That is, if there is a number 0x3256abcd, then HIWORD is 3256, and LOWORD is abcd, but this does not explain how to catch certain responses of ready-made functions and macros from the Win32 API. Is there a general rule of what kind of code construction needs to be written to catch the pressing of a certain button, selecting text from a multiple list, changing the style of a drop-down menu, etc.

 LRESULT CALLBACK WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
 {
    switch (msg)
    {
    case WM_CREATE:
    {
        ...
        fbHwnd = CreateWindow(L"BUTTON", L"Next", WS_TABSTOP | WS_VISIBLE | WS_CHILD | BS_DEFPUSHBUTTON, 150, 200, 70, 50, hwnd, NULL, (HINSTANCE)GetWindowLongPtr(hwnd, GWLP_HINSTANCE), NULL);
        sbHwnd = CreateWindow(L"BUTTON", L"Exit", WS_TABSTOP | WS_VISIBLE | WS_CHILD | BS_DEFPUSHBUTTON, 222, 272, 70, 50, hwnd, NULL,(HINSTANCE)GetWindowLongPtr(hwnd, GWLP_HINSTANCE), NULL);
        ...
     }
     break;
     case WM_COMMAND:
     {
         if (lParam == (int)fbHwnd)
         {
                if (HIWORD(wParam) == BN_CLICKED)
                   {
                      MessageBox(hwnd, L"First button", L"Warning", MB_OK);  
                   }
          }
          else if (lParam == (int)sbHwnd)
          {
                if (HIWORD(wParam) == BN_CLICKED)
                   {
                      MessageBox(hwnd, L"Second button", L"Warning", MB_OK);   
                   }
           }
           break;
           switch (LOWORD(wParam))
           {
            ...
           case ID_FILE_EXIT:
           {
                 PostMessageW(hwnd, WM_CLOSE, 0, 0);
           }
           break;
           ...
           }
      }
      break;
      }
 }











windows-api
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

1 Answer

RLWA32-6355 avatar image
1 Vote"
RLWA32-6355 answered RLWA32-6355 commented

Is there a general rule of what kind of code construction needs to be written to catch the pressing of a certain button, selecting text from a multiple list, changing the style of a drop-down menu, etc.

The general rules that you are referring to would be documentation for the messages and notifications that the various controls in the Windows API use. Its a large topic but the documentation is here - window-controls

As an example, the behavior of button controls is documented here - buttons

Carefully read the documentation for BN_CLICKED, WM_COMMAND and CreateWindow. In particular, carefully review the table in the Remarks section of the CreateWindow documentation. Compare these details with the posted code.

With respect to the posted code -

  1. CreateWindow does not assign control identifiers to the two buttons created in the WM_CREATE handler. This identifier is passed as the hMenu parameter.

  2. CreateWindow returns a window handle (an HWND). It should not be cast to an int.

  3. The switch statement in which the ID_FILE_EXIT menu command is handled appears to be outside of the WM_COMMAND handler.

Finally, handling messages in a window procedure can be simplified by using "message crackers". These are macros that will split out the relevant parts of window messages and make it easier to handle them. They are located in the windowsx.h header.

· 7
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

3.The switch statement in which the ID_FILE_EXIT menu command is handled appears to be outside of the WM_COMMAND handler.


Correct)) added 1 extra parentheses) in VS code is normal)

0 Votes 0 ·

This is an error. It should be within the WM_COMMAND handler. Refer to the table in the Remarks section of the WM_COMMAND message.

1 Vote 1 ·

In Visual Studio, this code is in WM_COMMAND, an error occurred while writing the question) Is there a comprehensive explanation on the use of upper and lower words? Or is it an internal OS mechanism and can't be found?

0 Votes 0 ·
Show more comments

Also, only one of the buttons can be the default button. The code assigns BS_DEFPUSHBUTTON to both buttons.

It is more common for button controls to be in dialog windows. So instead of using an ordinary window and window procedure to experiment with controls I suggest you create a dialog-based application that uses a dialog procedure. These are documented at Dialog Boxes.


1 Vote 1 ·