Page 1 of 2

Msgbox centered on the window

Posted: Sun Nov 06, 2011 3:39 pm
by Marco Turco
Hi all,
I need to center the msgbox (example: Msginfo, MsgNoYes etc.) automatically on my windows instead of the screen.
I tried SetCenterOnParent(.t.) but this runs only for dialogs.

Any solution ? Thanks in advance

Re: Msgbox centered on the window

Posted: Mon Nov 07, 2011 7:34 am
by José Luis Sánchez
Use this code:

Code: Select all

   ACTIVATE DIALOG oDlgInfo ;
      ON INIT oDlgInfo:Center( oApp():oWndMain )
where oDlgInfo is your dialog and oApp():oWndMain the main window of the application.

Regards,

Re: Msgbox centered on the window

Posted: Tue Nov 08, 2011 12:53 pm
by Marco Turco
Hi José,
your solution runs only with dialogs not with the msgbox functions.
The only running solution I have found is to make new function dialogs based for the msgbox functions.

Re: Msgbox centered on the window

Posted: Tue Nov 08, 2011 9:26 pm
by José Luis Sánchez
Marco,
I've the msgbox functions redefined based on dialogs, and for this runs ok in my programs.
Regards,

Re: Msgbox centered on the window

Posted: Sun Jul 19, 2015 3:22 pm
by Massimo Linossi
Hello Josè.
I have the same problem of Marco. Is possible to see your functions ?
Thanks a lot.
Massimo

Re: Msgbox centered on the window

Posted: Sun Jul 19, 2015 5:56 pm
by Antonio Linares
Here there is some code that we could try to adapt to FWH:

http://vbnet.mvps.org/index.html?code/h ... centre.htm

Re: Msgbox centered on the window

Posted: Sun Jul 19, 2015 6:13 pm
by Massimo Linossi
It would be great.
Thanks Antonio.

Re: Msgbox centered on the window

Posted: Sun Jul 19, 2015 10:27 pm
by Antonio Linares
This is already working

Code: Select all

#pragma BEGINDUMP

#include <windows.h>
#include <hbapi.h>

LRESULT CALLBACK MsgBoxHookProc( int nCode, WPARAM wParam, LPARAM lParam )
{
   if( nCode == HCBT_ACTIVATE )
   {
      HWND hWndMsgBox = wParam;
      
      SetWindowText( hWndMsgBox, "It works" );      
   }        
    
   return 0; // allow normal processing
}

HINSTANCE GetInstance( void );

HB_FUNC( CENTERMSGS )
{
   hb_retptr( ( void * ) SetWindowsHookEx( WH_CBT,  
                                MsgBoxHookProc, GetInstance(), 
                                GetCurrentThreadId() ) );
}

#pragma ENDDUMP
 
Now we need to find a way to locate the active window. I guess that the idea is to set this for the entire app.

Here you have an example:

Code: Select all

#include "FiveWin.ch"

//----------------------------------------------------------------------------//

function Main()

   local oWnd

   DEFINE WINDOW oWnd
   
   CenterMsgs()
    
   ACTIVATE WINDOW oWnd ;
      ON CLICK  MsgInfo( "Hello world" )
   
return nil

Re: Msgbox centered on the window

Posted: Sun Jul 19, 2015 11:05 pm
by Antonio Linares
In this version we are already able to move the Msg... window:

Code: Select all

static HHOOK hHook = NULL;

LRESULT CALLBACK MsgBoxHookProc( int nCode, WPARAM wParam, LPARAM lParam )
{
   if( nCode < 0 )  // do not process message 
        return CallNextHookEx( hHook, nCode, wParam, lParam ); 

   if( nCode == HCBT_CREATEWND )
   {
      HWND hWndMsgBox = wParam; 
      char cn[ 200 ];
            
      GetClassName( hWndMsgBox, cn, 199 );      

      if( cn[ 0 ] == '#' &&
          cn[ 1 ] == '3' &&
          cn[ 2 ] == '2' &&
          cn[ 3 ] == '7' &&
          cn[ 4 ] == '7' &&
          cn[ 5 ] == '0' &&
          cn[ 6 ] == 0 )
      {     
         ( ( CBT_CREATEWND * ) lParam )->lpcs->x = 50;
         ( ( CBT_CREATEWND * ) lParam )->lpcs->y = 50;
      }             
   }        
   
   return 0; // allow normal processing
}

HINSTANCE GetInstance( void );

HB_FUNC( CENTERMSGS )
{
   hHook = SetWindowsHookEx( WH_CBT,  
                             MsgBoxHookProc, GetInstance(), 
                             GetCurrentThreadId() );
}
 
