Tricks of the Windows Game Programming Gurus:The Windows Programming Model

All ITKnowledge Source Code Search Tips Advanced Search |

| Tricks of the Windows Game Programming Gurus by Andre LaMothe Sams, Macmillan Computer Publishing ISBN: 0672313618 Pub Date: 09/27/99

Search this book:

Previous | Table of Contents | Next

Now that you know what the WinProc does, let’s take a look at the prototype for it:

    LRESULT CALLBACK WindowProc(

                     HWND hwnd, // window handle of sender

                     UINT msg,  // the message id

                     WPARAM wparam,  // further defines message

                     LPARAM lparam); // further defines message

Of course, this is just a prototype for the callback. You can call the function anything you want because you are only going to assign the function’s address as a function pointer to `winclass.lpfnWndProc`, like this:

    winclass.lpfnWndProc = WindowProc;

Remember? Anyway, the parameters are fairly self-explanatory:

  • `hwnd`—This is the window handle and is only important if you have multiple windows open with the same Windows class. In that case, `hwnd` is the only way you can tell which messages are coming from which window. Figure 2.7 shows this possibility.

  Figure 2.7 Multiple windows based on the same class.

  • `msg`—This is the actual message ID that the WinProc should handle. This ID may be one of dozens of main messages.
  • `wparam` and `Lparam`—These further qualify or subclass the message sent in the `msg` parameter.

And finally, the return type, `LRESULT`, and declaration specifier, `CALLBCK`, are of interest. These keywords are a must, so don’t forget them!

So what most people do is switch() on the msg and then write code for each case. And based on msg, you will know if you need to further evaluate wparam and/or lparam. Cool? So let’s take a look at some of the possible messages that might come through the WinProc, and then we’ll see a bare-bones WinProc. Take a look at Table 2.11 to see a short list of some basic message IDs.

Table 2.11 A Short List of Message IDs

Value | Description
--- | ---

`WM_ACTIVATE` | Sent when a window is activated or becomes the focus.
`WM_CLOSE` | Sent when a window is closed.
`WM_CREATE` | Sent when a window is first created.
`WM_DESTROY` | Sent when a window is about to be destroyed.
`WM_MOVE` | Sent when a window has been moved.
`WM_MOUSEMOVE` | Sent when the mouse has been moved.
`WM_KEYUP` | Sent when a key is released.
`WM_KEYDOWN` | Sent when a key is pressed.
`WM_TIMER` | Sent when a timer event occurs.
`WM_USER` | Allows you to send messages.
`WM_PAINT` | Sent when a window needs repainting.
`WM_QUIT` | Sent when a Windows application is finally terminating.
`WM_SIZE` | Sent when a window has changed size.

Take a good look at Table 2.11 and read what all those messages are for. Basically, the WinProc will be sent one or more of these messages as the application runs. The message ID itself will be in `msg`, and anyremaining info is stored in `wparam` and `lparam`. Thus, it’s always a good idea to reference the online Win32 SDK Help to see what all the parameters of a particular message do.

Fortunately, we are only interested in three messages right now:

  • `WM_CREATE`—This message is sent when the window is first created and gives you a chance to do any setup, initialization, or resource allocation.
  • `WM_PAINT`—This message is sent whenever your window’s contents need repainting. This can occur for a number of reasons: the window was moved or resized by the user, another application popped up and obscured yours, and so on.
  • `WM_DESTROY`—This message is sent to your window when the window is about to be destroyed. Usually, this is a direct result of the user clicking the window’s close icon or closing from the window’s system menu. Either way, this is where you should deallocate all the resources and tell Windows to terminate the application completely by sending a `WM_QUIT` message yourself—more on this later.

So without further ado, let’s see a complete WinProc that handles all these messages:

    LRESULT CALLBACK WindowProc(HWND hwnd,

                                UINT msg,

                                WPARAM wparam,

                                LPARAM lparam)

    {

    // this is the main message handler of the system

    PAINTSTRUCT    ps;    // used in WM_PAINT

    HDC        hdc;    // handle to a device context

    // what is the message

    switch(msg)

        {

        case WM_CREATE:

            {

        // do initialization stuff here

            // return success

        return(0);

        } break;

        case WM_PAINT:

        {

        // simply validate the window

        hdc = BeginPaint(hwnd,&ps);

        // you would do all your painting here

            EndPaint(hwnd,&ps);

            // return success

        return(0);

        } break;

        case WM_DESTROY:

        {

        // kill the application, this sends a WM_QUIT message

        PostQuitMessage(0);

            // return success

        return(0);

        } break;

        default:break;

        } // end switch

    // process any messages that we didn't take care of

    return (DefWindowProc(hwnd, msg, wparam, lparam));

    } // end WinProc

As you can see, the function is composed of empty space for the most part—which is a good thing! Let’s begin with the processing of `WM_CREATE`. Here, all the function does is `return(0)`. This simply tells Windows that you handled it, so don’t take any more actions. Of course, you could have done all kinds of initialization in the `WM_CREATE` message, but that’s up to you.

The next message, `WM_PAINT`, is very important. This message is sent whenever your window needs repainting. This usually means that you have to do the repainting. For DirectX games, this isn’t going to matter because you are going to redraw the screen 30 to 60 fps (frames per second). But for a normal Windows application, it does matter. I’m going to cover `WM_PAINT` in much more detail in the next chapter, but for now just tell Windows that you did repaint the window, so it can stop sending `WM_PAINT` messages.

Previous | Table of Contents | Next

Copyright © Macmillan Computer Publishing, Inc.

Products | Contact Us | About Us | Privacy | Ad Info | Home
Use of this site is subject to certain Terms & Conditions, Copyright © 1996-2000 EarthWeb Inc. All rights reserved. Reproduction in whole or in part in any form or medium without express written permission of EarthWeb is prohibited. Read EarthWeb's privacy statement.