Я работаю с QThread
и механизмом слотов / сигналов;Я знаю, что в Интернете в целом и в частности в SO, много обсуждений, но я все еще не смог найти решение.В любом случае, вот контекст.
Кусок кода, который я пытаюсь придумать, нацелен на управление хотя бы GUI в конечном итоге долгим процессом, поэтому используется QThread
.
У меня есть окно с двумя кнопками, запуск и остановка.Мои Window
также имеют QThread
и Task
, где последний наследуется от QObject
.Я хочу иметь возможность остановить свою задачу, когда она выполняется, и предотвратить запуск ее снова, если нажать кнопку «Пуск», когда она уже запущена.
Вот выдержка из Task
(которая подделывает длиннуюпроцесс):
class Task: public QObject
{
public:
Task(): QObject(), stop_(true) {}
private slots:
void startTask()
{
stop_ = false;
run();
}
void stopTask()
{
stop_ = true;
}
void run() const
{
while ( ! stop_)
{
sleep(1);
}
}
bool stop_;
};
Я сделал два соединения между кнопками и задачей в конструкторе моего Window
:
class Window: public QWidget
{
public:
Window()
{
// Instantiate buttons and put them in a layout.
// ...
connect(buttonStart_, SIGNAL(clicked()), &task_, SLOT(startTask()));
connect(buttonStop_, SIGNAL(clicked()), &task_, SLOT(stopTask()),
Qt::DirectConnection);
task_.moveToThread(&thread);
thread_.start();
}
private:
QPushButton buttonStart_;
QPushButton buttonStop_;
QThread thread_;
Task task_;
};
Я использовал Qt::DirectConnection
во втором connect()
чтобы «форсировать» обработку моего сигнала, запрашивающего остановку задачи, поскольку (как я понимаю) task_
необходимо вернуться из своей работы перед дальнейшей обработкой событий (если я использую соединение по умолчанию, все мои клики обрабатываются послемоя задача "выполнена").
Здесь Qt::DirectConnection
"обходит" очередь событий, и таким образом я могу остановить свою задачу.Но, честно говоря, я не знаю, является ли это правильным способом, или это обходной путь (таким образом, возможно, корень моей проблемы).
В любом случае, это работает нормально таким образом, нокогда я начинаю играть с моими кнопками, графический интерфейс в конечном итоге зависает, и это моя проблема!
Любая помощь приветствуется;спасибо за ваше время!