Я хотел бы использовать расчет отдельно от Ui-потока. Метод расчета - приватный слот MainWindow Метод. Во время вычислений происходит постепенный перенос рассчитанных данных в объект OutputData - поле окна ProgressBar. Поток, в котором выполняются вычисления, также является полем главного окна.
Конструктор главного окна, в котором создается поток, а начало расчета связано с началом потока:
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::MainWindow) {
ui->setupUi(this);
calculation = new QThread(this);
settings.setToDefault();
outputData.setToDefault();
calculationDone = false;
connect(calculation, SIGNAL(started()), this, SLOT(calculate()));
ui->results_display->setText("Загрузите <b>параметры</b> и начинайте расчёты!");
}
Метод с помощью кнопки, запуск потока и модальное окно с ProgressBar:
void MainWindow::on_calculate_button_clicked() {
ui->results_display->clear();
ui->results_display2->clear();
calculation->start();
///TODO QProgressDialog
ProgressDialog progressDialog(&outputData, this);
progressDialog.setModal(true);
progressDialog.exec();
if (progressDialog.result() == QDialog::Rejected) {
calculation->terminate();
QMessageBox::critical(this, "Результат", "Расчёт был остановлен!");
} else {
if (progressDialog.result() == QDialog::Accepted) {
calculation->quit();
QMessageBox::about(this, "Результат", "Готово!");
}
}
}
Модальный оконный конструктор устанавливает параметры ProgressBar, создает таймер и устанавливает связь между таймером и методом обновления:
ProgressDialog::ProgressDialog(OutputData *outputData, QWidget *parent) :
QDialog(parent),
ui(new Ui::ProgressDialog) {
ui->setupUi(this);
data = outputData;
ui->quantity_label->setText("0");
ui->progressBar->setMinimum(0);
ui->progressBar->setMaximum(static_cast<int>(data->outputSettings.aircraftQuantity));
timer = new QTimer(this);
timer->setSingleShot(false);
connect(timer, SIGNAL(timeout()), this, SLOT(update()));
timer->start(50);
}
Метод обновления ProgressBar:
void ProgressDialog::update() {
unsigned long aircraftsDone = data->results.size() + data->unprocessedAircrafts.size();
ui->progressBar->setValue(static_cast<int>(aircraftsDone));
ui->aircraftQunatityDone_label->setText(QString::number(aircraftsDone));
ui->progressBar->repaint();
if (aircraftsDone == data->outputSettings.aircraftQuantity) {
accept();
}
}
Расчеты в настоящее время работают хорошо, но информация о прогрессе не рисуется и не обновляется.