Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. QMdiSubwindow deleted twice in singleton destructor

QMdiSubwindow deleted twice in singleton destructor

Scheduled Pinned Locked Moved Solved General and Desktop
qmdiareaqmdisubwindow
5 Posts 2 Posters 1.8k Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • ShadowigorS Offline
    ShadowigorS Offline
    Shadowigor
    wrote on last edited by
    #1

    Hi

    I have a singleton class that has a QMdiArea. If I add a new subwindow to it, QMdiArea wants to delete it twice. I have a minimal example here: (I'm calling SharedWindow::instance() at least once).

    // shared_window.h
    #ifndef SHARED_WINDOW_H
    #define SHARED_WINDOW_H
    
    #include <QObject>
    #include <QMdiArea>
    #include <QMdiSubWindow>
    #include <QMainWindow>
    
    class Q_DECL_EXPORT SharedWindow : public QMainWindow
    {
    Q_OBJECT
    
    public:
        ~SharedWindow();
    
        // Singleton
        SharedWindow(SharedWindow const&)   = delete;
        void operator=(SharedWindow const&) = delete;
    
        static SharedWindow &instance(void);
    
    private:
        QMdiArea *mdi;
    
        // Singleton
        SharedWindow();
    };
    
    #endif // SHARED_WINDOW_H
    
    // shared_window.cpp
    #include "shared_window.h"
    
    SharedWindow::SharedWindow()
    {
        this->mdi = new QMdiArea();
        this->setCentralWidget(this->mdi);
        this->mdi->addSubWindow(new QSlider());
        this->show();
    }
    
    SharedWindow::~SharedWindow()
    {
    }
    
    SharedWindow &SharedWindow::instance()
    {
        static SharedWindow i;
    
        return i;
    }
    
    Stack trace:
    
    1  ??                                                    0x7ffff7285cf2 
    2  ??                                                    0x7ffff72886f1 
    3  QMdiSubWindow::~QMdiSubWindow()                       0x7ffff728cd5d 
    4  QMdiSubWindow::~QMdiSubWindow()                       0x7ffff728cd99 
    5  QObjectPrivate::deleteChildren()                      0x7ffff61dcb11 
    6  QWidget::~QWidget()                                   0x7ffff7154d98 
    7  QWidget::~QWidget()                                   0x7ffff7155019 
    8  QObjectPrivate::deleteChildren()                      0x7ffff61dcb11 
    9  QWidget::~QWidget()                                   0x7ffff7154d98 
    10 QMdiArea::~QMdiArea()                                 0x7ffff7278a39 
    11 QObjectPrivate::deleteChildren()                      0x7ffff61dcb11 
    12 QWidget::~QWidget()                                   0x7ffff7154d98 
    13 SharedWindow::~SharedWindow      shared_window.cpp 19 0x7fffe37adffc
    14 __run_exit_handlers                                   0x7ffff4e8fbe8 
    15 exit                                                  0x7ffff4e8fc35 
    16 __libc_start_main                                     0x7ffff4e7a748 
    17 _start                                                0x400e49       
    
    

    Any ideas?

    1 Reply Last reply
    0
    • SGaistS Offline
      SGaistS Offline
      SGaist
      Lifetime Qt Champion
      wrote on last edited by
      #2

      Hi and welcome to devnet,

      Because it will be deleted by its parent when its parent gets destroyed (see Object Trees & Ownership)

      You should also avoid static QWidget object. They might get created before your QApplication object which should be the first thing created before using any GUI features.

      Out of curiosity, why are you using a singleton to create a QMainWindow ?

      Interested in AI ? www.idiap.ch
      Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

      1 Reply Last reply
      0
      • ShadowigorS Offline
        ShadowigorS Offline
        Shadowigor
        wrote on last edited by
        #3

        Hi

        Yes, that's what I was thinking too, but why is it deleted twice then? My QMainWindow is the parent of the QMdiArea, which is the parent of the QMdiSubWindow. And my QMainWindow doesn't have a parent. I'm also never deleting something manually. So why is it segfaulting anyway?

        Would it be better if the QMainWindow was a dynamically allocated member of SharedWindow instead of it's base then?

        I try to create a window that is shared by multiple plugins. They should later be able to (dynamically) push widgets to it. The window itself will also be a plugin, so I can't handle that when the plugins are loaded. A singleton seemed to be the easiest way to have one "global' object.

        1 Reply Last reply
        0
        • SGaistS Offline
          SGaistS Offline
          SGaist
          Lifetime Qt Champion
          wrote on last edited by
          #4

          Since I don't know the rest of your code, I can't comment on that part.

          Technically, it should be the other way around, your application loads the plugins and pulls widgets from them. That will also avoid making a tight coupling between the plugins and your MainWindow class.

          Interested in AI ? www.idiap.ch
          Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

          1 Reply Last reply
          0
          • ShadowigorS Offline
            ShadowigorS Offline
            Shadowigor
            wrote on last edited by
            #5

            I got it working! You were right, after some more testing, it turned out, that my class was deleted after QApplication was already deleted. That's what I'm using now:

            // shared_window.h
            #ifndef SHARED_WINDOW_H
            #define SHARED_WINDOW_H
            
            #include <QObject>
            #include <QMdiArea>
            #include <QMdiSubWindow>
            #include <QMainWindow>
            
            class ROBOTCORE_EXPORT SharedWindow : public QObject
            {
            Q_OBJECT
            
            // Singleton
            Q_DISABLE_COPY(SharedWindow)
            
            public:
                ~SharedWindow();
            
                static SharedWindow *instance(void);
            
            private:
                QMdiArea *mdi;
                static SharedWindow *inst;
                QMainWindow *wnd;
            
                // Singleton
                SharedWindow();
            
            private slots:
                void cleanup(void);
            };
            
            #endif // SHARED_WINDOW_H
            
            // shared_window.cpp
            #include "shared_window.h"
            
            SharedWindow *SharedWindow::inst = nullptr;
            
            SharedWindow::SharedWindow()
            {
                this->wnd = new QMainWindow();
                this->mdi = new QMdiArea();
                this->wnd->setCentralWidget(this->mdi);
                this->mdi->addSubWindow(new QSlider());
                this->wnd->show();
            }
            
            void SharedWindow::cleanup()
            {
                delete this->wnd;
            }
            
            SharedWindow::~SharedWindow()
            {
            }
            
            SharedWindow *SharedWindow::instance()
            {
                if(SharedWindow::inst == nullptr)
                {
                    SharedWindow::inst = new SharedWindow();
                    // Setting qApp as the parent won't do it, don't know why
                    connect(QApplication::instance(), &QApplication::aboutToQuit,
                            SharedWindow::inst, &SharedWindow::cleanup);
                }
            
                return SharedWindow::inst;
            }
            
            

            I couldn't delete it from the main application, because I have no control over the main application. Also, my shared window is only used by some specific plugins and isn't part of the main project. The main application has a window of it's own.

            Thanks!

            1 Reply Last reply
            0

            • Login

            • Login or register to search.
            • First post
              Last post
            0
            • Categories
            • Recent
            • Tags
            • Popular
            • Users
            • Groups
            • Search
            • Get Qt Extensions
            • Unsolved