How to change QMainWindow size at runtime?
Since there was no chance to determine the size of main window at very beginning, I have to change it later, at runtime.
Basically my main window contained a toolbar, menu bar, as well as status bar. Then
when the first child widget (will be central widget of main window) was created, it's best chance for me to adjust the size.
The code liked below,
Code:
// first set child widget geometry
setGeometry(rect);
// adjust main window accordingly
mainWnd->setCentralWidget(this);
mainWnd->adjustSize();
// I also tried below
// mainWnd->updateGeometry();
Besides, I've overridden sizeHint() of main window to return a QSize(0, 0), since it said if sizeHint() returned an invalid value, adjustSize() would set the size to the children rectangle that covers all child widgets.
However, the resulting size of main window was totally too small than I expected.
I'm really confused how Qt size policy was working.
Could anyone help me?
Thx.
Re: How to change QMainWindow size at runtime?
I am not sure I understand what it is you want to achieve, and more so why.
Have you tried resize()?
Also, if your main window needs to have a certain specific size, then you can have sizeHint() return it, in addition, if your main window should not change size you should set the sitzePolicy() to fixed.
But fixed sized main window (or windows that need to have more specific size than using the min and max size limits) shows more that you probably don't need a main window, and probably more a dialog.
Maybe if you explain more what it is and why you are trying to do, we might help you get on the right track.
Re: How to change QMainWindow size at runtime?
Basically, I'd like to build an app with main window by following steps,
1. build main window (size was not determined yet at this moment). now, main window only contained toolbar, menu, status bar, without a central widget
2. then dynamically create the first widget (QFrame-derived), it would be central widget of main window and it would expand main window size according to its size
3. continue to dynamically create some widgets and add them to central widget.
Briefly, main window size depends on central widget size.
Since main window size = all bars size + central widget size,
so resize() didn't work for my case, it actually resized entire geometry area which contains those bars, but I've no idea about what those bars size are.
Hopefully I'm clear for you.
Thanks.
Re: How to change QMainWindow size at runtime?
First make sure your central widget is using layouts properly. Then put it into the main window (if you really need a main window) and set the main window layout's size constraint (not size policy of any of the widgets) to QLayout::SetFixedSize (or SetMinimumSize).
Re: How to change QMainWindow size at runtime?
I built a simple demo to show what problem I've got,
Code:
QMyMainWindow
::QMyMainWindow(QWidget *parent, Qt
::WFlags flags
) : QMainWindow(parent, flags
){
setCentralWidget(frame);
QRect rect
(0,
0,
240,
320);
frame
->setFrameShape
(QFrame::Box);
frame->setLineWidth(3);
frame
->setFrameShadow
(QFrame::Plain);
frame->setGeometry(rect);
adjustSize();
}
I didn't specify main window size at first and it would be totally expanded by central widget.
I also tried other SizePolicy values, but the resulting size of main window was not (240, 320) as expected at all.
How could I do?
Thx
Re: How to change QMainWindow size at runtime?
You have to resize() your mainwindow, not the frame inside it. And calling adjustSize() destroy all other setting you made before.
Re: How to change QMainWindow size at runtime?
I've found the root cause
Code:
QSize QWidgetPrivate
::adjustedSize() const {
if (q->isWindow()) {
Qt::Orientations exp;
if (layout) {
if (layout->hasHeightForWidth())
s.setHeight(layout->totalHeightForWidth(s.width()));
exp = layout->expandingDirections();
} else
{
if (q->sizePolicy().hasHeightForWidth())
s.setHeight(q->heightForWidth(s.width()));
exp = q->sizePolicy().expandingDirections();
}
if (exp & Qt::Horizontal)
s.setWidth(qMax(s.width(), 200));
if (exp & Qt::Vertical)
s.setHeight(qMax(s.height(), 100));
#if defined(Q_WS_X11)
#else // all others
#endif
#if defined (Q_WS_WINCE) || defined (Q_OS_SYMBIAN)
s.setWidth(qMin(s.width(), screen.width()));
s.setHeight(qMin(s.height(), screen.height()));
#else
s.setWidth(qMin(s.width(), screen.width()*2/3));
s.setHeight(qMin(s.height(), screen.height()*2/3));
#endif
if (QTLWExtra *extra = maybeTopData())
extra->sizeAdjusted = true;
}
if (!s.isValid()) {
QRect r
= q
->childrenRect
();
// get children rectangle if (r.isNull())
return s;
s
= r.
size() + QSize(2 * r.
x(),
2 * r.
y());
}
return s;
}
The root was that window has a default size policy, so adjustSize() never ran into using childrenRect to expand size. How could I avoid to it?
Added after 4 minutes:
Quote:
Originally Posted by
Lykurg
You have to resize() your mainwindow, not the frame inside it. And calling adjustSize() destroy all other setting you made before.
but I can't get the total size of frame plus other bars (toolbar, menubar, etc).
Re: How to change QMainWindow size at runtime?
size policy is only relevant for widgets inside layouts. Your main window is not inside a layout. Furthermore your frame doesn't have a layout attached so it's sizeHint is practically 0. Hence the size of your mainwindow content is also 0. Why do you keep going the wrong way despite being told a couple of times how you should approach your problem? childrenRect() will likely use sizeHint() of your child widgets and since sizeHint of the frame is 0, you will get a useless output for the whole calculation. And even if not then your frame is controlled by a layout so using setGeometry() on it has no effect at all.
Re: How to change QMainWindow size at runtime?
Quote:
Originally Posted by
wysota
First make sure your central widget is using layouts properly. Then put it into the main window (if you really need a main window) and set the main window layout's size constraint (not size policy of any of the widgets) to QLayout::SetFixedSize (or SetMinimumSize).
What layout should be assinged to central frame?
Quote:
Originally Posted by
wysota
size policy is only relevant for widgets inside layouts. Your main window is not inside a layout. Furthermore your frame doesn't have a layout attached so it's sizeHint is practically 0. Hence the size of your mainwindow content is also 0. Why do you keep going the wrong way despite being told a couple of times how you should approach your problem? childrenRect() will likely use sizeHint() of your child widgets and since sizeHint of the frame is 0, you will get a useless output for the whole calculation. And even if not then your frame is controlled by a layout so using setGeometry() on it has no effect at all.
As far as I known, QMainWindow has its default layout management, why did you say that it's not inside a layout?
I didn't quite follow your words. I'm really confused with concept layout in Qt, and things like relationship between size policy and layout:(
Could you please explain it little more or refer me to something to read?
Thanks.
Re: How to change QMainWindow size at runtime?
Quote:
Originally Posted by
myfifth
What layout should be assinged to central frame?
It depends on the contents of the frame. If it has no contents then layout is not required but you need to manually fix the size of the frame to something constant using QWidget::setFixedSize.
Quote:
As far as I known, QMainWindow has its default layout management, why did you say that it's not inside a layout?
A layout of a widget is inside the widget not outside it. The main window is a floating window so it's not "in" a layout (as it would need to have a parent).
Quote:
Could you please explain it little more or refer me to something to read?
Size policy is a set of rules that are used by a layout controlling the current widget to determine how much space to give to each widget controlled by the layout. Layout controlls the widgets that are in the layout, not the one the layout is in (the parent). If a particular widget (like your main window) is not part of some layout, its size policy and its size hint are ignored. The exception is that size hint of a window is used to determine the initial size of this window.
Re: How to change QMainWindow size at runtime?
@wysota
I'm now much more clear.
Layout in a widget is used to control layouting of its children, and size policy defines how layout works.
In my case, I should care about how to design frame layout instead of main window. I'll try it later.
Thanks a lot.
Re: How to change QMainWindow size at runtime?
@wysota
Sorry for late reply.
setFixedSize and setSizeConstraint worked quite well. I simply set both of them to expected values, finally it rocked.
Really thx.