Qt C++ connect QPushButton click
Я только начал разрабатывать с использованием QtGUI, и я проверил некоторые учебники и документацию, и то, что я прочитал, должно работать.
#define CONNECT QObject::connect
void test();
QPushButton *lpTestBtn;
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
QtProject w;
w.show();
lpTestBtn = w.window()->findChild<QPushButton*>("TestBtn");
CONNECT(lpTestBtn, SIGNAL(clicked()),qApp,SLOT(test()));
return a.exec();
}
void test()
{
lpTestBtn->setText("Hi");
}
Но test() никогда не вызывается. Кроме того, lpTestBtn не является нулевым и найден правильно.
Я пробовал следующие изменения
CONNECT(lpTestBtn, SIGNAL(clicked()),qApp->activeWindow(),SLOT(test()));
CONNECT(lpTestBtn, SIGNAL(clicked()),w.window(),SLOT(test()));
Я знаю, что могу просто сделать QtProject::on_TestBtn_clicked(); но я бы хотел, чтобы он работал, используя CONNECT,SIGNAL и SLOT.
3 ответа
Тестовая функция в вашем коде не является слотом и не относится к классу приложений Q(Core), как вы, похоже, ее использовали.
Лучше всего было бы переместить эту строку в тестовой функции в соединение с лямбда-синтаксисом. Это потребует поддержки C++11, но в наши дни это довольно распространенное использование.
Вы бы использовали новый блестящий синтаксис сигнального слота. Это избавит вас от головной боли из-за проблем во время выполнения в будущем, потому что они появятся во время компиляции.
Поэтому вы бы написали что-то вроде этого:
main.cpp
#include <QMainWindow>
#include <QApplication>
#include <QPushButton>
int main(int argc, char **argv)
{
QApplication a(argc, argv);
// Replace it with "QtProject".
QMainWindow w;
w.show();
QPushButton * lpTestBtn = w.window()->findChild<QPushButton*>("TestBtn");
QObject::connect(lpTestBtn, &QPushButton::clicked, [=]() {
lpTestBtn->setText("Hi");
});
return a.exec();
}
main.pro
TEMPLATE = app
TARGET = main
QT += widgets
CONFIG += c++11
SOURCES += main.cpp
Построить и запустить
qmake && make && ./main
Также обратите внимание, что создание глобального указателя для объекта QPushButton - плохая идея. Это не только утечка памяти, но и другие проблемы.
1) QApplication не имеет test()
слот в нем. Вам нужно создать свой собственный класс, наследующий QApplication, и дать этому классу test()
слот. Что вы сделали, это создали обычную функцию, которая не поможет.
2) Вы не проверили возвращаемое значение connect, что означает, что вы не видели, что оно выдает ошибку, что, вероятно, дало бы вам некоторые подсказки.
Вы можете подключить сигналы к слотам, которые находятся в классах, полученных из QObject
поэтому мета-компилятор может выводить вызовы слотов. Но твой test()
это глобальная функция. Вы должны поместить свою слот-функцию в класс, производный от QObject
и поддерживает Q_OBJECT
макрос или определение лямбда-функции (с поддержкой C++11), как показал Ласло Папп.
Пример:
// testwrapper.h
class TestWrapper : public QObject
{
Q_OBJECT
//...
public slots:
void test();
};
// main.cpp
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
QtProject w;
w.show();
QPushButton * lpTestBtn = w.window()->findChild<QPushButton*>("TestBtn");
TestWrapper tw;
CONNECT( lpTestBtn, SIGNAL( clicked()),tw,SLOT( test()));
return a.exec();
}