Still we need to get the handle of the parent window

Re: Msgbox centered on the window

Posted: Sun Jul 19, 2015 11:53 pm
by Antonio Linares
Ok, this one seems to be working fine :-)

Still we need to implement a function to remove the hook.

Code: Select all

static HHOOK hHook = NULL;

static void CenterWindowOnParent( HWND hChildWnd, LPARAM lParam )
{
   HWND hParent = GetParent( hChildWnd );
   RECT rcChild, rcParent;
   int cxChild, cyChild, cxParent, cyParent;

   GetWindowRect( hChildWnd, &rcChild );
   GetWindowRect( hParent, &rcParent );

   cxChild = rcChild.right - rcChild.left;
   cyChild = rcChild.bottom - rcChild.top;
   cxParent = rcParent.right - rcParent.left;
   cyParent = rcParent.bottom - rcParent.top;
   
   SetWindowPos( hChildWnd, NULL, 
               rcParent.left + ( cxParent - cxChild ) / 2, 
                 rcParent.top + ( cyParent - cyChild ) / 2, 0, 0, 0x15 );       
}

LRESULT CALLBACK MsgBoxHookProc( int nCode, WPARAM wParam, LPARAM lParam )
{
   if( nCode < 0 )  // do not process message 
        return CallNextHookEx( hHook, nCode, wParam, lParam ); 

   if( nCode == HCBT_ACTIVATE )
   {
      HWND hWndMsgBox = ( HWND ) wParam;    
      char cn[ 200 ];
            
      GetClassName( hWndMsgBox, cn, 199 );      

      if( cn[ 0 ] == '#' &&
          cn[ 1 ] == '3' &&
          cn[ 2 ] == '2' &&
          cn[ 3 ] == '7' &&
          cn[ 4 ] == '7' &&
          cn[ 5 ] == '0' &&
          cn[ 6 ] == 0 )
         CenterWindowOnParent( hWndMsgBox, lParam );            
   }        
    
   return 0; // allow normal processing
}

HINSTANCE GetInstance( void );

HB_FUNC( CENTERMSGS )
{
   hHook = SetWindowsHookEx( WH_CBT,  
                             MsgBoxHookProc, GetInstance(), 
                             GetCurrentThreadId() );
}
 
Image

Re: Msgbox centered on the window

Posted: Mon Jul 20, 2015 3:48 am
by dutch
Dear Antonio,

The theme (Dialog, MsgBox) is so nice. Is this Win8 theme or standard screen? If so, can we make it the screen on other Windows version such as Win7 or WinXP.
Antonio Linares wrote:Ok, this one seems to be working fine :-)

Still we need to implement a function to remove the hook.

Code: Select all

static HHOOK hHook = NULL;

static void CenterWindowOnParent( HWND hChildWnd, LPARAM lParam )
{
   HWND hParent = GetParent( hChildWnd );
   RECT rcChild, rcParent;
   int cxChild, cyChild, cxParent, cyParent;

   GetWindowRect( hChildWnd, &rcChild );
   GetWindowRect( hParent, &rcParent );

   cxChild = rcChild.right - rcChild.left;
   cyChild = rcChild.bottom - rcChild.top;
   cxParent = rcParent.right - rcParent.left;
   cyParent = rcParent.bottom - rcParent.top;
   
   SetWindowPos( hChildWnd, NULL, 
               rcParent.left + ( cxParent - cxChild ) / 2, 
                 rcParent.top + ( cyParent - cyChild ) / 2, 0, 0, 0x15 );       
}

LRESULT CALLBACK MsgBoxHookProc( int nCode, WPARAM wParam, LPARAM lParam )
{
   if( nCode < 0 )  // do not process message 
        return CallNextHookEx( hHook, nCode, wParam, lParam ); 

   if( nCode == HCBT_ACTIVATE )
   {
      HWND hWndMsgBox = ( HWND ) wParam;    
      char cn[ 200 ];
            
      GetClassName( hWndMsgBox, cn, 199 );      

      if( cn[ 0 ] == '#' &&
          cn[ 1 ] == '3' &&
          cn[ 2 ] == '2' &&
          cn[ 3 ] == '7' &&
          cn[ 4 ] == '7' &&
          cn[ 5 ] == '0' &&
          cn[ 6 ] == 0 )
         CenterWindowOnParent( hWndMsgBox, lParam );            
   }        
    
   return 0; // allow normal processing
}

HINSTANCE GetInstance( void );

HB_FUNC( CENTERMSGS )
{
   hHook = SetWindowsHookEx( WH_CBT,  
                             MsgBoxHookProc, GetInstance(), 
                             GetCurrentThreadId() );
}
 
