`
`2. Resource script: The resource script is an ASCII file that generally has the extension
`.RC. This file contains definitions of menus, dialog boxes, string tables, and keyboard
`accelerators used by the program. The resource script can also reference other files
`that contain icons, cursors, bitmaps, and fonts in binary form, as well as other read(cid:173)
`only data defined by the programmer. When a program is running, Windows loads
`resources into memory only when they are needed and in most cases can discard
`them if additional memory space is required.
`SAMPLE.RC, the resource script for the SAMPLE program, is shown in Figure 17-12; it
`contains only the definition of the menu used in the program.
`
`#include "sample.h"
`
`Sample MENU
`BEGIN
`POPUP "&Typeface"
`BEGIN
`MENUITEM "&Script", IDM_SCRIPT, CHECKED
`MENUITEM "&Modern",
`IDM_MODERN
`MENUITEM "&Roman",
`IDM_ROMAN
`
`END
`
`END
`
`Figure 17-12. The resource script for the SAMPLE program.
`
`3. Header (or include) file: This file, with the extension .H, can contain definitions of
`constants or macros, as is customary in C programming. For Windows programs, the
`header file also reconciles constants used in both the resource script and the pro(cid:173)
`gram source-code file. For example, in the SAMPLE.RC resource script, each item in
`the pop-up menu (Script, Modern, and Roman) also includes an identifier(cid:173)
`IDM_SCRIPT, IDM_MODERN, and IDM_ROMAN, respectively. These identifiers
`are merely numbers that Windows uses to notify the program of the user's selection
`of a menu item. The same names are used to identify the menu selection in the C
`source-code file. And, because both the resource compiler and the source-code com(cid:173)
`piler must have access to these identifiers, the header file is included in both the
`resource script and the source-code file.
`The header file for the SAMPLE program, SAMPLE.H, is shown in Figure 17-13.
`
`#define IDM_SCRIPT 1
`#define IDM-MODERN 2
`#define IDM_ROMAN
`3
`
`Figure 17-13. The SAMPLE.H header file.
`
`4. Module-definition file: The module-definition file generally has a .DEF extension.
`The Windows linker uses this file in creating the executable .EXE file. The module(cid:173)
`definition file specifies various attributes of the program's code and data segments,
`and it lists all imported and exported functions in the source-code file. In large pro(cid:173)
`grams that are divided into multiple code segments, the module-definition file allows
`the programmer to specify different attributes for each code segment.
`
`516
`
`The MS-DOS Encyclopedia
`
`HUAWEI EX. 1110 - 526/1582
`
`
`
`Article 17: Windows
`
`The module-definition file for the SAMPLE program is named SAMPLE.DEF and is
`shown in Figure 17-14.
`
`NAME
`DESCRIPTION
`STUB
`CODE
`DATA
`HEAP SIZE
`STACKSIZE
`EXPORTS
`
`SAMPLE
`'Demonstration Windows Program'
`'WINSTUB.EXE'
`MOVABLE
`MOVABLE MULTIPLE
`1024
`4096
`WndProc
`
`Figure 17-14. The SAMPLE.DEF module-definition file.
`
`5. Make file: To facilitate construction of the executable file from these different com(cid:173)
`ponents, Windows programmers often use the MAKE program to compile only those
`files that have changed since the last time the program was linked. To do this, the
`programmer first creates an ASCII text file called a make file. By convention, the
`make file has no extension.
`The make file for the SAMPLE program is named SAMPLE and is shown in Figure
`17-15. The programmer can create the SAMPLE.EXE executable file by executing
`
`C>MAKE SAMPLE <Enter>
`
`A make file often contains several sections, each beginning with a target filename,
`followed by a colon and one or more dependent filenames, such as
`
`sample.obj : sample.c sample.h
`
`If either or both the SAMPLE.C and SAMPLE.H files have a later creation time than
`SAMPLE.OBJ, then MAKE runs the program or programs listed immediately below.
`In the case of the SAMPLE make file, the program is the C compiler, and it compiles
`the SAMPLE.C source code:
`
`cl -c -Gsw -W2 -Zdp sample.c
`
`Thus, if the programmer changes only one of the several files used in the develop(cid:173)
`ment of SAMPLE, then running MAKE ensures that the executable file is brought up
`to date, while carrying out only the required steps.
`
`sample.obj : sample.c sample.h
`cl -c -Gsw -W2 -Zdp sample.c
`
`sample.res : sample.rc sample.h
`rc -r sample.rc
`
`sample.exe : sample.obj sample.def sample.res
`link4 sample, /align:16, /map /line, slibw, sample
`rc sample.res
`mapsym sample
`
`Figure 17-15. The make file for the SAMPLE program.
`
`Section IL· Programming in the MS-DOS Environment
`
`517
`
`HUAWEI EX. 1110 - 527/1582
`
`
`
`Part D: Directions of MS-DOS
`
`Construction of a Windows program
`The make file shows the steps that create a program's .EXE file from the various
`components:
`
`1. Compiling the source-code file:
`
`cl -c -Gsw -W2 -Zdp sample.c
`
`-
`
`This step uses the CL.EXE C compiler to create a .OBJ object-module file. The com(cid:173)
`mand line switches are
`-c: Compiles the program but does not link it. Windows programs must be linked ·
`-
`with Windows' LINK4linker, rather than with the LINK program the C compiler
`would normally invoke.
`-Gsw: Includes two switches, -Gs and -Gw. The -Gs switch removes stack checks
`from the program. The -Gw switch inserts special prologue and epilogue code in
`all far functions defined in the program. This special code is required for Win(cid:173)
`dows' memory management.
`-W2: Compiles with warning level2. This is the highest warning level, and it causes
`the compiler to display messages for conditions that may be acceptable in normal C
`programs but that can cause serious errors in a Windows program.
`-Zdp: Includes two switches, -Zd and -Zp. The -Zd switch includes line numbers
`in the .OBJ file-helpful for debugging at the source-code level. The -Zp switch
`packs structures on byte boundaries. The -Zp switch is required, because data
`structures used within Windows are in a packed format.
`2. Compiling the resource script:
`
`-
`
`rc -r sample.rc
`
`This step runs the resource compiler and converts the ASCII .RC resource script into a
`binary .RES form. The -r switch indicates that the resource script should be compiled
`but the resources should not yet be added to the program's .EXE file.
`3. Linking the program:
`
`link4 sample, /align:16, /map /line, slibw, sample
`
`This step uses the special Windows linker, LINK4. The first parameter listed is the
`name of the .OBJ file. The /align: 16 switch instructs LINK4 to align segments in the
`.EXE file on 16-byte boundaries. The /map and /line switches cause LINK4 to create a
`.MAP file that contains program line numbers- again, useful for debugging source
`code. Next, slibw is a reference to the SLIBW.LIB file, which is an import library that
`contains module names and ordinal numbers for all Windows functions. The last
`parameter, sample, is the program's module-definition file, SAMPLE.DEF.
`4. Adding the resources to the .EXE file:
`
`rc sample.res
`
`518
`
`The MS-DOS Encyclopedia
`
`HUAWEI EX. 1110 - 528/1582
`
`
`
`Article 17: Windows
`
`This step runs the resource compiler a second time, using the compiled resource file,
`SAMPLE.RES. This time, the resource compiler adds the resources to the .EXE file.
`
`Header or
`include files
`(.Hor .INC)
`
`I
`
`Libraries
`(.Lm)
`
`I
`
`Resource script
`(.RC)
`
`...
`
`RC.EXE
`Resource compiler
`
`Compiled resources
`(.RES)
`
`Module
`definition file
`(.DEF)
`
`t
`
`Map file
`(.MAP)
`
`MAPSYM.EXE
`Converts map file
`to symbol file
`
`t
`
`Symbol file
`(.SYM)
`
`Program
`source code
`(.C, .PAS, or .ASM)
`
`~
`
`t
`
`Cor Pascal
`Compiler or
`Macro Assembler
`
`~
`
`Object module
`(.OBJ)
`
`...
`
`~
`
`...
`
`LINK4.EXE
`Window linker
`
`I ~
`
`Executable
`without resources
`(.EXE)
`
`~ t
`
`RC.EXE
`Resource compiler
`
`t
`
`Executable
`(.EXE)
`
`Figure 17-16. A block diagram showing the creation of a Windows .EXEfile.
`
`Section II: Programming in the MS-DOS Environment
`
`519
`
`HUAWEI EX. 1110 - 529/1582
`
`
`
`Part D: Directions of MS-DOS
`
`5. Creating a symbol (.SYM) file from the linker's map (.MAP) file:
`
`mapsym sample
`
`This step is required for symbolic debugging with SYMDEB.
`
`Figure 17-16 on the preceding page shows how the various components of a Windows pro-
`gram fit into the creation of a .EXE file.
`·
`Program initialization
`The SAMPLE.C program shown in Figure 17-11 contains some code that appears in almbst
`every Windows program. The statement
`
`#include <windows.h>
`
`appears at the top of every Windows source-code file written in C. The WINDOWS.H file,
`provided with the Microsoft Windows Software Development Kit, contains templates for
`all Windows functions, structure definitions, and #define statements for many mnemonic
`identifiers.
`
`Some of the variable names in SAMPLE.C may look unusual to C programmers because
`they begin with a prefix notation that denotes the data type of the variable. Windows
`programmers are encouraged to use this type of notation. Some of the more common
`prefixes are
`
`Prefix
`
`Data Type
`
`i or n
`w
`
`dw
`h
`sz
`lpsz
`lpfn
`
`Integer (16-bit signed integer)
`Word (16-bit unsigned integer)
`Long (32-bit signed integer)
`Doubleword (32-bit unsigned integer)
`Handle (16-bit unsigned integer)
`Null-terminated string
`Long pointer to null-terminated string
`Long pointer to a function
`
`The program's entry point (following some startup code) is the WinMain function,
`which is passed the following parameters: a handle to the current instance of the
`program (hlnstance), a handle to the most recent previous instance of the program
`(hPrevlnstance), a long pointer to the program's command line (lpszCmdLine), and a
`number (nCmdShow) that indicates whether the program should initially be displayed as a
`normally sized window or as an icon.
`
`The first job SAMPLE performs in the WinMain function is to register a window class- a
`structure that describes characteristics of the windows that will be created in the class.
`These characteristics include background color, the type of cursor to be displayed in the
`window, the window's initial menu and icon, and the window function (the structure
`member called lpfnWndProc).
`
`520
`
`The MS-DOS Encyclopedia
`
`HUAWEI EX. 1110 - 530/1582
`
`
`
`Article 17: Windows
`
`Multiple instances of a program can share the same window class, so SAMPLE registers the
`window class only for the first instance of the program:
`
`if (!hPrevinstance)
`
`CS_VREDRAW
`
`CS_HREDRAW
`wndclass.style
`WndProc
`wndclass.lpfnWndProc
`0 ;
`wndclass.cbClsExtra
`0
`;
`wndclass.cbWndExtra
`hlnstance
`wndclass.hlnstance
`NULL
`;
`wndclass.hlcon
`IDC_ARROW)
`LoadCursor (NULL,
`wndclass.hCursor
`GetStockObject (WHITE_BRUSH)
`wndclass.hbrBackground
`szAppName
`wndclass.lpszMenuName
`wndclass.lpszClassName = szAppName
`
`RegisterClass (&wndclass)
`)
`
`;
`
`The SAMPLE program then creates a window using the CreateWindow call, displays it to
`the screen by calling ShowWindow, and updates the client area by calling UpdateWindow:
`
`hWnd = CreateWindow (szAppName, "Demonstration Windows Program",
`WS_OVERLAPPEDWINDOW,
`(int) CW_USEDEFAULT,O,
`(int) CW_USEDEFAULT,O,
`NULL, NULL, hinstance, NULL)
`ShowWindow (hWnd, nCmdShow)
`;
`UpdateWindow (hWnd)
`;
`
`The first parameter to Create Window is the name of the window class. The second param(cid:173)
`eter is the actual text that appears iri the window's title bar. The third parameter is the style
`of the window- in this case, the WINDOWS.H identifier WS_OVERLAPPEDWINDOW.
`The WS_OVERLAPPEDWINDOW is the most common window style. The fourth through
`seventh parameters specify the initial position and size of the window. The identifier
`CW _USEDEFAULT tells Windows to position and size the window according to the default
`rules.
`
`After creating and displaying a Window, the SAMPLE program enters a piece of code
`called the message loop:
`
`while (GetMessage (&msg, NULL, 0, 0))
`(
`TranslateMessage (&msg)
`DispatchMessage (&msg)
`
`;
`
`return msg.wParam ;
`
`This loop continues to execute until the GetMessage call returns zero. When that happens,
`the program instance terminates and the memory required for the instance is freed.
`
`Section II: Programming in the MS-DOS Environment
`
`521
`
`HUAWEI EX. 1110 - 531/1582
`
`
`
`Part D: Directions of MS-DOS
`
`The Windows messaging system
`Interactive programs written for the normal MS-DOS environment generally obtain user
`input only from the keyboard, using either an MS-DOS or a ROM BIOS software interrupt
`to check for keystrokes. When the user types something, such programs act on the key~
`stroke and then return to wait for the next keystroke.
`
`Programs written for Windows, however, can receive user input from a variety of sources,
`including the keyboard, the mouse, the Windows timer, menus, scroll bars, and controls,
`such as buttons and edit boxes.
`
`Moreover, a Windows program must be informed of other events occurring within the
`system. For instance, the user of a Windows program might choose to make its window
`smaller or larger. Windows must make the program aware of this change so that the pro(cid:173)
`gram can adjust its screen output to fit the new window size. Thus, for example, if a Win(cid:173)
`dows program is minimized as an icon and the user maximizes its window to fill the full
`screen, Windows must inform the program that the size of the client area has changed
`and needs to be re-created.
`
`Windows carries out this job of keeping a program informed of other events through the
`use of formatted messages. In effect, Windows sends these messages to the program. The
`Windows program receives and acts upon the messages.
`
`This messaging makes the relationship between Windows and a Windows program much
`different from the relationship between MS-DOS and an MS-DOS program. Whereas
`MS-DOS does not provide information until a program requests it through an MS-DOS
`function call, Windows must continually notify a program of all the events that affect its
`window.
`
`Window messages can be separated into two major categories: queued and nonqueued.
`
`Queued messages are similar to the keyboard information an MS-DOS program obtains
`from MS-DOS. When the Windows user presses a key on the keyboard, moves the mouse,
`or presses one of the mouse buttons, Windows saves information about the event (in the
`form of a data structure) in the system message queue. Each message is destined for a par(cid:173)
`ticular window in a particular instance of a Windows program. Windows therefore deter(cid:173)
`mines which window should get the information and then places the message in the
`instance's own message queue.
`
`A Windows program retrieves information from its queue in the message loop:
`
`while (GetMessage (&msg, NULL, 0, ,0))
`(
`TranslateMessage (&msg)
`DispatchMessage (&msg)
`)
`
`;
`
`The msg variable is a structure. During the GetMessage call, Windows fills in the fields of
`this structure with information about the message. The fields are as follows:
`
`522
`
`The MS-DOS Encyclopedia
`
`HUAWEI EX. 1110 - 532/1582
`
`
`
`Article 17: Windows
`
`•
`•
`
`•
`
`•
`•
`
`•
`•
`
`hwnd: The handle for the window that is to receive the message.
`iMessage: A numeric code identifying the type of message (for example, keyboard
`or mouse).
`wParam: A 16-bit value containing information specific to the message. See The
`Windows Messages below.
`lParam: A 32-bit value containing information specific to the message.
`time: The time, in milliseconds, that the message was placed in the queue. The time
`is a 32-bit value relative to the time at which the current Windows session began.
`pt.x: The horizontal coordinate of the mouse cursor at the time the event occurred.
`pt.y: The vertical coordinate of the mouse cursor at the time the event occurred.
`
`GetMessage always returns a nonzero value except when it receives a quit message. The
`quit message causes the message loop to end. The program should then terminate and
`return control to Windows.
`
`Within the message loop, the TranslateMessage function translates physical keystrokes into
`character-code messages. Windows places these translated messages into the program's
`message queue.
`
`The DispatchMessage function essentially makes a call to the window function of the win(cid:173)
`dow specified by the hwnd field. This window function (WndProc in SAMPLE) is indicated
`in the lpfn WndProc field of the window class structure.
`
`When DispatchMessage passes the message to the window function, Windows uses the
`first four fields of the message structure as parameters to the function. The window func(cid:173)
`tion can then process the message. In SAMPLE, for instance, the four fields passed to
`WndProc are hwnd (the handle to the window), iMessage (the numeric message iden(cid:173)
`tifier), wParam, and lParam. Although Windows does not pass the time and mouse(cid:173)
`position information fields as parameters to the window function, this information is
`available through the Windows functions GetMessageTime and GetMessagePos.
`
`A Windows program obtains only a few specific types of messages through its message
`queue. These are keyboard messages, mouse messages, timer messages, the paint message
`that tells the program it must re-create the client area of its window, and the quit message
`that tells the program it is being terminated.
`
`In addition to the queued messages, however, a program's window function also receives
`many nonqueued messages. Windows sends these nonqueued messages by bypassing the
`message loop and calling the program's window function directly.
`
`Many of these non queued messages are derived from queued messages. For example,
`when the user clicks the mouse onthe menu bar, a mouse-click message is placed in the
`program's message queue. The GetMessage function retrieves the message and the Dis(cid:173)
`patchMessage function sends it to the program's window function. However, because this
`mouse message affects a nonclient area of the window (an area outside the window's cli(cid:173)
`ent area), the window function normally does not process it. Instead, the function passes
`the message back to Windows. In this example, the message tells Windows to invoke a
`pop-up menu. Windows calls up the menu and then sends the window function several
`non queued messages to inform the program of this action.
`
`Section !1: Programming in the MS-DOS Environment
`
`523
`
`HUAWEI EX. 1110 - 533/1582
`
`
`
`Part D: Directions of MS-DOS
`
`A Windows program is thus message driven. Once a program reaches the message loop,
`it acts only when the window function receives a message. And, although a program
`receives many messages that affect the window, the program usually processes only some
`of them, sending the rest to Windows for normal default processing.
`
`The Windows messages
`
`Windows can send a window function more than 100 different messages. The
`WINDOWS.H header file includes identifiersJor all these messages so that C programmers
`do not have to remember the message numbers. Some of the more common messages and
`the meanings of the wParam and lParam parameters are discussed here:
`
`WM_CREATE. Windows sends a window function this nonqueued message while pro(cid:173)
`cessing the CreateWindow call. The lParam parameter is a pointer to a creation structure.
`A window function can perform some program initialization during the WM_ CREATE .
`message.
`
`WM_MOVE. Windows sends a window function the nonqueued WM_MOVE message
`when the window has been moved to another part of the display. The lParam parameter
`gives the new coordinates of the window relative to the upper left corner of the screen.
`
`WM_SIZE. This nonqueued message indicates that the size of the window has been
`changed. The new size is encoded in the lParam parameter. Programs often save this
`window size for later use.
`
`WM_PAINT. This queued message indicates that a region in the window's client area
`needs repainting. (The message queue can contain only one WM_ PAINT message.)
`
`WM_COMMAND. This nonqueued message signals a program that a user has selected a
`menu item or has triggered a keyboard accelerator. Child-window controls also use
`WM_COMMAND to send messages to the parent window.
`
`WM_KEYDOWN. The wParam parameter of this queued message is a virtual key code
`that identifies the key being pressed. The lParam parameter includes flags that indicate
`the previous key state and the number of keypresses the message represents.
`
`WM_KEYUP. This queued message tells a window function that a key has been released.
`The wParam parameter is a virtual key code.
`
`WM_CHAR. This queued message is generated from WM_KEYDOWN messages during
`the TranslateMessage call. The wParam parameter is the ASCII code of a keyboard key.
`
`WM_MOUSEMOVE. Windows uses this queued message to tell a program about mouse
`movement. The lParam parameter contains the coordinates of the mouse relative to the
`upper left corner of the client area of the window. The wParam parameter contains flags
`that indicate whether any mouse buttons or the Shift or Ctrl keys are currently pressed.
`
`WM_xBUTTONDOWN. This queued message tells a program that a button on the mouse
`was depressed while the mouse was in the window's. client area. The xcan be either L, R,
`or M for the left, right, or middle mouse button. The wParam and lParam parameters are
`the same as for WM_MOUSEMOVE.
`
`524
`
`The MS-DOS Encyclopedia
`
`HUAWEI EX. 1110 - 534/1582
`
`
`
`Article 17: Windows
`
`WM_xBUTTONUP This queued message tells a program that the user has released a
`mouse button.
`
`WM_xBUTTONDBLCLK. When the user double-clicks a mouse button, Windows
`generates a WM_xBUTTONDOWN message for the first click and a queued
`WM_xBUTTONDBLCLK message for the second click.
`
`WM_ TIMER. When a Windows program sets a timer with the SetTimer function,
`Windows places a WM_ TIMER message in the message queue at periodic intervals.
`The wParam parameter is a timer ID. (If the message queue already contains a
`WM_TIMER message, Windows does not add another one to the queue.)
`
`WM_ VSCROLL. A Windows program that includes a vertical scroll bar in its window
`receives nonqueued WM_ VSCROLL messages indicating various types of scroll-bar
`manipulation.
`
`WM....;.HSCROLL. This nonqueued message indicates a user is manipulating a horizontal
`scroll bar.
`
`WM_CLOSE. Windows sends a window function this nonqueued message when the user
`has selected Close from the window's system menu. A program can query the user to de(cid:173)
`termine whether any action, such as saving a file to disk, is needed before the program
`is terminated.
`
`WM_QUERYENDSESSION. This nonqueued message indicates that the user is shutting
`down Windows by selecting Close from the MS-DOS Executive system menu. A program
`can request the user to verify that the program should be ended. If the window function
`returns a zero value from the message, Windows does not end the session.
`
`WM_DESTROY. This nonqueued message is the last message a window function receives
`before the program ends. A window function can perform some last-minute cleanup while
`processing WM_DESTROY.
`
`WM_QUIT. This is a queued message that never reaches the window function because it
`causes GetMessage to return a zero value that causes the program to exit the message loop.
`
`Message processing
`
`Programmers can choose to process some messages and ignore others in the window
`function. Messages that are ignored are generally passed on to the function
`DefWindowProc for default processing within Windows.
`
`Because Windows eventually has access to messages that a window function does not
`process, it can send a program messages that might otherwise be regarded as pertaining to
`system functions- for example, mouse messages that occur in a non client area of the win(cid:173)
`dow, or system keyboard messages that affect the menu. Unless these messages are passed
`on to DefWindowProc, the menu and other system functions do not work properly.
`
`A program can, however, trap some of these messages to override Windows' default pro(cid:173)
`cessing. For example, when Windows needs to repaint the nonclient area of a window (the
`title bar, system-menu box, and scroll bars), it sends the window function a WM_NCPAINT
`
`Section II: Programming in the MS-DOS Environment
`
`525
`
`HUAWEI EX. 1110 - 535/1582
`
`
`
`Part D: Directions of MS-DOS
`
`(nonclient paint) message. The window function normally passes this message to
`DefWindowProc, which then calls routines to update the nonclient areas of the window.
`The program can, however, choose to process the WM_NCPAINT message and paint the
`. nonclient area itself. A program that does this can, for example, draw its own scroll bars.
`
`The Windows messaging system also notifies a program of important events occurring
`outside its window. For example, if the MS-DOS Executive were simply to end the Win(cid:173)
`dows session when the user selects the Close option from its system menu, then applica(cid:173)
`tions that were still running would not have a chance to save changed files to disk. Instead,
`when the user selects Close from the last instance of the MS-DOS Executive's system
`menu, the MS-DOS Executive sends a WM_QUERYENDSESSION message to each cur(cid:173)
`rently running application. If any application responds by returning a zero value, the MS(cid:173)
`DOS Executive does not end the Windows session.
`
`Before responding, an application can process the WM_QUERYENDSESSION message
`and display a message box asking the user if a file should be saved. The message box
`should include three buttons labeled Yes, No, and Cancel. If the user answers Yes, the pro(cid:173)
`gram can save the file and then return a nonzero value to the WM_QUERYENDSESSION
`message. If the user answers No, the program can return a nonzero value without saving
`the file. But if the user answers Cancel, the program should return a zero value so that
`the Windows session will not be ended. If a program does not process the
`WM_QUERYENDSESSION message, DefWindowProc returns a nonzero value.
`
`When a user selects Close from the system menu of a particular instance of an application,
`rather than from the MS-DOS Executive's menu, Windows sends the window function a
`WM_CLOSE message. If the program has an unsaved file loaded, it can query the user with
`a message box- possibly the same one displayed when WM_QUERYENDSESSION is
`processed. If the user responds Yes to the query, the program can save the file and then
`call DestroyWindow. If the user responds No, the program can call DestroyWindow
`without saving the file. If the user responds Cancel, the window function does not call
`DestroyWindow and the program will not be terminated. If a program does not process
`WM_CLOSE messages, DefWindowProc calls DestroyWindow.
`
`Finally, a window function can send messages to other window functions, either within
`the same program or in other programs, with the Windows Send Message function. This
`function returns control to the calling program after the message has been processed. A
`program can also place messages in a program's message queue with the PostMessage
`function. This function returns control immediately after posting the message.
`
`For example, when a program makes changes to the WIN.INI file (a file containing
`Windows initialization information), it can notify all currently running instances of these
`changes by sending them a WM_ WININICHANGE message:
`
`SendMessage (-1, WM_WININICHANGE, 0, OL)
`
`;
`
`The -1 parameter indicates that the message is to be sent to all window functions of
`all currently running instances. Windows calls the window functions with the
`WM_WININICHANGE message and then returns control to the program that sent the
`message.
`
`526
`
`The MS-DOS Encyclopedia
`
`HUAWEI EX. 1110 - 536/1582
`
`
`
`Article 17: Windows
`
`SAMPLE's message processing
`
`The SAMPLE program shown in Figure 17-11 processes only four messages:
`WM_COMMAND, WM_SIZE, WM_PAINT, and WM_DESTROY. All other messages are
`passed to DefWindowProc. As is typical with most Windows programs written inc,
`SAMPLE uses a switch and case construction for processing messages.
`
`The WM_COMMAND message signals the program that the user has selected a new font
`from the menu. SAMPLE first obtains a handle to the menu and removes the checkmark
`from the previously selected font:
`
`hMenu = GetMenu (hWnd)
`;
`CheckMenuitem (hMenu, nCurrentFont, MF_UNCHECKED)
`
`;
`
`The value of wParam in the WM_COMMAND message is the menu ID of the newly
`selected font. SAMPLE saves that value in a static variable (nCurrentFont) and then places a
`checkmark on the new menu choice:
`
`nCurrentFont = wParam ;
`CheckMenuitem (hMenu, nCurrentFont, MF_CHECKED)
`
`;
`
`Because the typeface has changed, SAMPLE must repaint its display. The program does
`not repaint it immediately, however. Instead, it calls the InvalidateRect function:
`
`InvalidateRect (hWnd, NULL, TRUE)
`
`;
`
`This causes a WM_PAINT message to be placed in the program's message queue. The
`NULL parameter indicates that the entire client area should be repainted. The TRUE
`parameter indicates that the background should be erased.
`
`The WM_SIZE message indicates that the size of SAMPLE's client area has changed.
`SAMPLE simply saves the new dimensions of the client area in two static variables:
`
`xClient = LOWORD (lParam)
`yClient = HIWORD (lParam)
`
`;
`;
`
`The LOWORD and HIWORD macros are defined in WINDOWS. H.
`
`Windows also places a WM_PAINT message in SAMPLE's message queue when the size
`of the client area has changed. As is the case with WM_COMMAND, the program does
`not have to repaint the client area immediately, because the WM_ PAINT message is in the
`message queue.
`
`SAMPLE can receive a WM_PAINT message for many reasons. The first WM_PAINT mes(cid:173)
`sage it receives results from calling UpdateWindow in the WinMain function. Later, if the
`current font is changed from the menu, the program itself causes a WM_ PAINT message
`to be placed in the message queue by calling InvalidateRect. Windows also sends a win(cid:173)
`dow function a WM_ PAINT message whenever the user changes the size of the window
`or when part of the window previously covered by another window is uncovered.
`
`Programs begin processing WM_PAINT messages by calling Begin Paint:
`
`BeginPaint (hWnd, &ps)
`
`;
`
`Section II: Programming in the MS-DOS Environment
`
`527
`
`HUAWEI EX. 1110 - 537/1582
`
`
`
`Part D: Directions of MS-DOS
`
`The SAMPLE program then creates a font based on the current size of the client area and
`the current typeface selected from the menu:
`
`hFont = CreateFont (yClient, xClient I 8,
`0, O, 400, 0, 0, 0, OEM_CHARSET,
`OUT_STROKE_pRECIS, OUT_STROKE_pRECIS,
`DRAFT-QUALITY,
`(BYTE) VARIABLE_piTCH
`cFamily [nCurrentFont- IDM___SCRIPT],
`szFace
`[nCurrentFont- IDM___SCRIPT])
`
`The font is selected into the device context (a data structure internal to Windows that
`describes the characteristics of the output device); the program also saves the original
`device-context font:
`
`hFont = SelectObject (ps.hdc, hFont)
`
`And the word Windows is displayed:
`
`TextOut (ps.hdc, 0, 0, "Windows", 7)
`
`The original font in the device context is then selected, and the font that was created is
`now deleted:
`
`DeleteObject (SelectObject (ps.hdc, hFont))
`
`;
`
`Finally, SAMPLE calls EndPaint to signal Windows that the client area is now updated and
`valid:
`
`EndPaint (hWnd, &ps)
`
`;
`
`Although the processing of the WM_ PAINT message in this program is simple, the
`method used is common to all Windows programs. The Begin Paint and End Paint func(cid:173)
`tions always occur in pairs, first to get information about the area that needs repainting
`and then to mark that area as valid.
`
`SAMPLE will display this text even when the program is minimized to be displayed as an
`icon at the bottom of the screen. Although most Windows programs use a customized icon
`for this purpose, the window-class structure in SAMPLE indicates that the program's icon
`is NULL, meaning that the program is responsible for drawing its own icon. SAMPLE does
`not, however, make any special provisions for drawing the icon. To it, the icon is simply
`a small client area. As a result, SAMPLE displays the word Windows in its "icon," using a
`small font size.
`
`Windows sends the window function the WM_DESTROY message as a result of the
`DestroyWindow function that DefWindowProc calls when processing a WM_ CLOSE
`message. The standard processing involves placing a WM_QUIT message in the message
`queue:
`
`PostQuitMessage (0)
`
`;
`
`When the GetMessage function retrieves WM_QUIT from the message queue, GetMessage
`returns 0. This terminates the message loop and the program.
`
`528
`
`The MS-DOS Encyclopedia
`
`HU