Important: Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

Get geometry and size of object that is in Layout



  • Hi,

    I'm trying to get geometry of the object that was created in Qt designer.
    If this object is not in laoyt then everything is fine and I can simply write:

        QSize frameSize = ui->qwtPlot->size();
        QSize canvasSize = ui->qwtPlot->canvas()->size();
    
        QRect frameGeom = ui->qwtPlot->geometry();
        QRect canvasGeom = ui->qwtPlot->canvas()->geometry();
    

    But if the object in layout then I get wrong geometry and size.
    There should be a known solution I guess but googling it brought me nothing :(


  • Moderators

    It depends on where you call that.
    The first time layout is applied is when the window is first shown. If you call those methods anywhere before that, e.g. in the window class constructor, the values won't be what you expect, as the layout was not yet applied and the window itself was not yet resized. A good place to call this is the first showEvent() or anywhere after that.


  • Moderators

    It depends on where you call that.
    The first time layout is applied is when the window is first shown. If you call those methods anywhere before that, e.g. in the window class constructor, the values won't be what you expect, as the layout was not yet applied and the window itself was not yet resized. A good place to call this is the first showEvent() or anywhere after that.



  • @Chris-Kawa thank you!
    As you mentioned I used to do it in mainwindow class constructor.
    After I put the code in main() below w.show(); it is getting to work normally.

    I didn't understand what is showEvent()? Is it the same as w.show()?



  • @Please_Help_me_D

    The showEvent gets triggered every time you show a widget or make it visible.

    Just implement QMainWindow::showEvent in your MainWindow class and put your code from above there

    https://doc.qt.io/qt-5/qwidget.html#showEvent



  • @Pl45m4 Thank you for the answer

    Am i right that I should use QMainWindow::showEvent only if I want to do something with the object before it is shown? Forexample if I do something with the object in mainwindow constructor?

    Let's suppose that the window is appeared and only then I want to do something with the object. In this case should I use QMainWindow::showEvent? Because in my case it is not the problem to use my code after the window is shown like that:

    int main(int argc, char *argv[])
    {
        QApplication a(argc, argv);
        MainWindow w;
        w.show();
        w.MyCode();
        return a.exec();
    }
    


  • @Please_Help_me_D said in Get geometry and size of object that is in Layout:

    Am i right that I should use QMainWindow::showEvent only if I want to do something with the object before it is shown?

    Not only, but this would be a good use case for a showEvent. As @Chris-Kawa said, it fits perfectly when it comes to layouts and geometry. By using the showEvent you can get the actual size, before your window gets eventually resized by your window manager and before the layout rules apply.

    This is perfect use case for showEvent. (or if you want to get the actual size of a QGraphicsView)

    @Please_Help_me_D said in Get geometry and size of object that is in Layout:

    QSize frameSize = ui->qwtPlot->size();
    QSize canvasSize = ui->qwtPlot->canvas()->size();
    
    QRect frameGeom = ui->qwtPlot->geometry();
    QRect canvasGeom = ui->qwtPlot->canvas()->geometry()


  • @Pl45m4 Thank you
    I will keep that in mind



  • @Pl45m4 Hi
    I just tried to implement void MainWindow::showEvent(QShowEvent *ev) and it works but seems to me it works not perfectly.
    In QDesigner I create QGraphicsView widget in form layout.
    Then I check the size of QGraphicsView with this code:

    void MainWindow::showEvent(QShowEvent *ev)
    {
        QMainWindow::showEvent(ev);
        showEventHelper();
    }
    
    void MainWindow::showEventHelper()
    {
        QRect geomGraphView = ui->graphicsView->geometry();
        QRect geomScene = QRect(0, 0, geomGraphView.width(), geomGraphView.height());
        scene->setSceneRect(geomScene);
    }
    

    and I get wrong heigh and fine width. If I compare the heigh of QGraphicsView and QColorDialog (the are in form layout) the I figure out that the heigh of QGraphicsView = 525 and heigh of QColorDialog = 359. But they both should have almost equal values
    1.png



  • @Please_Help_me_D said in Get geometry and size of object that is in Layout:

    If I compare the heigh of QGraphicsView and QColorDialog (the are in form layout) the I figure out that the heigh of QGraphicsView = 525 and heigh of QColorDialog = 359. But they both should have almost equal values

    They shouldnt because you set the (correct or actual) width and height from your QGraphicsView inside showEvent. The QColorDialog' s size is still dynamic (depends on layout and MainWindow size).

    According your movable rectangle:

    Your sceneRect equals the width and height of your QGraphicsView

     QRect geomScene = QRect(0, 0, geomGraphView.width(), geomGraphView.height());
     scene->setSceneRect(geomScene);
    

    So you cant move your items further than the (visible) border of your QGraphicsView, because your scene ends there.

    EDIT:

    Ah, I've read CANT instead of CAN...

    Try this (without geometry):

    scene->setSceneRect( 0, 0, ui->graphicsView->width(), ui->graphicsView->height() );
    


  • @Pl45m4 said in Get geometry and size of object that is in Layout:

    They shouldnt because you set the (correct or actual) width and height from your QGraphicsView inside showEvent. The QColorDialog' s size is still dynamic (depends on layout and MainWindow size).

    Do you mean that the size of QGraphicsView in determined somewhere after void MainWindow::showEventHelper() ? Because I don't understand the thing that after window is shown I can see that QGraphicsView has heigh say 300 pixels and if I stop the program in showEventHelper() I can see that its heigh is about 500 pixels.

    @Pl45m4 said in Get geometry and size of object that is in Layout:

    Try this (without geometry):
    scene->setSceneRect( 0, 0, ui->graphicsView->width(), ui->graphicsView->height() );

    No this doesn't work neither:
    1.png



  • @Please_Help_me_D said in Get geometry and size of object that is in Layout:

    after window is shown I can see that QGraphicsView has heigh say 300 pixels and if I stop the program in showEventHelper() I can see that its heigh is about 500 pixels.

    Because the layout applied.

    If nothings works, you have to check if item->pos() is at the border and ignore movement, that would set your item outside your visible area.

    Here is one approach to restrict item movement by using itemChanged
    https://forum.qt.io/topic/4474/solved-restrict-the-movement-of-qgraphicsitem



  • @Pl45m4 yes I restrict the movable area with itemChanged virtual function (found this in internet). But to restrict this area it would be good to know the coordinates of boreders of visible part of QGraphicsView.
    Now I use fixed width of QGraphicsView and the height I get from the QColorDialog (their heights should be almost the same since they are in form layout).
    But I'm afraid of would that be ok when porting on other operating system (I'm on Windows now but would it be ok on Linux)?


Log in to reply