Chapter 18: Solving Some Problems with Windows Programming

This chapter was a compromise for me. There are lots of problems in Windows programming, and my natural desire was to coyer them all. However, if I dedicated an entire chapter to every question, the book would soon be too large. Therefore, I decided to devote one chapter to problem-solving aspects and to cover in detail as many interesting problems as I could. This chapter is built on questions that you might ask and answers that I would provide.

Placing an Icon on the System Toolbar

Q. How can I ensure that the icon of the minimized application fits on the system toolbar?

This problem can be solved using the shell_NotifyIcon system function. This solution is so simple that I have to wonder why most programmers employ various libraries for this purpose. The shell_NotifyIcon function accepts the following parameters:

  • First parameterThe action that needs to be carried out

    • NIM_ADD equ 0h Add an icon to the system toolbar

    • NIM_MODIFY equ 1h Delete the icon from the system toolbar

    • NIM_DELETE equ 2h Modify the icon

  • Second parameterThe pointer to the structure that contains information required for carrying out the specified action

     NOTI_ICON STRUC       cbSize           DWORD ?       hWnd             DWORD ?       uID              DWORD ?       uFlags           DWORD ?       uCallbackMessage DWORD ?       hIcon            DWORD ?       szTip            DB 64 DUP (?)     NOTI_ICON ENDS 

The elements of the preceding structure are as follows :

  • cbSize Structure size .

  • hWnd Descriptor of the window, to which the message will be sent (described later).

  • uID Icon identifier.

  • uFlags Combination of the following flags:

    • NIF_MESSAGE equ 1h Use the hIcon field

    • NIF_ICON equ 2h Use the uCallbackMessage field

    • NIF_TIP equ 4h Use the szTip field

  • uCallbackMessage Message that arrives to the window identified by the hWnd descriptor if some event occurs near the system toolbar icon. The message value must be more than 1024. When this message arrives, WPARAM contains the icon identifier and LPARAM defines the event that occurred to the icon.

  • hIcon Icon handle.

  • SzTip Popup help text.

Consider how the entire mechanism operates. If the window is minimized, the WM_SIZE message arrives at the window function. In this message, wParam must contain the SIZE_MINIMIZED value. In this case, it is necessary to use the shell_NotifyIcon function that will place the icon to the system toolbar. Any event related to the mouse when its cursor is located over the icon would cause the uCallbackMessage to arrive at the window function. You have defined this message yourself. In this case, the most significant wParam word will contain the icon identifier, and the least significant lParam word will allow you to define the event type. Listing 18.1 demonstrates how this mechanism operates.

