* @brief Opens a Save dialog for the report path and launches the export on accept. */
| 892 | * @brief Opens a Save dialog for the report path and launches the export on accept. |
| 893 | */ |
| 894 | void Sessions::DatabaseManager::requestPdfOutputPath(int sessionId, HtmlReportOptions opts) |
| 895 | { |
| 896 | const bool wantsPdf = (opts.format != HtmlReportOptions::Format::Html); |
| 897 | const QString ext = wantsPdf ? QStringLiteral("pdf") : QStringLiteral("html"); |
| 898 | const QString title = wantsPdf ? tr("Save PDF Report") : tr("Save HTML Report"); |
| 899 | const QString filter = wantsPdf ? tr("PDF files (*.pdf)") : tr("HTML files (*.html)"); |
| 900 | |
| 901 | const auto meta = sessionMetadata(sessionId); |
| 902 | const QString projTitle = meta.value("project_title").toString(); |
| 903 | const QString safeProj = sanitiseTitleForPath(projTitle); |
| 904 | const QString dir = |
| 905 | QStringLiteral("%1/%2").arg(Misc::WorkspaceManager::instance().path("Reports"), safeProj); |
| 906 | QDir().mkpath(dir); |
| 907 | |
| 908 | const QString baseName = opts.documentTitle.isEmpty() |
| 909 | ? QStringLiteral("session_%1").arg(sessionId) |
| 910 | : sanitiseTitleForPath(opts.documentTitle); |
| 911 | const QString suggested = QStringLiteral("%1/%2.%3").arg(dir, baseName, ext); |
| 912 | |
| 913 | auto* dialog = new QFileDialog(qApp->activeWindow(), title, suggested, filter); |
| 914 | dialog->setAcceptMode(QFileDialog::AcceptSave); |
| 915 | dialog->setFileMode(QFileDialog::AnyFile); |
| 916 | dialog->setAttribute(Qt::WA_DeleteOnClose); |
| 917 | |
| 918 | connect(dialog, |
| 919 | &QFileDialog::fileSelected, |
| 920 | this, |
| 921 | [this, opts, ext, sessionId](const QString& path) mutable { |
| 922 | if (path.isEmpty()) { |
| 923 | Q_EMIT pdfExportFinished(QString(), false); |
| 924 | return; |
| 925 | } |
| 926 | |
| 927 | QMetaObject::invokeMethod( |
| 928 | this, |
| 929 | [this, opts = std::move(opts), ext, sessionId, path]() mutable { |
| 930 | QString finalPath = path; |
| 931 | const QString dot = QStringLiteral(".") + ext; |
| 932 | if (!finalPath.endsWith(dot, Qt::CaseInsensitive)) |
| 933 | finalPath += dot; |
| 934 | |
| 935 | opts.outputPath = finalPath; |
| 936 | launchPdfExport(sessionId, std::move(opts)); |
| 937 | }, |
| 938 | Qt::QueuedConnection); |
| 939 | }); |
| 940 | |
| 941 | connect( |
| 942 | dialog, &QFileDialog::rejected, this, [this] { Q_EMIT pdfExportFinished(QString(), false); }); |
| 943 | |
| 944 | dialog->open(); |
| 945 | } |
| 946 | |
| 947 | /** |
| 948 | * @brief Continues the PDF flow on the main thread once the worker has shipped data. |
nothing calls this directly
no test coverage detected