QT 和新的信号槽语法,用于 QApplication::quit 外部主函数的槽
Posted
技术标签:
【中文标题】QT 和新的信号槽语法,用于 QApplication::quit 外部主函数的槽【英文标题】:QT and the new signal slot syntax, slot for QApplication::quit outside main function 【发布时间】:2018-05-27 09:57:49 【问题描述】:我正在尝试测试新旧 QT 插槽/信号语法。旧样式可以,新样式只能在 main 函数中使用,如果我们将 app 对象传递给另一个函数,它就不起作用。 VS 2017编译器生成错误C2665:“重载函数的参数无法转换为所需类型”。
void testTimer(const QApplication& app)
QTimer::singleShot(1000, &app, SLOT(quit())); // OK - works
// This generates compiler error C2665:
QTimer::singleShot(1000, &app, &QApplication::quit); // Compiler error
int main(int argc, char *argv[])
QApplication app(argc, argv);
QTimer::singleShot(1000, &app, SLOT(quit())); // OK - works
QTimer::singleShot(1000, &app, &QApplication::quit); // OK - works
testTimer(app);
app.exec();
【问题讨论】:
您需要在不称为main()
的函数中尝试与main()
完全相同的代码。
更改为void testTimer(QApplication *app)QTimer::singleShot(1000, app, &QApplication::quit);
和testTimer(&app);
我的代码在 main 和 testTimer 函数中完全一样。我也尝试使用指向应用程序的指针,但它给出了相同的结果。
@Klearuegh 一个疯狂的猜测 - 从 QApplication& app
函数 testTimer
参数中删除 const
?注意:quit
是一个静态插槽,完全不确定为什么一个对象会在这里相关
非常感谢,删除 const 后没有编译器错误。我花了 2 个小时在上面:)
【参考方案1】:
为什么? QCoreApplication::quit
是一个类方法:它根本不需要对象。你应该像 C 函数指针一样调用它:
QTimer::singleShot(1000, &QCoreApplication::quit);
即使是这样 - 你应该使用qApp
。该应用程序实际上是一个全局单例,您可以控制其生命周期。没有必要传递它。
如果你在一个实际的非静态成员上尝试它,你会发现它工作得很好(用 Qt 5.10 测试过)。 Qt 甚至可以让你在腿上开枪:
#include <QTimer>
#include <utility>
struct Foo : QObject
void slot() const
void nonConstSlot()
;
void test(const Foo *foo)
QTimer::singleShot(900, foo, &Foo::slot);
template <typename P, typename M, typename> struct valid
static std::false_type value;
;
template <typename P, typename M> struct valid<P, M, decltype((*P().*M())())>
static std::true_type value;
;
template <typename P, typename M, typename ...Args> constexpr bool isValid(P, M, Args...)
return valid<P, M, void>::value;
int main()
const Foo foo;
QTimer::singleShot(1000, &foo, &Foo::slot);
QTimer::singleShot(1000, &foo, &Foo::nonConstSlot); //oops
static_assert(isValid(&foo, &Foo::slot), "");
static_assert(!isValid(&foo, &Foo::nonConstSlot), ""); // (foo.*&Foo::nonConstSlot)() must be invalid
test(&foo);
return 0;
【讨论】:
感谢您的回答。我在测试新样式语法时不知道问题出在哪里。除非您手动进行类型转换,否则您似乎无法以新样式使用常量。未来的教训。 @Klearuegh 这是错误的。以上是关于QT 和新的信号槽语法,用于 QApplication::quit 外部主函数的槽的主要内容,如果未能解决你的问题,请参考以下文章