What is the best practices for laying out child windows (common controls) in a dialog box or main window? I mean is there a binding mechanism which would fix a relative positions of the control to parent window's border like in WPF. And during window resize the child control would resize together with the main window.
Currently I have this:
As you can see from the red lines it does not look pretty when I am resizing parent window of a list view control. I would like to bind for example ListView's right side to DialogBox's right border and similarly other controls.
I know that I can play around with GetWindowRect, GetClientRect and MoveWindow functions. But is this the correct way?
Currently I am working with pure Win32 Api without MFC.
If you're just using the Win32 API, you normally handle this by handling the WM_SIZE message, and respond by calling GetClientRect on the parent window and MoveWindow on the children to move/resize the children to fill the parent appropriately.
If you want to badly enough, you can (of course) implement a layout manager, so the rest of the program doesn't need to handle things like this directly. At least IME, doing this well is sufficiently difficult that it's rarely worth the trouble unless you can make quite a lot of use of that layout code.
While its a manual process, I find it helpful to work in coordinates relative to each control's parent window.
I use the following function to return a control's current position relative to its parent, so that it can be easily moved/resized with SetWindowPos().
void GetRelativeCtrlRect(HWND hWnd, RECT *rc) {
// Get the position of the window relative to the entire screen
GetWindowRect(hWnd, rc);
// Now convert those with regards to the control's parent
ScreenToClient(GetParent(hWnd), (LPPOINT) &((LPPOINT)rc)[0]);
ScreenToClient(GetParent(hWnd), (LPPOINT) &((LPPOINT)rc)[1]);
}
This returns a size RECT
relative to the parent window/control. As an example, if you wanted to resize the child control to the "near" bottom edge of the parent, just bump off a few pixels off rc.bottom before calling SetWindowPos(childHWND,...)
I also have some "anchoring" functions that help position controls relative to other reference points. Its still a manual -at-code-time- process however, but gives excellent hand-tweaked results.
Some other options I have bookmarked, all are likely to require tweaking for your needs but it gives you an idea of some of the tools others have created to solve this problem.
- Box Planner - Code Project
- Easy Dialog Resizer - Code Project
- EvaLayout - Code Project
- CResizableDialog (MFC) - Code Project
- RPResizeDialog (MFC) - Code Project
- EasySize (MFC) - Code Project
- Resize Dialog - Code Project
- Dynamic child windows - Code Project
- Layout Manager (MFC) - Code Project
- ResizableLib (MFC) - Code Project
Try selecting the control and playing with its property "Dock". With that, you can dock the control to some sides or even all sides of the parent control.