'qt exec() cannot be closed
I am coding in C++ with Qt5.7. I are facing a problem with QDialog exec(). I need it in modal, so I cannot use show(). When the dialog is finished and closed, the UI disappears but the dialog variables and functions are still running. The dialog has a timer function to send out bytes to a serial port which keeps sending after the dialog is closed. In contrary this is not happening when I use show() instead. Please help.
I on purpose use redundant commands for the sake of testing like: QuitOnClose and DeleteOnClose... But none of them work as intended.
The dialog is created in MainWindow
wizard = new Wizard();
wizard->setAttribute(Qt::WA_QuitOnClose);
wizard->setAttribute(Qt::WA_DeleteOnClose, true);
connect(wizard, SIGNAL(closeWizardForm()), this, SLOT(closeWizardForm()));
wizard->exec();
also,
void MainWindow::closeWizardForm()
wizard->destroyed();
wizard = NULL;
In the dialog, it closes by
void Wizard::closeEvent(QCloseEvent *event)
// "x" button clicked
if (changeMade == true){
// give warning if changes not saved
QMessageBox::StandardButton resBtn = QMessageBox::critical(this, "Setup Wizard", tr("Unsaved data will be lost. \r\n"
" Are you sure you want to quit?"),
QMessageBox::Yes | QMessageBox::No, QMessageBox::No);
if (resBtn != QMessageBox::Yes){
event->ignore();
return;
}
}
// continue to quit
emit closeWizardForm();
event->accept();
this->close();
}
Thank you very much for your kind attention.
SP.
Solution 1:[1]
I don't see a statement here where you ever delete the Wizard object. Somewhere in there, I would expect to see:
delete wizard;
That means your wizard object still exists and the timer will still be running. I don't expect that you would get different results from "show" versus "exec" in this case, but perhaps you changed something else in switching between the two.
Emitting the "destroyed" signal doesn't destroy an object, and I think that you should not be emitting it yourself. I believe the QObject destructor does that for you when you delete the object. If you found that was necessary, it's probably because you never the deleted the object, so the QObject destructor was never called.
Solution 2:[2]
I know this question has been and gone for a few years now, but one small (stupid) mistake I made with this particular issue was a real nightmare to fix. Make sure that you actually have your buttonBox
object tied to the right Signal/Slots that you expect. In the UI XML file I believe it should look something like this:
<connections>
<connection>
<sender>buttonBox</sender>
<signal>accepted()</signal>
<receiver>SomeDialog</receiver>
<slot>accept()</slot>
<hints>
<hint type="sourcelabel">
<x>164</x>
<y>226</y>
</hint>
<hint type="destinationlabel">
<x>164</x>
<y>125</y>
</hint>
</hints>
</connection>
<connection>
<sender>buttonBox</sender>
<signal>rejected()</signal>
<receiver>SomeDialog</receiver>
<slot>reject()</slot>
<hints>
<hint type="sourcelabel">
<x>164</x>
<y>226</y>
</hint>
<hint type="destinationlabel">
<x>164</x>
<y>125</y>
</hint>
</hints>
</connection>
</connections>
So in short, the OK button needs to be mapped to accept()
, accepted()
, reject()
and rejected()
. It sounds obvious but its something that I assumed was caught by a parent class and it still has to be done even if the parent function knows how to interpet accept()
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | goug |
Solution 2 | CosmologyLuke |