Я разрабатываю приложение, в котором пользователь может анализировать некоторые двоичные файлы. После того, как он нажмет кнопку «анализ», он может сначала выбрать некоторые файлы, которые затем будут проанализированы. Пока приложение обрабатывает файлы, я хотел бы отобразить модальный диалог, который информирует пользователя о ходе выполнения (панель QProgressBar) и уже проанализированных файлах (список QListView/listModel).
Мой текущий подход состоит в том, чтобы переопределить метод exec() подсистемы QDialog. Таким образом, я мог бы просто позвонить
parseAssistant.exec()
Текущая реализация выглядит так:
class ParseAssistant : public QDialog { public: int exec(); };
int ParseAssistant::exec()
{
bar->setMaximum(files.size());
this->show();
this->setModal(true);
for (int i = 0; i < files.size(); i++) {
PluginTable* table = parser.parse(files[i]);
// do something with the table
// saveTableintoDB();
// update GUI
// bar->setValue(i);
// listModel->insertRow(0, new QStandardItem(files[i]));
}
this->hide();
return QDialog::Accepted;
}
После запуска этого (блокирующего) метода пользователь либо проанализировал все файлы, либо где-то отменил прогресс. Чтобы достичь этого, я попытался использовать QApplication::processEvents в цикле while (который кажется немного запаздывающим, поскольку он прогрессирует только после завершения синтаксического анализа файла) или передать тяжелые вычисления какой-либо реализации QConcurrent (::run, ::отображено). К сожалению, я не знаю, как вернуть поток программы обратно в метод exec() после завершения QFuture, не полагаясь на цикл с интенсивным использованием ЦП, например:
while (!future.isFinished()) { QApplication::processEvents(); }
Есть ли более разумный подход к модальному диалогу, который выполняет тяжелые вычисления (которые могут быть отменены пользователем) без блокировки цикла обработки событий?