PDA

View Full Version : QWidget::resizeEvent is not called



maximAL
1st February 2008, 18:06
hi,

so, for the last few hours or so i tried to get the layout of some custom widgets right.
i got a widget, that serves as a container for other widgets and when resizing, i want to resize the children, too.

i overloaded resizeEvent for that - but it never gets called.

declaration:

protected:
virtual void resizeEvent(QResizeEvent *i_pEvent);

i really don't know what other code to post here. i call resize(...), the widget actually gets resized, but resizeEvent never gets called.

are there any side effects involved? some property or whatever that has to be set?

btw: i know, i could use layouts for that purpose. but then i could open another thread on why sizeHint() of the child widgets just never gets called, resulting in a messed up layout.

jpn
1st February 2008, 18:09
Can you make a small, simplest possible example which reproduces the problem?

maximAL
2nd February 2008, 21:25
so, i made a sample targeting both the resizing and layout issue.

basically, i subclassed a QScrollArea, what sets a container widget (subclassed from QFrame) as the viewport.
the container widget has a QVBoxLayout holding Obj - widgets (also subclassed from QFrame).

now, several problems arise:
the container (ScrollArea's viewport) gets resized although it shouldn't, while the container's resizeEvent() never gets called.
the Objs inside the container seem to align more or less OK, except the height of the minimumSizeHint is underrun, but i'm not sure, if this is avoidable.


#include <QApplication>
#include <QScrollArea>
#include <QFrame>
#include <QVBoxLayout>
#include <QDebug>

// the objects for the container
// should behave like pushbuttons, so horizontal resizig but fixed vertical size
// the vertical sizeHint is used for the max size but underrun for the min size
class Obj : public QFrame
{
public:
Obj(QWidget *i_pParent = NULL):
QFrame(i_pParent)
{
this->setFrameStyle(QFrame::Raised | QFrame::Box);

this->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed);

this->updateGeometry();
}

virtual QSize sizeHint() const
{
return QSize(100, 20);
}

virtual QSize minimumSizeHint() const
{
return this->sizeHint();
}
};


// hold the objects in a vertical layout
class Container : public QFrame
{
public:
Container(QWidget *i_pParent = NULL):
QFrame(i_pParent)
{
this->setFrameStyle(QFrame::Sunken | QFrame::Box);

this->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);

this->setLayout(new QVBoxLayout(this));

for(int i = 0; i < 10; ++i)
{
this->layout()->addWidget(new Obj(this));
}

this->updateGeometry();
}

// never gets called
virtual QSize sizeHint() const
{
return QSize(1000, 1000);
}

// never gets called
virtual QSize minimumSizeHint() const
{
return this->sizeHint();
}

protected:
// never gets called
virtual void resizeEvent(QResizeEvent *i_pEvent)
{

}
};

class ScrollArea : public QScrollArea
{
public:
Container *m_pContainer;

ScrollArea(QWidget *i_pParent = NULL):
QScrollArea(i_pParent)
{
this->m_pContainer = new Container(this);
this->setViewport(this->m_pContainer);

this->setWidgetResizable(false);

// some messed up value "QRect(9,9 -18x-18)"
qDebug() << this->m_pContainer->layout()->contentsRect();
// QSize(1000,1000) as it ought to be
qDebug() << this->m_pContainer->size();
// false
qDebug() << this->widgetResizable();
}
};

int main(int argc, char **argv)
{
QApplication p_App(argc, argv);

ScrollArea p_ScrollArea;

p_ScrollArea.resize(250, 250);

// viewport downsized, no scollbars
p_ScrollArea.show();

// QSize(230,230) - where did the QSize(1000, 1000) go?
// resizeEvent wasn't called
// and it shouldn't resize at all!
qDebug() << p_ScrollArea.m_pContainer->size();

return p_App.exec();
}

jpn
3rd February 2008, 11:05
Viewport events are delivered through viewportEvent(). QAbstractScrollArea filters all events of the viewport and delivers them through this specialized event handler.

By default QScrollArea resizes the content widget to its sizeHint() by the time its added. If the size hint changes, you will have to call for example adjustSize() yourself. This behavior can be changed by setting widgetResizable property to true. In this mode QScrollArea will resize the content widget on the fly but still honoring its min/max sizes etc.

maximAL
3rd February 2008, 16:07
Viewport events are delivered through viewportEvent(). QAbstractScrollArea filters all events of the viewport and delivers them through this specialized event handler.
ok, now that explains A LOT.


By default QScrollArea resizes the content widget to its sizeHint() by the time its added.
hmm, in my example it doesn't :confused:

jpn
3rd February 2008, 16:12
Hmm, I don't see QScrollArea::setWidget() being called anywhere.

maximAL
3rd February 2008, 16:25
oh, you are right. but what exactly is the difference between setViewport and setWidget? i mean, both seems to set the central widget?!

in my original program i used setViewport since i subclassed a QAbstractItemView, what again is a subclass of QAbstractScollArea...

jpn
3rd February 2008, 16:57
Viewport is a scrollable "viewport" to the content. You will see the content through the viewport. The viewport widget is laid next to scroll bars. This is usually a plain QWidget. The content widget, however, as set with QScrollArea::setWidget() is the actual scrollable content. I'm quite sure you want to set the content widget instead of a custom viewport.

maximAL
3rd February 2008, 17:24
so, to sum it up, that means when subclassing QAbstractItemView, i shouldn't set the viewport, but instead add the content as a child to the viewport, right?

ok, obviously many things have gone wrong at once in my code *goes refactoring*

jpn
3rd February 2008, 17:41
so, to sum it up, that means when subclassing QAbstractItemView, i shouldn't set the viewport, but instead add the content as a child to the viewport, right?
I'm not sure what kind of content do you mean, but for QAbstractItemView there are index widgets, editors, persistent editors, custom delegates... but of course, some kind of overlays could be implemented as children of viewport too.