Image

Re: Msgbox centered on the window

Posted: Mon Jul 20, 2015 6:20 am
by ukoenig
I needed a solution, to display different messages
on any defined position and with any style ( color,brush, gradient, font, icon .... )

the sample shows a message displayed on left upper corner on button-action

Image

MYMSGBOX( .T., { 100, 50, 100, 300 }, ; // .F. = center
"< " + ALLTRIM(STR( nMenge1 )) + " > Patient(en) mit" + CRLF + ;
"< " + ALLTRIM(STR( nMenge2 )) + " > Verordnungen geprüft " + CRLF + ;
" " + CRLF + ;
"< " + ALLTRIM(STR( nMenge3 )) + " > Fehler gefunden", ;
{"&Weiter"}, "VERORDNUNGS-PRÜFUNG", "A", 1, ;
{{ nDColorB, nDColorB, nDColorB, nDColorB }}, , , , ;
oFontSys, aVal[27], c_Pfad1 + "Info1.bmp" )


YES / NO centered

Image

DO WHILE nOpt = 0
nOpt := MYMSGBOX( .F., { 10, 10, 100, 300 }, ;
"Wollen Sie den Monat : " + cNach + CRLF + ;
"neu aufbauen ?", ;
{"&Aufbau","A&bbruch"}, ;
"MONATSÜBERNAHME", ;
"O", 1, ;
{{ nDColorB, nDColorB, nDColorB, nDColorB }}, , , , ;
oFontSys, aVal[27], c_Pfad1 + "Sort.bmp" )
ENDDO

IF nOpt = 1
....
....


best regards
Uwe :)

Re: Msgbox centered on the window

Posted: Mon Jul 20, 2015 7:35 am
by Antonio Linares
Dutch,

I am using Windows 10 :-)
dutch wrote:Dear Antonio,

The theme (Dialog, MsgBox) is so nice. Is this Win8 theme or standard screen? If so, can we make it the screen on other Windows version such as Win7 or WinXP.
Antonio Linares wrote:Ok, this one seems to be working fine :-)

Still we need to implement a function to remove the hook.

Code: Select all

static HHOOK hHook = NULL;

static void CenterWindowOnParent( HWND hChildWnd, LPARAM lParam )
{
   HWND hParent = GetParent( hChildWnd );
   RECT rcChild, rcParent;
   int cxChild, cyChild, cxParent, cyParent;

   GetWindowRect( hChildWnd, &rcChild );
   GetWindowRect( hParent, &rcParent );

   cxChild = rcChild.right - rcChild.left;
   cyChild = rcChild.bottom - rcChild.top;
   cxParent = rcParent.right - rcParent.left;
   cyParent = rcParent.bottom - rcParent.top;
   
   SetWindowPos( hChildWnd, NULL, 
               rcParent.left + ( cxParent - cxChild ) / 2, 
                 rcParent.top + ( cyParent - cyChild ) / 2, 0, 0, 0x15 );       
}

LRESULT CALLBACK MsgBoxHookProc( int nCode, WPARAM wParam, LPARAM lParam )
{
   if( nCode < 0 )  // do not process message 
        return CallNextHookEx( hHook, nCode, wParam, lParam ); 

   if( nCode == HCBT_ACTIVATE )
   {
      HWND hWndMsgBox = ( HWND ) wParam;    
      char cn[ 200 ];
            
      GetClassName( hWndMsgBox, cn, 199 );      

      if( cn[ 0 ] == '#' &&
          cn[ 1 ] == '3' &&
          cn[ 2 ] == '2' &&
          cn[ 3 ] == '7' &&
          cn[ 4 ] == '7' &&
          cn[ 5 ] == '0' &&
          cn[ 6 ] == 0 )
         CenterWindowOnParent( hWndMsgBox, lParam );            
   }        
    
   return 0; // allow normal processing
}

HINSTANCE GetInstance( void );

HB_FUNC( CENTERMSGS )
{
   hHook = SetWindowsHookEx( WH_CBT,  
                             MsgBoxHookProc, GetInstance(), 
                             GetCurrentThreadId() );
}
 
Image

Re: Msgbox centered on the window

Posted: Mon Jul 20, 2015 9:23 am
by Horizon
Hi,

Should we call CenterMsgs() function just in main window or should we call before every MsgInfo function?

Re: Msgbox centered on the window

Posted: Mon Jul 20, 2015 9:35 am
by Antonio Linares
Hakan,

Just once at the beginning of your app.

And we should remove the hook before the app quits