From a4051749fdb2dc94013673702e1d1858294541bd Mon Sep 17 00:00:00 2001 From: Berthold Stoeger Date: Mon, 1 Oct 2018 14:17:38 +0200 Subject: [PATCH] Import: import Poseidon MkVI logs via DiveLogImportDialog Poseidon MkVI logs (.txt) were special cased in MainWindow.cpp, which led to a user-interface inconsistency. In some cases [user chooses ".txt" (non-Poseidon) and ".csv"], *two* import-dialogs were shown. Move handling of Poseidon MkVI logs into DiveLogImportDialog. There are already other "special" cases handled in this dialog. At the moment, this shows the first 10 depth-values, which is kind of useless, as this will all be at surface level. We might think about something more useful. Signed-off-by: Berthold Stoeger --- desktop-widgets/divelogimportdialog.cpp | 57 ++++++++++++++++++++--- desktop-widgets/divelogimportdialog.h | 2 +- desktop-widgets/mainwindow.cpp | 60 +++++++++---------------- desktop-widgets/mainwindow.h | 1 - 4 files changed, 72 insertions(+), 48 deletions(-) diff --git a/desktop-widgets/divelogimportdialog.cpp b/desktop-widgets/divelogimportdialog.cpp index 2068c3916..63655b5ea 100644 --- a/desktop-widgets/divelogimportdialog.cpp +++ b/desktop-widgets/divelogimportdialog.cpp @@ -27,6 +27,7 @@ const DiveLogImportDialog::CSVAppConfig DiveLogImportDialog::CSVApps[CSVAPPS] = { "Seabear CSV", 0, 1, 5, -1, -1, -1, -1, -1, 2, 3, 4, 6, -1, ";" }, { "SubsurfaceCSV", -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, "Tab" }, { "AV1", 0, 1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, " " }, + { "Poseidon MkVI", 0, 2, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, "," }, { NULL, SILENCE_WARNING } }; @@ -39,7 +40,8 @@ enum Known { SENSUS, SEABEAR, SUBSURFACE, - AV1 + AV1, + POSEIDON }; ColumnNameProvider::ColumnNameProvider(QObject *parent) : QAbstractListModel(parent) @@ -107,8 +109,6 @@ int ColumnNameProvider::mymatch(QString value) const return -1; } - - ColumnNameView::ColumnNameView(QWidget*) { setAcceptDrops(true); @@ -345,6 +345,7 @@ DiveLogImportDialog::DiveLogImportDialog(QStringList fn, QWidget *parent) : QDia specialCSV << SUBSURFACE; specialCSV << DL7; specialCSV << AV1; + specialCSV << POSEIDON; for (int i = 0; !CSVApps[i].name.isNull(); ++i) ui->knownImports->addItem(CSVApps[i].name); @@ -378,9 +379,24 @@ void DiveLogImportDialog::loadFileContentsKnownTypesSelected(int value) loadFileContents(value, KNOWNTYPES); } +// Turn a "*.csv" or "*.txt" filename into a pair of both, "*.csv" and "*.txt". +// If the input wasn't either "*.csv" or "*.txt", then both returned strings +// are empty +static QPair poseidonFileNames(const QString &fn) +{ + if (fn.endsWith(".csv", Qt::CaseInsensitive)) { + QString txt = fn.left(fn.size() - 3) + "txt"; + return { fn, txt }; + } else if (fn.endsWith(".txt", Qt::CaseInsensitive)) { + QString csv = fn.left(fn.size() - 3) + "csv"; + return { csv, fn }; + } else { + return { QString(), QString() }; + } +} + void DiveLogImportDialog::loadFileContents(int value, whatChanged triggeredBy) { - QFile f(fileNames.first()); QList fileColumns; QStringList currColumns; QStringList headers; @@ -389,6 +405,7 @@ void DiveLogImportDialog::loadFileContents(int value, whatChanged triggeredBy) bool xp5 = false; bool apd = false; bool dl7 = false; + bool poseidon = false; // reset everything ColumnNameProvider *provider = new ColumnNameProvider(this); @@ -397,6 +414,26 @@ void DiveLogImportDialog::loadFileContents(int value, whatChanged triggeredBy) resultModel = new ColumnNameResult(this); ui->tableView->setModel(resultModel); + // Poseidon MkVI is special: it is made up of a .csv *and* a .txt file. + // If the user specified one, we'll try to check for the other. + QString fileName = fileNames.first(); + QPair pair = poseidonFileNames(fileName); + if (!pair.second.isEmpty()) { + QFile f_txt(pair.second); + f_txt.open(QFile::ReadOnly); + QString firstLine = f_txt.readLine(); + if (firstLine.startsWith("MkVI_Config ")) { + poseidon = true; + fileName = pair.first; // Read data from CSV + headers.append("Time"); + headers.append("Depth"); + blockSignals(true); + ui->knownImports->setCurrentText("Poseidon MkVI"); + blockSignals(false); + } + } + + QFile f(fileName); f.open(QFile::ReadOnly); QString firstLine = f.readLine(); if (firstLine.contains("SEABEAR")) { @@ -497,11 +534,8 @@ void DiveLogImportDialog::loadFileContents(int value, whatChanged triggeredBy) } } firstLine = f.readLine().trimmed(); - } - - // Special handling for APD Log Viewer if ((triggeredBy == KNOWNTYPES && (value == APD || value == APD2)) || (triggeredBy == INITIAL && fileNames.first().endsWith(".apd", Qt::CaseInsensitive))) { QString apdseparator; @@ -726,6 +760,12 @@ void DiveLogImportDialog::loadFileContents(int value, whatChanged triggeredBy) while (rows < 10 && !f.atEnd()) { QString currLine = f.readLine().trimmed(); currColumns = currLine.split(separator); + // For Poseidon, read only columns where the second value is 8 (=depth) + if (poseidon) { + if (currColumns.size() < 3 || currColumns[1] != "8") + continue; + currColumns.removeAt(1); + } fileColumns.append(currColumns); rows += 1; } @@ -845,6 +885,9 @@ void DiveLogImportDialog::on_buttonBox_accepted() for (int i = 0; i < fileNames.size(); ++i) { if (ui->knownImports->currentText() == "Seabear CSV") { parse_seabear_log(qPrintable(fileNames[i]), &dive_table); + } else if (ui->knownImports->currentText() == "Poseidon MkVI") { + QPair pair = poseidonFileNames(fileNames[i]); + parse_txt_file(qPrintable(pair.second), qPrintable(pair.first), &dive_table); } else { char *params[49]; int pnr = 0; diff --git a/desktop-widgets/divelogimportdialog.h b/desktop-widgets/divelogimportdialog.h index a6f2a8868..318895617 100644 --- a/desktop-widgets/divelogimportdialog.h +++ b/desktop-widgets/divelogimportdialog.h @@ -121,7 +121,7 @@ private: QString separator; }; -#define CSVAPPS 10 +#define CSVAPPS 11 static const CSVAppConfig CSVApps[CSVAPPS]; }; diff --git a/desktop-widgets/mainwindow.cpp b/desktop-widgets/mainwindow.cpp index e6b3424e8..0ab46fafd 100644 --- a/desktop-widgets/mainwindow.cpp +++ b/desktop-widgets/mainwindow.cpp @@ -1742,35 +1742,6 @@ void MainWindow::importFiles(const QStringList fileNames) refreshDisplay(); } -void MainWindow::importTxtFiles(const QStringList fileNames) -{ - QStringList csvFiles; - - if (fileNames.isEmpty()) - return; - - QByteArray fileNamePtr, csv; - - for (int i = 0; i < fileNames.size(); ++i) { - csv = fileNamePtr = QFile::encodeName(fileNames.at(i)); - csv.replace(csv.size() - 3, 3, "csv"); - - QFileInfo check_file(csv); - if (check_file.exists() && check_file.isFile()) { - if (parse_txt_file(fileNamePtr.data(), csv, &dive_table) == 0) - csvFiles += fileNames.at(i); - } else { - csvFiles += fileNamePtr; - } - } - if (csvFiles.size()) { - DiveLogImportDialog *diveLogImport = new DiveLogImportDialog(csvFiles, this); - diveLogImport->show(); - } - process_imported_dives(false); - refreshDisplay(); -} - void MainWindow::loadFiles(const QStringList fileNames) { if (fileNames.isEmpty()) { @@ -1805,6 +1776,19 @@ void MainWindow::loadFiles(const QStringList fileNames) } } +static const char *csvExtensions[] = { + ".csv", ".apd", ".zxu", ".zxl", ".txt" +}; + +static bool isCsvFile(const QString &s) +{ + for (const char *ext: csvExtensions) { + if (s.endsWith(ext, Qt::CaseInsensitive)) + return true; + } + return false; +} + void MainWindow::on_actionImportDiveLog_triggered() { QStringList fileNames = QFileDialog::getOpenFileNames(this, tr("Open dive log file"), lastUsedDir(), filter_import()); @@ -1813,12 +1797,14 @@ void MainWindow::on_actionImportDiveLog_triggered() return; updateLastUsedDir(QFileInfo(fileNames[0]).dir().path()); - QStringList logFiles = fileNames.filter(QRegExp("^(?!.*\\.(csv|txt|apd|zxu|zxl))", Qt::CaseInsensitive)); - QStringList csvFiles = fileNames.filter(".csv", Qt::CaseInsensitive); - csvFiles += fileNames.filter(".apd", Qt::CaseInsensitive); - csvFiles += fileNames.filter(".zxu", Qt::CaseInsensitive); - csvFiles += fileNames.filter(".zxl", Qt::CaseInsensitive); - QStringList txtFiles = fileNames.filter(".txt", Qt::CaseInsensitive); + QStringList logFiles; + QStringList csvFiles; + for (const QString &fn: fileNames) { + if (isCsvFile(fn)) + csvFiles.append(fn); + else + logFiles.append(fn); + } if (logFiles.size()) { importFiles(logFiles); @@ -1828,10 +1814,6 @@ void MainWindow::on_actionImportDiveLog_triggered() DiveLogImportDialog *diveLogImport = new DiveLogImportDialog(csvFiles, this); diveLogImport->show(); } - - if (txtFiles.size()) { - importTxtFiles(txtFiles); - } } void MainWindow::editCurrentDive() diff --git a/desktop-widgets/mainwindow.h b/desktop-widgets/mainwindow.h index c047a31e3..05f6ade68 100644 --- a/desktop-widgets/mainwindow.h +++ b/desktop-widgets/mainwindow.h @@ -73,7 +73,6 @@ public: void loadFiles(const QStringList files); void importFiles(const QStringList importFiles); - void importTxtFiles(const QStringList fileNames); void cleanUpEmpty(); void setToolButtonsEnabled(bool enabled); ProfileWidget2 *graphics() const;