The Window Function

Every window must have a window function. The window function responds to input and window-management messages received from Windows. The window function can be a short function, processing only a message or two, or it can be complex, processing many types of messages for a variety of application windows.

A window function has the following form:

long FAR PASCAL MainWndProc(hWnd, message, wParam, lParam)

HWND hWnd; /* window handle */

unsigned message; /* type of message */

WORD wParam; /* additional information */

LONG lParam; /* additional information */

{

.

.

.

switch (message) {

.

.

.

default: /* Passes it on if unprocessed */

return (DefWindowProc(hWnd, message,

wParam, lParam));

}

return (NULL);

}

The window function uses the PASCAL calling convention. Since Windows calls this function directly and always uses this convention, PASCAL is required. The window function also uses the FAR keyword in its definition, since Windows uses a 32-bit address whenever it calls a function. Also, you must name the window function in an EXPORTS statement in the application's module-definition file. For more information on module-definition files, see “Creating a Module-Definition File”.

The window function receives messages from Windows. These may be input messages that have been dispatched by the WinMain function or window-management messages that come directly from Windows. The window function must examine each message; it then either carries out some specific action based on the message, or passes the message back to Windows for default processing through the DefWindowProc function.

The message parameter defines the message type. You use this parameter in a switch statement to direct processing to the correct case. The lParam and wParam parameters contain additional information about the message. The window function typically uses these parameters to carry out the requested action. If a window function doesn't process a message, it must pass it to the DefWindowProc function. Passing the message to DefWindowProc ensures that any special actions that affect the window, the application, or Windows itself can be carried out.

Most window functions process the WM_DESTROY message. Windows sends this message to the window function immediately after destroying the window. The message gives the window function the opportunity to finish its processing and, if it is the window function for the application's main window, to post a WM_QUIT message in the application queue. The following example shows how the main window function should process this message:

case WM_DESTROY:

PostQuitMessage(0);

break;

The PostQuitMessage function places a WM_QUIT message in the application's queue. When the GetMessage function retrieves this message, it will terminate the message loop and the application.

A window function receives messages from two sources. Input messages come from the message loop and window-management messages come from Windows. Input messages correspond to mouse input, keyboard input, and sometimes timer input. Typical input messages are WM_KEYDOWN, WM_KEYUP, WM_MOUSEMOVE, and WM_TIMER, all of which correspond directly to hardware input.

Windows sends window-management messages directly to a window function without going through the application queue or message loop. These window messages are typically requests for the window function to carry out some action, such as painting its client area or supplying information about the window. The messages may also inform the window function of changes that Windows has made to the window. Some typical window-management messages are WM_CREATE, WM_DESTROY, and WM_PAINT.

The window function should return a long value. The actual value to be returned depends on the message received. The Windows Programming Reference describes the return values when they are significant (for most messages, the return value is arbitrary). If the window function doesn't process a message, it should return the DefWindowProc function's return value.