May 10, 2024, 02:33:53 AM

News:

Own IWBasic 2.x ? -----> Get your free upgrade to 3.x now.........


Sizing the MDI Client Area

Started by WayneA, September 23, 2010, 05:55:31 PM

Previous topic - Next topic

0 Members and 1 Guest are viewing this topic.

WayneA

I've tried numerous methods to change the size and position of the MDI client area for MDI frames created with the CreateWindow function without success, is this possible without jumping through a lot of hoops? I considered subclassing the window and handling the appropriate messages but I felt like if I am going to do that then I may as well do the enter MDI app using API, so I can use tried and true methods instead of having to looks for things that I forgot to override.

I'm mostly interested in this for a tabbed MDI interface.

Thanks,

Wayne
99 little bugs in the code,
99 bugs in the code,
Fix one bug,
Compile again,
104 little bugs in the code...

All code I post is in the public domain.

fasecero

September 23, 2010, 10:28:25 PM #1 Last Edit: September 23, 2010, 10:30:47 PM by fasecero
Hi, WayneA. To resize the MDI client window you will need the window handle, then you can use for example the api:

MoveWindow(hwndclient, ...)

If you are using the IW basic functions, then the handle is WINDOW.hClient, like in w1.hClient.
However, if you are using just API functions you obtain that handle when you create the client window, this is an example:

hwndclient = CreateWindowEx(0, "MDICLIENT", "", WS_CHILD|WS_VISIBLE|WS_CLIPCHILDREN|WS_CLIPSIBLINGS|WS_VSCROLL|WS_HSCROLL, 0, 0, 0, 0, hwndframe, 0, hinstance, &ccs)

WayneA

Sorry it took so long for me to get around to following up on this.

Heres the test code I did for this method:
$Include "windows.inc"
AutoDefine "Off"
Dim wndMain As Window
OpenWindow wndMain,0,0,640,480,@MinBox|@MaxBox|@Size|@MDIFrame,0,"MDI Test",&wndMainProc
WaitUntil IsWindowClosed wndMain
End

Sub wndMainProc
Select @Message
Case @IDCreate
_MoveWindow(wndMain.hClient,10,0,50,50,True)
Case @IDSize
_MoveWindow(wndMain.hClient,10,0,50,50,True)
Case @IDCloseWindow
CloseWindow wndMain
EndSelect
EndSub


If you size the parent you'll see that theres alot of flicker because the MDIClient is being resized before I get a chance to handle the message. Any ideas how to prevent this?

Thanks for the response fasecero, I had no idea the hClient property existed.
99 little bugs in the code,
99 bugs in the code,
Fix one bug,
Compile again,
104 little bugs in the code...

All code I post is in the public domain.

sapero

September 26, 2010, 04:12:00 PM #3 Last Edit: September 26, 2010, 04:14:42 PM by sapero
Wayne, it flickers (and the MDi frame is resized to fit owner client area) because WM_SIZE message is passed to DefFrameProc in the default handler.
If you install a subclass to your main window and set wndMain.hClient to zero before executing the default handler, MDI client will be not automatically resized.

I have used the new subclassing functions from XP: SetWindowSubclass, DefSubclassProc, RemoveWindowSubclass instead the old, and not always safe SetWindowLong tricks.

$Include "windowssdk.inc"
$include "commctrl.inc"
AutoDefine "Off"
Dim wndMain As WINDOW

OPENWINDOW wndMain,0,0,640,480,@MINBOX|@MAXBOX|@SIZE|@MDIFRAME|WS_CLIPCHILDREN,0,"MDI Test",&wndMainProc

WaitUntil ISWINDOWCLOSED wndMain
End

$define MDI_SUBCLASS_ID 1

Sub wndMainProc
Select @MESSAGE

Case @IDCREATE
' subclass this window to grab WM_SIZE message before the default handler
' passes it to DefFrameProc. SetWindowSubclass comes from comctl32.lib; win XP
SetWindowSubclass(wndMain.hWnd, &MdiParentSubclassProc, MDI_SUBCLASS_ID, &wndMain/*any user data*/)
' delayed MDI frame resize
PostMessage(wndMain.hWnd, @IDSIZE, 0, 0)

Case @IDSIZE
MoveWindow(wndMain.hClient,10,0,50,50,TRUE)

Case @IDCLOSEWINDOW
CLOSEWINDOW wndMain

case @IDDESTROY
RemoveWindowSubclass(wndMain.hWnd, &MdiParentSubclassProc, MDI_SUBCLASS_ID)
EndSelect
return 0
EndSub


sub MdiParentSubclassProc(HWND hWnd,UINT uMsg,WPARAM wParam,LPARAM lParam,UINT_PTR uIdSubclass,WINDOW win/*any user data*/),LRESULT
HWND hwndSave
LRESULT result

select (uMsg)
case WM_SIZE
' prevent passing WM_SIZE to MDI frame
hwndSave = win.hClient
win.hClient = 0
result      = DefSubclassProc(hWnd, uMsg, wParam, lParam)
win.hClient = hwndSave
return result
endselect
return DefSubclassProc(hWnd, uMsg, wParam, lParam)
endsub

WayneA

99 little bugs in the code,
99 bugs in the code,
Fix one bug,
Compile again,
104 little bugs in the code...

All code I post is in the public domain.