Listing 18.1: The procedure that places an icon on the system toolbar
image from book
 // The TRAY.RC file // Constant definitions #define WS_SYSMENU     0x00080000L #define WS_MINIMIZEBOX 0x00020000L #define WS_MAXIMIZEBOX Ox000l0000L #define DS_3DLOOK      0x0004L // Identifiers #define IDI_ICON1 1 // Define the icon IDI_ICON1 ICON "ico1.ico" // Dialog box definition DIAL1 DIALOG 0, 0, 250, 110 STYLE WS_SYSMENU  WS_MINIMIZEBOX  WS_MAXIMIZEBOX  DS_3DLOOK CAPTION "Place the icon on the system toolbar" FONT 8, "Arial" { } ; The TRAY.INC file ; Constants NIM_ADD           equ Oh ; Add the icon to the system toolbar NIM_MODIFY        equ 1h ; Remove the icon NIM_DELETE        equ 2h ; Modify the icon NIF_MESSAGE       equ 1h ; Use the hIcon field NIF_ICON          equ 2h ; Use the uCallbackMessage field NIF_TIP           equ 4h ; Use the szTip field FLAG              equ NIF_MESSAGE or NIF_ICON or NIF_TIP SIZE_MINIMIZED    equ 1h SW_HIDE           equ 0 SW_SHOWNORMAL     equ 1 ; This message arrives when the window is closed WM_CLOSE          equ 10h WM_INITDIALOG     equ 110h WM_SIZE           equ 5h WM_LBUTTONDBLCLK  equ 203h WM_LBUTTONDOWN    equ 201h ; Prototypes of external procedures IFDEF MASM        EXTERN ShowWindow@8:NEAR        EXTERN LoadIconA@8:NEAR        EXTERN lstrcpyA@8:NEAR        EXTERN Shell_NotifyIconA@8:NEAR        EXTERN ExitProcess@4:NEAR        EXTERN GetModuleHandleA@4:NEAR        EXTERN DialogBoxParamA@20:NEAR        EXTERN EndDialog@8:NEAR        EXTERN SendDlgItemMessageA@20:NEAR ELSE        EXTERN ShowWindow:NEAR        EXTERN LoadIconA:NEAR        EXTERN lstrcpyA:NEAR        EXTERN Shell_NotifyIconA:NEAR        EXTERN ExitProcess:NEAR        EXTERN GetModuleHandleA:NEAR        EXTERN DialogBoxParamA:NEAR        EXTERN EndDialog:NEAR        EXTERN SendDlgItemMessageA:NEAR        ShowWindow@8 = ShowWindow        LoadIconA@8 = LoadIconA        lstrcpyA@8 = lstrcpyA        Shell_NotifyIconA@8 = Shell_NotifyIconA        ExitProcess@4 = ExitProcess        GetModuleHandleA@4 = GetModuleHandleA        DialogBoxParamA@20 = DialogBoxParamA        EndDialog@8 = EndDialog        SendDlgItemMessageA@20 = SendDlgItemMessageA ENDIF ; Structures ; Message structure MSGSTRUCT STRUC        MSHWND    DD ?        MSMESSAGE DD ?        MSWPARAM  DD ?        MSLPARAM  DD ?        MSTIME    DD ?        MSPT      DD ? MSGSTRUCT ENDS ; Structure for the Shell_NotifyIcon function NOTI_ICON STRUC    cbSize        DWORD ?    hWnd             DWORD ?    uID              DWORD ?    uFlags           DWORD ?    uCallbackMessage DWORD ?    hIcon            DWORD ?    szTip            DB 64 DUP (?) NOTI_ICON ENDS ; The TRAY.ASM file .586P ; Flat memory model .MODEL FLAT, stdcall include tray.inc ; INCLUDELIB directives for the linker IFDEF MASM        includelib c:\masm32\lib\user32.lib        includelib c:\masm32\lib\kernel32.lib        includelib c:\masm32\lib\shell32.lib ELSE        includelib c:\tasm32\lib\import32.lib ENDIF ;------------------------------------------------ ; Data segment _DATA SEGMENT        MSG   MSGSTRUCT  <?>        HINST DD 0 ; Application descriptor        PA    DB "DIAL1", 0        NOTI  NOTI_ICON  <0>        TIP   DB "Example of using the function"              DB "Shell_NotifyIcon", 0 _DATA ENDS ; Code segment _TEXT SEGMENT START: ; Get the application handle        PUSH  0        CALL  GetModuleHandleA@4        MOV   [HINST], EAX ;--------------------------------        PUSH  0        PUSH  OFFSET WNDPROC        PUSH  0        PUSH  OFFSET PA        PUSH  [HINST]        CALL  DialogBoxParamA@20        CMP   EAX, -1        JNE   KOL ; Error message KOL: ;--------------------------------        PUSH  0        CALL  ExitProcess@4 ;-------------------------------- ; Window procedure ; Position of parameters in the stack ; [EBP+014H] ; LPARAM ; [EBP+10H]  ; WAPARAM ; [EBP+0CH]  ; MES ; [EBP+8]    ; HWND WNDPROC    PROC        PUSH EBP        MOV  EBP, ESP        PUSH EBX        PUSH ESI        PUSH EDI ;--------------        CMP  DWORD PTR [EBP+0CH], WM_CLOSE        JNE  L1        PUSH 0        PUSH DWORD PTR [EBP+08H]        CALL EndDialog@8        JMP  FINISH L1:        CMP  DWORD..PTR [EBP+0CH],. WM_INITDIALOG        JNE  L2        JMP  FINISH L2:        CMP  DWORD PTR [EBP+0CH], WM_SIZE        JNE  L3        CMP  DWORD PTR [EBP+10H], SIZE_MINIMIZED        JNE  . L3 ; Here, all work related to setting the icon ; on the system toolbar is carried out        MOV  NOTI.cbSize, 88        MOV  EAX, DWORD PTR [EBP+8H]        MOV  NOTI.hWnd, EAX        MOV  NOTI.uFlags, FLAG        MOV  NOTI.uID, 12 ; Icon identifier        MOV  NOTI.uCallbackMessage, 2000 ; Message ; Load an icon from the resources        PUSH 1        PUSH [HINST]        CALL LoadIconA@8 ; Copy the popup help message        MOV  NOTI.hIcon, EAX        PUSH OFFSET TIP        PUSH OFFSET NOTI.SzTip        CALL lstrcpyA@8 ; Place the icon        PUSH OFFSET NOTI        PUSH NIM_ADD        CALL Shell_NotifyIconA@8 ; Hide the minimized window        PUSH SW_HIDE        PUSH DWORD PTR [EBP+08H]        CALL ShowWindow@8        JMP  FINISH L3: ; Message from the toolbar icon?        CMP  DWORD PTR [EBP+0CH], 2000        JNE  FINISH ; Identifier of the icon?        CMP  WORD PTR [EBP+10H], 12        JNE  FINISH ; What happened? Was it a double click?        CMP  WORD PTR [EBP+14H], WM_LBUTTONDBLCLK        JNE  FINISH ; Fill the structure        MOV  NOTI.cbSize, 88        MOV  EAX, DWORD PTR [EBP+8H]        MOV  NOTI.hWnd, EAX        MOV  NOTI.uFlags, NIF_ICON        MOV  NOTI.uID, 12 ; Icon identifier        MOV  NOTI.uCallbackMessage, 1000 ; Message ; Delete the icon        PUSH OFFSET NOTI        PUSH NIM_DELETE        CALL Shell_NotifyIconA@8 ; Restore the window        PUSH SW_SHOWNORMAL        PUSH DWORD PTR [EBP+08H]        CALL,ShowWindow@8 FINISH:        MOV  EAX, 0        POP  EDI        POP  ESI        POP  EBX        POP  EBP        RET  16 WNDPROC   ENDP _TEXT ENDS END START 
image from book
 

To translate the program from Listing 18.1, issue the following commands for MASM32:

 ml /c /coff /DMASM tray.asm     rc tray.rc     link /subsystem:windows tray.obj tray.res 

Issue the following commands for TASM32:

 tasm32 /ml tray.asm     brcc32 tray.rc     tlink32 -aa tray.obj,,,,,tray.res 

In relation to the program from Listing 18.1, I'd like to draw your attention to the WM_SIZE message. It's very useful. Assume that you have placed some information in your window. If this window can be resized, you'll have to solve the problem of positioning the information in the window every time it is resized. This message can be used if you carefully redraw and rescale the window output. It is necessary to point out that when the message is sent, the window size has already changed, WPARAM contains the flag specifying what has happened to the window, and LPARAM gives the new window size (the least significant word is for the width, and the most significant word is for the height).



The Assembly Programming Master Book
The Assembly Programming Master Book
ISBN: 8170088178
EAN: 2147483647
Year: 2004
Pages: 140
Authors: Vlad Pirogov

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net