Program Initialization

In MDIDEMO.C, WinMain begins by registering window classes for the frame window and the two child windows. The window procedures are called FrameWndProc, HelloWndProc, and RectWndProc. Normally, different icons should be associated with these window classes. For the purpose of simplicity, I've simply used the standard IDI_APPLICATION icon for the frame and child.

Note that I've defined the hbrBackground field of the WNDCLASS structure for the frame window class to be the COLOR_APPWORKSPACE system color. This is not entirely necessary because the client area of the frame window is covered up by the client window, and the client window has this color anyway. However, using this color looks a little better when the frame window is first displayed.

The lpszMenuName field is set to NULL for each of these three window classes. For the Hello and Rect child window classes, this is normal. For the frame window class I've chosen to indicate the menu handle in the CreateWindow function when creating the frame window.

The window classes for the Hello and Rect child windows allocate extra space for each window using a nonzero value as the cbWndExtra field of the WNDCLASS structure. This space will be used to store a local memory handle that will reference a block of memory (the size of the HELLODATA or RECTDATA structures defined near the top of MDIDEMO.C) used to store information unique to each document window.

Next, WinMain uses LoadMenu to load the three menus and save their handles in global variables. Three calls to the GetSubMenu function obtain handles to the Window submenu to which the document list will be appended. These are also saved in global variables. The LoadAccelerators function loads the accelerator table.

A call to CreateWindow in WinMain creates the frame window. During the WM- CREATE processing in FrameWndProc, the frame window creates the client window. This involves another call to CreateWindow. The window class is set to MDICLIENT, which is the preregistered class for MDI client windows. The last parameter to CreateWindow must be set to a pointer to a structure of type CLIENTCREATESTRUCT. This structure has two fields:

hWindowMenu is the handle of the submenu to which the document list will be appended. In MDIDEMO, this is hMenuInitWindow, which was obtained during WinMain. You'll see later how the menu is changed.

idFirstChild is the menu ID to be associated with the first document window in the document list. This is simply IDM_FIRSTCHILD.

Back in WinMain, MDIDEMO displays the newly created frame window and enters the message loop. The message loop differs a little from a normal loop: After obtaining the message from the message queue with a call to GetMessage, an MDI program passes the message to TranslateMDISysAccel (and TranslateAccelerator if, like the MDIDEMO program, the program also has menu accelerators).

The TranslateMDISysAccel function translates any keystrokes that may correspond to the special MDI accelerators (Ctrl-F6, for example) into a WM_SYSCOMMAND message. If neither TranslateMDISysAccel nor TranslateAccelerator returns TRUE (indicating that a message was translated by one of these functions), do not call TranslateMessage and DispatchMessage.

Notice the two different window handles passed to TranslateMDISysAccel and TranslateAccelerator: hwndClient and hwndFrame, respectively. The WinMain function obtains the hwndClient window handle by calling GetWindow with the GW_CHILD parameter.