Difference between revisions of "Win messages"

From Team Developer SqlWindows Wiki
Jump to: navigation, search
m (Added download link to MouseLeaveWindow sample)
(Added tip on SysColors)
Line 230: Line 230:
 
The Reason to have a Return FALSE in the On WM_CHAR message is, that otherwise a SPACE-Character would be printed. But in this way nothing will happens.
 
The Reason to have a Return FALSE in the On WM_CHAR message is, that otherwise a SPACE-Character would be printed. But in this way nothing will happens.
  
TODO Translate in correct English and proof if the Links are copied in the right way...
+
TODO Translate in correct English and proof if the Links are copied in the right way...<br>
 +
<br>
 +
<!--------------------------------------------------------------------------------------------------------------------------------------------------------------------------->
 +
{{TipHeader|How to detect SysColors have changed}}
 +
 
 +
When the user changes the Windows theme or changes any colors for the several GUI elements, Windows will send<br>
 +
message [http://msdn.microsoft.com/en-us/library/ms532603(VS.85).aspx <b>WM_SYSCOLORCHANGE</b>] to all top level windows currently present in the system.<br>
 +
<br>
 +
When your application is depending or anticipating on special colors, you might want to be informed the System colors have changed.<br>
 +
For instance when you do custom painting or display icons/bitmaps in predefined colors and you want to repaint them in the correct wanted color.<br>
 +
<br>
 +
First declare this constant
 +
<pre>
 +
Number: WM_SYSCOLORCHANGE  = 0x0015
 +
</pre>
 +
 
 +
Now, trap this message on top level windows. Also send the message to all children to inform them.<br>
 +
 
 +
<pre>
 +
Form Window: frmMain
 +
  Message actions
 +
      On WM_SYSCOLORCHANGE
 +
        Call SalSendMsgToChildren( hWndForm, WM_SYSCOLORCHANGE, wParam, lParam )
 +
</pre>
 +
 
 +
Now, depending on your needs, update used icons/bitmaps or repaint the custom drawings.<br>
 +
<br>
 +
To get the colors set by the user, you can use the WinAPI function [http://msdn.microsoft.com/en-us/library/ms724371(VS.85).aspx <b>GetSysColor</b>].<br>
 +
<br>
 +
This is the declaration
 +
 
 +
<pre>
 +
Library name: USER32.dll
 +
  Function: GetSysColor
 +
      Returns
 +
        Number: DWORD
 +
      Parameters
 +
        Number: INT
 +
</pre>
 +
Use the default WinAPI SysColor index values for the input parameter.<br>
 +
You can find the complete list of color index values on [http://msdn.microsoft.com/en-us/library/ms724371(VS.85).aspx <b>GetSysColor</b>].<br>
 +
Or you can find them in SalExtension library and in the sample supplied here.<br>
 +
<br>
 +
The next sample shows :<br>
 +
*Detect changes in SysColors
 +
*Show all current SysColors (as picture backround colors, RGB values or color values)
 +
*Set SysColors from the sample (using SetSysColors WinAPI). (Beware, it is a system wide setting, not only within the application)
 +
<br>
 +
Here you can download the sample:
 +
*[http://samples.tdcommunity.net/index.php?dir=&file=WIKI_SysColorChange.zip WIKI_SysColorChange.zip]<br>
 +
<br>
  
  
 
[[Category:Windows API]]
 
[[Category:Windows API]]

Revision as of 14:51, 22 December 2008

This page covers Windows messages for various features.

Contents


Pointer2.png How to detect mouse leaving a window Pointer.png

When the mouse cursor is leaving a window a message is send to the window indicating this.
But to enable this feature, you will have to call the Windows API function TrackMouseEvent first to register the window.

This is the declaration for TrackMouseEvent

Library name: USER32.DLL
   Function: TrackMouseEvent
      Export Ordinal: 0
      Returns
         Boolean: BOOL
      Parameters
         structPointer
            Number: DWORD
            Number: DWORD
            Window Handle: HWND
            Number: DWORD

The following list of possible constant declarations for the function TrackMouseEvent

(The NC constants are for the non-client area's like caption or borders)

! Below the flags for TrackMouseEvent

Number: TME_HOVER         = 0x0001
Number: TME_LEAVE         = 0x0002
Number: TME_NONCLIENT     = 0x0010

! Below the message constants being send on notification

Number: WM_NCMOUSEHOVER   = 0x02A0
Number: WM_MOUSEHOVER     = 0x02A1
Number: WM_NCMOUSELEAVE   = 0x02A2
Number: WM_MOUSELEAVE     = 0x02A3

! Below the mousemove message as used in the sample

Number: WM_MOUSEMOVE     = 0x0200

To register a window to receive messages when leaving or hovering the window

! Below register window to receive LEAVE notification
Call TrackMouseEvent( 16, TME_LEAVE, hWndForm, 1 )

! Below register window to receive HOVER notification
Call TrackMouseEvent( 16, TME_HOVER, hWndForm, 400 )

The next sample shows an implementation of this feature.
When the user moves the mouse within the window, the message WM_MOUSEMOVE is received.
There the window will be registered to be notified when the mouse is leaving.
A boolean (wbTracking) is used to hold if the window is allready registered.

The window will be registered until it receives a notification.

Form Window: frmSample
   Window Variables
      Boolean: wbTracking
   Message Actions
      On WM_MOUSELEAVE
         ! The mouse is leaving the window, do custom actions here
         Set wbTracking = FALSE
      On WM_MOUSEMOVE
         If NOT wbTracking
            If TrackMouseEvent( 16, TME_LEAVE, hWndForm, 1 )
               Set wbTracking = TRUE

Here you can download a sample:


Pointer2.png How to detect (double) clicks on a window Pointer.png

Several windows messages are send to the window when clicking.

WM_LBUTTONDOWN
Received when the user presses the left mousebutton
WM_LBUTTONUP
Received when the user releases the left mousebutton
WM_LBUTTONDBLCLK
Received when the user doubleclicks the left mousebutton
WM_RBUTTONDOWN
Received when the user presses the right mousebutton
WM_RBUTTONUP
Received when the user releases the right mousebutton
WM_RBUTTONDBLCLK
Received when the user doubleclicks the right mousebutton


Below the constant declarations for the messages

! Left button
Number: WM_LBUTTONDOWN    = 0x0201
Number: WM_LBUTTONUP      = 0x0202
Number: WM_LBUTTONDBLCLK  = 0x0203
! Right button
Number: WM_RBUTTONDOWN    = 0x0204
Number: WM_RBUTTONUP      = 0x0205
Number: WM_RBUTTONDBLCLK  = 0x0206

TODO MIDDLE AND X BUTTONS (INCL NC CLICKS)

Pointer2.png How to drag a window without a caption Pointer.png

When a window does not have a caption or you want to be able to drag a window while clicking anywhere on the window, this is the easiest way.

First you will have to declare the next constants.

Number: WM_NCLBUTTONDOWN	= 0x00A1
Number: WM_LBUTTONDOWN         = 0x0201
Number: HTCAPTION		= 2

When clicking on a window (anywhere in the client area) send a message to the window indicating the mouse is within the caption area.

Form Window: frmSample
   Message Actions
      On WM_LBUTTONDOWN
         ! The user clicks somewhere in the client area of the window.
         ! Send a message to trick windows the user has clicked on the caption.
         ! While moving the mouse, the window will be dragged
         Call SalSendMsg( hWndForm, WM_NCLBUTTONDOWN, HTCAPTION, NUMBER_Null )


Here you can download a sample:


Pointer2.png How to detect/suppress system commands from a window (minimise, maximise, close etc) Pointer.png

A window receives the WM_SYSCOMMAND message when the user presses any of the syscommand options of a window.
First you will have to declare the constant for this message

Number: WM_SYSCOMMAND   = 0x0112

The wParam of this message contains the action taken.
Next is a list of all possible action values.

Number: SC_MAXIMIZE         = ????
TODO LIST

Catch the message and determine which action was taken

wParam & 0xFFF0

TODO


Pointer2.png How to detect that CTRL + SPACE was pressed within an graphical Object Pointer.png

The WM_CHAR message is posted to the window with the keyboard focus when a WM_KEYDOWN message is translated by the TranslateMessage function. The WM_CHAR message contains the character code of the key that was pressed. For Unicode there is also a WM_UNICHAR Message.
First you will have to declare the constant for this message

Number: WM_CHAR   = 0x0102

The wParam specifies the character code of the key.
The lParam specifies the repeat count, scan code, extended-key flag, context code, previous key-state flag, and transition-state flag, as shown in the following table.

0-15
    Specifies the repeat count for the current message. 
    The value is the number of times the keystroke is autorepeated as a result of the user holding down the key. 
    If the keystroke is held long enough, multiple messages are sent. However, the repeat count is not cumulative.
16-23
    Specifies the scan code. The value depends on the OEM.
24
    Specifies whether the key is an extended key, such as the right-hand ALT and CTRL keys that appear on an 
    enhanced 101- or 102-key keyboard. The value is 1 if it is an extended key; otherwise, it is 0.
25-28
    Reserved; do not use.
29
    Specifies the context code. The value is 1 if the ALT key is held down while the key is pressed; otherwise, the value is 0.
30
    Specifies the previous key state. The value is 1 if the key is down before the message is sent, or it is 0 if the key is up.
31
    Specifies the transition state. The value is 1 if the key is being released, or it is 0 if the key is being pressed.

Catch the message and determine with GetKeyState which Keys has been pressed

On WM_CHAR
   If GetKeyState( VK_CONTROL ) < 0 AND GetKeyState( VK_SPACE ) < 0
      Return FALSE

To have the GetKeyState Function availible you need to declare it in USER32.DLL like the following:

Global Declarations
   External Functions
      Library Name: USER32.DLL
         Function: GetKeyState
            Export Ordinal: 0
            Return: Number: SHORT
            Parameters: Number: INT

The Constants VK_CONTROLL and VK_SPACE are the following:

Number: VK_CONTROLL   = 0x0011
Number: VK_SPACE      = 0x0020

The Reason to have a Return FALSE in the On WM_CHAR message is, that otherwise a SPACE-Character would be printed. But in this way nothing will happens.

TODO Translate in correct English and proof if the Links are copied in the right way...

Pointer2.png How to detect SysColors have changed Pointer.png

When the user changes the Windows theme or changes any colors for the several GUI elements, Windows will send
message WM_SYSCOLORCHANGE to all top level windows currently present in the system.

When your application is depending or anticipating on special colors, you might want to be informed the System colors have changed.
For instance when you do custom painting or display icons/bitmaps in predefined colors and you want to repaint them in the correct wanted color.

First declare this constant

Number: WM_SYSCOLORCHANGE  = 0x0015

Now, trap this message on top level windows. Also send the message to all children to inform them.

Form Window: frmMain
   Message actions
      On WM_SYSCOLORCHANGE
         Call SalSendMsgToChildren( hWndForm, WM_SYSCOLORCHANGE, wParam, lParam )

Now, depending on your needs, update used icons/bitmaps or repaint the custom drawings.

To get the colors set by the user, you can use the WinAPI function GetSysColor.

This is the declaration

Library name: USER32.dll
   Function: GetSysColor
      Returns
         Number: DWORD
      Parameters
         Number: INT

Use the default WinAPI SysColor index values for the input parameter.
You can find the complete list of color index values on GetSysColor.
Or you can find them in SalExtension library and in the sample supplied here.

The next sample shows :

  • Detect changes in SysColors
  • Show all current SysColors (as picture backround colors, RGB values or color values)
  • Set SysColors from the sample (using SetSysColors WinAPI). (Beware, it is a system wide setting, not only within the application)


Here you can download the sample: