Qt析构函数调用关闭的小部件 [英] Qt destructor call for closed widget

查看:342
本文介绍了Qt析构函数调用关闭的小部件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

有处理文本命令的应用程序。我有一个Qt小部件,用一些 close * 命令关闭。 Qt :: WA_DeleteOnClose 属性设置为该窗口小部件,它接收closeEvent,但该对象的析构函数稍后调用(我猜在空闲)。如果我有两个命令
close *;得到的东西; 程序崩溃,因为获取某事在析构函数之前调用该小部件,所以它试图访问被删除的数据 close * 命令。如何强制Qt调用析构函数? QCoreApplication :: processEvents()后关闭命令不起作用。
我有这个问题后从4.3.3更改qt版本到4.7.2。

p>

这是代码示例。

  test * t = new test ); 
t-> show();
std :: cout<< before deleteLater()<< std :: endl;
t-> deleteLater();
std :: cout<< after deleteLater()<< std :: endl;
QCoreApplication :: sendPostedEvents();
QCoreApplication :: processEvents();
std :: cout<< after processEvents()< std :: endl;

测试类派生自QDialog。它在构造函数中打印 test(),在析构函数中打印〜test()。此代码提供以下输出

  test()
before deleteLater()
deleteLater b $ b after processEvents()
〜test()

根据Qt文档删除对象之前最后一个cout,我是对吗?看起来像Qt中的错误,有人知道任何关于它吗?任何解决方法?



我在Qt邮件列表中提出了问题,但仍在等待答案。





一次更新



此代码

  Dialog ::〜Dialog(){
std :: cout< 〜test()< std :: endl;
}

int main(int argc,char * argv []){
QApplication app(argc,argv);
Dialog * dlg = new Dialog();
dlg-> setAttribute(Qt :: WA_DeleteOnClose);
dlg-> show();
dlg-> close();
std :: cout<< before sendPostedEvents()< std :: endl;
QCoreApplication :: sendPostedEvents();
std :: cout<< after sendPostedEvents()<< std :: endl;
return app.exec()
}

打印此

  before sendPostedEvents()
sendPostedEvents()
〜test()

但是一旦我在该处理函数中添加了closeEvent处理函数并调用了deleteLater(),sendPostedEvents就开始删除延迟对象。

  void Dialog :: closeEvent(QCloseEvent * ev){
deleteLater();
QWidget :: closeEvent(ev);
}

在sendPostedEvents()之前打印

〜test ()
sendPostedEvents()之后



任何人都可以解释一下到底发生了什么?这只是一个错误?我可以使用它作为解决方法吗?



这是如何工作的?应该不应该Qt自动调用deleteLater(),如果CloseOnDelete属性设置,closeEvent是否被接受?

解决方案

设置 Qt :: WA_DeleteOnClose 表示qt可以在您调用 close /doc.qt.io/qt-5/qobject.html#deleteLaterrel =nofollow> deleteLater() 。您可以使用 QObject :: destroyed() 信号。


There is application that handles text commands. I have a Qt widget that is closed with some close * command. Qt::WA_DeleteOnClose attribute is set for that widget, it receives closeEvent, but destructor for that object is called later (I guess on idle). If I have two commands close *; get something; the program crashes because get something is called before destructor for that widget, so it tries to access data deleted by close * command. How can I force Qt to call destructors? QCoreApplication::processEvents() after close command doesn't help. I've got this problem after changing qt version to 4.7.2 from 4.3.3. There is no multithreading here.

Thanks in advance.

added

Here is the code example.

test *t = new test();
t->show();
std::cout << "before deleteLater()" << std::endl;
t->deleteLater();
std::cout << "after deleteLater()" << std::endl;
QCoreApplication::sendPostedEvents();
QCoreApplication::processEvents();
std::cout << "after processEvents()" << std::endl;

test class is derived from QDialog. It prints test() in constructor and ~test() in destructor. This code gives the following output

test()
before deleteLater()
after deleteLater()
after processEvents()
~test()

According to Qt documentation it should delete the object before last cout, am I right? Looks like a bug in Qt, does anybody know anything about it? Any workaround?

I asked the question in Qt mailing list, but still waiting for an answer.

Thanks.

one more update

This code

Dialog::~Dialog() {
    std::cout << "~test()" << std::endl;
}

int main(int argc, char* argv[]) {
    QApplication app(argc, argv);
    Dialog* dlg = new Dialog();
    dlg->setAttribute(Qt::WA_DeleteOnClose);
    dlg->show();
    dlg->close();
    std::cout << "before sendPostedEvents()" << std::endl;
    QCoreApplication::sendPostedEvents();
    std::cout << "after sendPostedEvents()" << std::endl;
    return app.exec();
}

prints this

before sendPostedEvents()
after sendPostedEvents()
~test()

but as soon as I add closeEvent handler and call deleteLater() in that handler function sendPostedEvents starts deleting deferred objects.

void Dialog::closeEvent(QCloseEvent* ev) {
    deleteLater();
    QWidget::closeEvent(ev);
}

prints this before sendPostedEvents() ~test() after sendPostedEvents()

Can anybody explain what the hell is going on there? Is it just a bug? Can I use that as a workaround?

How does this work? Shouldn't Qt call deleteLater() automatically, after closeEvent is accepted if CloseOnDelete attribute is set?

解决方案

Setting Qt::WA_DeleteOnClose means qt can delete anytime after you call close() because qt uses deleteLater() internally. You can ensure the deletion using QObject::destroyed() signal.

这篇关于Qt析构函数调用关闭的小部件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