/*---------------------------------------------------------------------------- MINIGUI - Harbour Win32 GUI library source code Copyright 2002-2010 Roberto Lopez <harbourminigui@gmail.com> http://harbourminigui.googlepages.com/ MDI window source code (C)2005 Janusz Pora <januszpora@onet.eu> This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this software; see the file COPYING. If not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA (or visit the web site http://www.gnu.org/). As a special exception, you have permission for additional uses of the text contained in this release of Harbour Minigui. The exception is that, if you link the Harbour Minigui library with other files to produce an executable, this does not by itself cause the resulting executable to be covered by the GNU General Public License. Your use of that executable is in no way restricted on account of linking the Harbour-Minigui library code into it. Parts of this project are based upon: "Harbour GUI framework for Win32" Copyright 2001 Alexander S.Kresin <alex@belacy.belgorod.su> Copyright 2001 Antonio Linares <alinares@fivetech.com> www - http://harbour-project.org "Harbour Project" Copyright 1999-2012, http://harbour-project.org/ "WHAT32" Copyright 2002 AJ Wos <andrwos@aust1.net> "HWGUI" Copyright 2001-2009 Alexander S.Kresin <alex@belacy.belgorod.su> ---------------------------------------------------------------------------*/ #define WINVER 0x0500 /* #define _WIN32_IE 0x0500 #ifdef __POCC__ #define _WIN32_WINNT 0x0500 #else // #define _WIN32_WINNT 0x0400 #define _WIN32_WINNT 0x0501 #endif */ #include "c_ver.h" #define WM_TASKBAR WM_USER + 1043 #include <windows.h> #include <TChar.h> #include "hbapi.h" #include "hbvm.h" #include <commctrl.h> #include "c_winbk9.h" #ifdef __XHARBOUR__ #define HB_PARNI( n, x ) hb_parni( n, x ) #define HB_STORNL( n, x, y ) hb_stornl( n, x, y ) #else #define HB_PARNI( n, x ) hb_parvni( n, x ) #define HB_STORNL( n, x, y ) hb_storvnl( n, x, y ) #endif LRESULT CALLBACK MdiWndProc ( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam ); LRESULT CALLBACK MdiChildWndProc ( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam ); static HWND hwndMDIClient; HB_FUNC( REGISTERMDIWINDOW ) { WNDCLASS WndClass; HBRUSH hbrush = 0; INITCOMMONCONTROLSEX cc; cc.dwSize = sizeof( INITCOMMONCONTROLSEX ); cc.dwICC = ICC_DATE_CLASSES | ICC_COOL_CLASSES | ICC_LISTVIEW_CLASSES | ICC_NATIVEFNTCTL_CLASS | ICC_PAGESCROLLER_CLASS | ICC_PROGRESS_CLASS | ICC_STANDARD_CLASSES | ICC_TAB_CLASSES | ICC_TREEVIEW_CLASSES | ICC_USEREX_CLASSES; ; InitCommonControlsEx( &cc ); memset( &WndClass, 0, sizeof( WNDCLASS ) ); WndClass.style = CS_DBLCLKS; // CS_HREDRAW | CS_VREDRAW | CS_DBLCLKS; WndClass.lpfnWndProc = MdiWndProc; WndClass.cbClsExtra = 0; WndClass.cbWndExtra = 0; WndClass.hInstance = GetModuleHandle( NULL ); WndClass.hIcon = LoadIcon( GetModuleHandle(NULL), hb_parc_t(1) ); if( WndClass.hIcon == NULL ) WndClass.hIcon = ( HICON ) LoadImage( 0, hb_parc_t(1), IMAGE_ICON, 0, 0, LR_LOADFROMFILE + LR_DEFAULTSIZE ); if( WndClass.hIcon == NULL ) WndClass.hIcon = LoadIcon( NULL, IDI_APPLICATION ); WndClass.hCursor = LoadCursor( NULL, IDC_ARROW ); if( HB_PARNI(3, 1) == -1 ) WndClass.hbrBackground = ( HBRUSH ) ( COLOR_WINDOW + 1 ); else { hbrush = CreateSolidBrush( RGB(HB_PARNI(3, 1), HB_PARNI(3, 2), HB_PARNI(3, 3) ) ); WndClass.hbrBackground = hbrush; } WndClass.lpszMenuName = NULL; WndClass.lpszClassName = hb_parc_t( 2 ); if( !RegisterClass(&WndClass) ) { MessageBox( 0, _TEXT("Window MDI Registration Failed!"), _TEXT("Error!"), MB_ICONEXCLAMATION | MB_OK | MB_SYSTEMMODAL ); ExitProcess( 0 ); } WndClass.style = 0; WndClass.lpfnWndProc = ( WNDPROC ) MdiChildWndProc; WndClass.cbClsExtra = 0; WndClass.cbWndExtra = 20; WndClass.hInstance = GetModuleHandle( NULL );; // Owner of this class WndClass.hIcon = LoadIcon( GetModuleHandle(NULL), hb_parc_t(1) ); if( WndClass.hIcon == NULL ) WndClass.hIcon = ( HICON ) LoadImage( 0, hb_parc_t(1), IMAGE_ICON, 0, 0, LR_LOADFROMFILE + LR_DEFAULTSIZE ); if( WndClass.hIcon == NULL ) WndClass.hIcon = LoadIcon( NULL, IDI_APPLICATION ); WndClass.hCursor = LoadCursor( NULL, IDC_ARROW ); if( HB_PARNI(3, 1) == -1 ) WndClass.hbrBackground = ( HBRUSH ) ( COLOR_WINDOW + 1 ); else WndClass.hbrBackground = hbrush; WndClass.lpszMenuName = NULL; WndClass.lpszClassName = _TEXT("MdiChildWndClass"); if( !RegisterClass( ( LPWNDCLASS ) &WndClass) ) { MessageBox( 0, _TEXT("Window MdiChild Registration Failed!"), _TEXT("Error!"), MB_ICONEXCLAMATION | MB_OK | MB_SYSTEMMODAL ); ExitProcess( 0 ); } hb_retnl( ( LONG ) hbrush ); } LRESULT CALLBACK MdiWndProc ( HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam ) { static PHB_SYMB pSymbol = NULL; long int r; // ------------------- Win32 ------------------------------------ // Запрос из другого прцесса. Дай полный Номер ! if( message==WM_WIN32_POST_FAQ ) return OnEventWM_GetBase_NNN(); // Разбор сигнала из другой программы и послать PostMSG if( message==WM_COPYDATA) return OnEventWM_CopyData( lParam ); // ------------------- Win32 ------------------------------------ if( !pSymbol ) pSymbol = hb_dynsymSymbol( hb_dynsymGet("EVENTS") ); if( pSymbol ) { hb_vmPushSymbol( pSymbol ); hb_vmPushNil(); hb_vmPushLong( ( LONG ) hWnd ); hb_vmPushLong( message ); hb_vmPushLong( wParam ); hb_vmPushLong( lParam ); hb_vmDo( 4 ); } r = hb_parnl( -1 ); if( r == 0 ) return DefFrameProc(hWnd, hwndMDIClient, message, wParam, lParam); return ((r==2)? 0 : r); } LRESULT CALLBACK MdiChildWndProc ( HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam ) { static PHB_SYMB pSymbol = NULL; long int r; // ------------------- Win32 ------------------------------------ // Запрос из другого прцесса. Дай полный Номер ! if( message==WM_WIN32_POST_FAQ ) return OnEventWM_GetBase_NNN(); // Разбор сигнала из другой программы и послать PostMSG if( message==WM_COPYDATA) return OnEventWM_CopyData( lParam ); // ------------------- Win32 ------------------------------------ if( !pSymbol ) pSymbol = hb_dynsymSymbol( hb_dynsymGet("MDIEVENTS") ); if( pSymbol ) { hb_vmPushSymbol( pSymbol ); hb_vmPushNil(); hb_vmPushLong( ( LONG ) hWnd ); hb_vmPushLong( message ); hb_vmPushLong( wParam ); hb_vmPushLong( lParam ); hb_vmDo( 4 ); } r = hb_parnl( -1 ); if( r == 0 ) return DefMDIChildProc( hWnd, message, wParam, lParam ); return r; } HB_FUNC( INITMDIWINDOW ) { HWND hwnd; int Style = WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_BORDER | WS_SYSMENU | WS_THICKFRAME; int ExStyle; if( hb_parl(16) ) ExStyle = WS_EX_CONTEXTHELP; else { ExStyle = 0; if( !hb_parl(6) ) Style = Style | WS_MINIMIZEBOX; if( !hb_parl(7) ) Style = Style | WS_MAXIMIZEBOX; } if( !hb_parl(8) ) Style = Style | WS_SIZEBOX; if( !hb_parl(9) ) Style = Style | WS_SYSMENU; if( !hb_parl(10) ) Style = Style | WS_CAPTION; if( hb_parl(11) ) ExStyle = ExStyle | WS_EX_TOPMOST; if( hb_parl(14) ) Style = Style | WS_VSCROLL; if( hb_parl(15) ) Style = Style | WS_HSCROLL; hwnd = CreateWindowEx ( ExStyle, hb_parc_t(12), hb_parc2_t(1), Style, hb_parni(2), hb_parni(3), hb_parni(4), hb_parni(5), ( HWND ) hb_parnl(13), ( HMENU ) NULL, GetModuleHandle(NULL), NULL ); if( hwnd == NULL ) { MessageBox( 0, _TEXT("MDI Window Creation Failed!"), _TEXT("Error!"), MB_ICONEXCLAMATION | MB_OK | MB_SYSTEMMODAL ); return; } hb_retnl( ( LONG ) hwnd ); } HB_FUNC( INITMDICLIENTWINDOW ) { HWND hwndparent; int icount; CLIENTCREATESTRUCT ccs; memset( &ccs, 0, sizeof( ccs ) ); hwndparent = ( HWND ) hb_parnl( 1 ); icount = GetMenuItemCount( GetMenu(hwndparent) ); // Find window menu where children will be listed ccs.hWindowMenu = GetSubMenu( GetMenu(hwndparent), icount - 2 ); ccs.idFirstChild = 1000; // 0; // Create the MDI client filling the client area hwndMDIClient = CreateWindow ( _TEXT("mdiclient"), NULL, WS_CHILD | WS_CLIPCHILDREN | WS_CLIPSIBLINGS | WS_VSCROLL | WS_HSCROLL | WS_VISIBLE, 0, 0, 0, 0, hwndparent, ( HMENU ) 0xCAC, GetModuleHandle(NULL), ( LPSTR ) &ccs ); ShowWindow( hwndMDIClient, SW_SHOW ); hb_retnl( ( LONG ) hwndMDIClient ); } HB_FUNC( INITMDICHILDWINDOW ) { HWND hwndChild; MDICREATESTRUCT mcs; TCHAR rgch[ 150 ]; static int cUntitled; int Style = 0; if( hb_parl(9) ) // Заголовок rgch[ 0 ] = 0; else { if( hb_parc_t(2) == NULL ) wsprintf( rgch, _TEXT("Untitled%d"), cUntitled++ ); else { lstrcpyn( rgch, hb_parc_t(2), 149 ); rgch[ 149 ] = 0; } } if( !hb_parl(7) ) Style = Style | WS_MINIMIZE; // BOX; if( !hb_parl(8) ) Style = Style | WS_MAXIMIZE; // BOX; if( hb_parl(10) ) Style = Style | WS_VSCROLL; if( hb_parl(11) ) Style = Style | WS_HSCROLL; // Create the MDI child window mcs.szClass = _TEXT("MdiChildWndClass"); // window class name mcs.szTitle = rgch; // window title mcs.hOwner = GetModuleHandle( NULL ); // owner mcs.x = hb_parni( 3 ); // x position mcs.y = hb_parni( 4 ); // y position mcs.cx = hb_parni( 5 ); // width mcs.cy = hb_parni( 6 ); // height mcs.style = Style; // window style mcs.lParam = 0; // lparam hwndChild = ( HWND ) SendMessage( ( HWND ) hb_parnl(1), WM_MDICREATE, 0, ( LPARAM ) ( LPMDICREATESTRUCT ) &mcs ); // if( hwndChild != NULL ) // ShowWindow( hwndChild, SW_SHOW ); // SW_SHOWMAXIMIZED // if( hwndChild != NULL ) // ShowWindow( hwndChild, SW_HIDE ); // SW_SHOWMAXIMIZED hb_retnl( ( LONG ) hwndChild ); } HB_FUNC( SHOWMDICHILDWINDOW ) { HWND hwndChild = ( HWND ) hb_parnl( 1 ); if( IsWindow( hwndChild ) ) ShowWindow( hwndChild, SW_SHOW ); } HB_FUNC( HIDEMDICHILDWINDOW ) { HWND hwndChild = ( HWND ) hb_parnl( 1 ); if( IsWindow( hwndChild ) ) ShowWindow( hwndChild, SW_HIDE ); } #define SHIFTED 0x8000 #define NEED_CTRL(S) ((S & WS_TABSTOP)==WS_TABSTOP)&&((S & WS_VISIBLE)==WS_VISIBLE)&&((S & WS_DISABLED)!=WS_DISABLED) HWND _GetFirstCtrl(HWND hControl ){ LONG nStyle; HWND h = GetParent( hControl ); h = GetWindow( h, GW_HWNDFIRST ); while( IsWindow( h ) ){ nStyle = GetWindowLong( h, GWL_STYLE); if( NEED_CTRL( nStyle ) ) return h; h = GetWindow( h, GW_HWNDNEXT ); } return NULL; } HWND _GetNextCtrl(HWND hChild, int Sh ){ HWND h, hFocus; LONG nStyle; DWORD flag, lFocus; BOOL lSh; if(Sh < 0 ) lSh = (GetKeyState( VK_SHIFT) & SHIFTED) != 0; else lSh = Sh > 0; hFocus = GetFocus(); flag = (lSh) ? GW_HWNDPREV : GW_HWNDNEXT ; h = GetWindow(hChild, GW_CHILD); // Текущее дочернее h = GetWindow(h, (lSh) ? GW_HWNDLAST : GW_HWNDFIRST ); lFocus = 0; while( IsWindow(h) && ! lFocus ){ // Ищем сл. в зависимости от флага - flag if( hFocus==h ) lFocus++; h = GetWindow( h, flag); } if( lFocus ){ // Если найдено то while( IsWindow(h) ){ nStyle = GetWindowLong(h, GWL_STYLE); if( NEED_CTRL( nStyle ) ) return h; h = GetWindow( h, flag); } } h = GetWindow(hChild, GW_CHILD); // Текущее дочернее h = GetWindow(h, (lSh) ? GW_HWNDLAST : GW_HWNDFIRST ); while( IsWindow(h) ){ nStyle = GetWindowLong(h, GWL_STYLE); if( NEED_CTRL( nStyle ) ) return h; h = GetWindow( h, flag); } return NULL; } HB_FUNC( _DOMDIMESSAGELOOP ) { MSG Msg; HWND h, hWndChild; BOOL lLoop; while( GetMessage(&Msg, NULL, 0, 0) ) { if( !TranslateMDISysAccel(hwndMDIClient, &Msg) ) { lLoop = TRUE; // Стандартно обработать if( Msg.message==WM_KEYDOWN && Msg.wParam==VK_TAB ) { if( GetWindowLong( Msg.hwnd, GWL_USERDATA) != MET_FOR_GETBOX) { hWndChild = ( HWND ) SendMessage( hwndMDIClient, WM_MDIGETACTIVE, 0, 0); h = _GetNextCtrl( hWndChild, -1); if( h!=NULL && IsWindow(h) ){ SetFocus( h ); lLoop = FALSE; } } } if(lLoop){ h = GetActiveWindow(); if( ! IsWindow( h ) || ! IsDialogMessage( h, &Msg) ) { TranslateMessage( &Msg ); // Translates virtual key codes DispatchMessage( &Msg ); // Dispatches message to window } } } } return; } /* GetNextDlgTabITemMDI( hWnd ) // , GetFocus() , lPrevious ) */ HB_FUNC( GETNEXTDLGTABITEMMDI ) // ( hWnd, GetFocus() , lPrevious ) { HWND h, hWndChild = ( HWND ) hb_parnl( 1 ); BOOL lShift = hb_parl(2); h = _GetNextCtrl( hWndChild, ((lShift) ? 1 : 0) ); // if( h!=NULL && IsWindow(h) ) SetFocus( h ); hb_retnl( ( LONG ) h ); } HB_FUNC( GETFIRSTDLGTABITEMMDI ) // ( hWnd, GetFocus() , lPrevious ) { HWND h, hWndChild = ( HWND ) hb_parnl( 1 ); // BOOL lShift = hb_parl(2); h = _GetFirstCtrl( hWndChild ); // , ((lShift) ? 1 : 0) ); // if( h!=NULL && IsWindow(h) ) SetFocus( h ); hb_retnl( ( LONG ) h ); } HB_FUNC( TRANSLATEMDISYSACCEL ) { hb_retl( TranslateMDISysAccel( ( HWND ) hb_parnl(1), ( MSG * ) hb_parc_t(2) ) ); } HB_FUNC( ARRANGEICONICWINDOWS ) { hb_retni( ArrangeIconicWindows( ( HWND ) hb_parnl(1) ) ); } HB_FUNC( DEFMDICHILDPROC ) { hb_retnl( DefMDIChildProc( ( HWND ) hb_parnl(1), hb_parnl(2), hb_parnl(3), hb_parnl(4) ) ); } HB_FUNC( DEFFRAMEPROC ) { hb_retnl( DefFrameProc( ( HWND ) hb_parnl(1), ( HWND ) hb_parnl(2), hb_parnl(3), hb_parnl(4), hb_parnl(5) ) ); } HB_FUNC( GETCLIENTRECT ) { RECT rect; hb_retl( GetClientRect( ( HWND ) hb_parnl(1), &rect) ); HB_STORNL( rect.left, 2, 1 ); HB_STORNL( rect.top, 2, 2 ); HB_STORNL( rect.right, 2, 3 ); HB_STORNL( rect.bottom, 2, 4 ); } HB_FUNC( SIZECLIENTWINDOW ) { RECT rc, rcClient; GetClientRect( ( HWND ) hb_parnl(1), &rcClient ); if( hb_parnl(2) ) { GetWindowRect( ( HWND ) hb_parnl(2), &rc ); ScreenToClient( ( HWND ) hb_parnl(1), ( LPPOINT ) &rc.left ); rcClient.bottom = rc.top; } rcClient.top = hb_parnl( 4 ); MoveWindow( ( HWND ) hb_parnl(3), rcClient.left, rcClient.top, rcClient.right - rcClient.left, rcClient.bottom - rcClient.top, TRUE ); }
|