From 66dd35254724ec5d4471a8be71f92e06cf0fa8e8 Mon Sep 17 00:00:00 2001 From: Javier Date: Sun, 12 Sep 2021 01:36:41 +0200 Subject: add ability to export a stroke list in plain text --- mainwindow.cc | 21 ++++++++++++++- mainwindow.h | 1 + notebookview.cc | 9 ++++++- notebookview.h | 4 ++- scribiu.pro | 2 ++ stfgraphicsitem.cc | 11 +++----- stfreader.cc | 2 +- stfreader.h | 2 +- stftxtexport.cc | 79 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ stftxtexport.h | 35 ++++++++++++++++++++++++ 10 files changed, 153 insertions(+), 13 deletions(-) create mode 100644 stftxtexport.cc create mode 100644 stftxtexport.h diff --git a/mainwindow.cc b/mainwindow.cc index bba19cc..8a32f2c 100644 --- a/mainwindow.cc +++ b/mainwindow.cc @@ -117,7 +117,7 @@ void MainWindow::openNotebook(const QString &pen, const QString ¬ebook) void MainWindow::exportCurrentPageAsPng(const QString &file) { qDebug() << "Exporting current page" << ui->notebookView->curPage() << "to" << file; - QImage image = ui->notebookView->exportPage(ui->notebookView->curPage()); + QImage image = ui->notebookView->exportPageAsImage(ui->notebookView->curPage()); if (!image.save(file, "PNG")) { QMessageBox::warning(this, tr("Export page"), tr("Could not export current page to '%s'").arg(file)); @@ -139,6 +139,18 @@ void MainWindow::exportCurrentPageAsSvg(const QString &file) painter.end(); } +void MainWindow::exportCurrentPageAsStrokeListTxt(const QString &file) +{ + QFile f(file); + if (!f.open(QIODevice::WriteOnly | QIODevice::Truncate | QIODevice::Text)) { + QMessageBox::warning(this, tr("Export page"), + tr("Could not export current page to '%s'").arg(file)); + return; + } + ui->notebookView->exportPageAsStrokeList(&f, ui->notebookView->curPage()); + f.close(); +} + void MainWindow::exportCurrentPaperReplayAsAac(const QString &file) { QString src = _media->currentSource().fileName(); @@ -311,6 +323,7 @@ void MainWindow::handleExport() QStringList filters; filters << tr("Current page as PNG image (*.png)") << tr("Current page as SVG image (*.svg)") + << tr("Current page as stroke list text file (*.txt)") << tr("Current audio as AAC (*.aac)"); QString filter; QString fileName = QFileDialog::getSaveFileName(this, tr("Export page"), QString(), @@ -331,6 +344,12 @@ void MainWindow::handleExport() exportCurrentPageAsSvg(fileName); break; case 2: + if (!fileName.endsWith(".txt", Qt::CaseInsensitive)) { + fileName.append(".txt"); + } + exportCurrentPageAsStrokeListTxt(fileName); + break; + case 3: if (!fileName.endsWith(".aac", Qt::CaseInsensitive)) { fileName.append(".aac"); } diff --git a/mainwindow.h b/mainwindow.h index f3f6128..c7a871f 100644 --- a/mainwindow.h +++ b/mainwindow.h @@ -45,6 +45,7 @@ public slots: void exportCurrentPageAsPng(const QString &file); void exportCurrentPageAsSvg(const QString &file); + void exportCurrentPageAsStrokeListTxt(const QString &file); void exportCurrentPaperReplayAsAac(const QString &file); private slots: diff --git a/notebookview.cc b/notebookview.cc index 833f8e8..c8fd1c0 100644 --- a/notebookview.cc +++ b/notebookview.cc @@ -18,6 +18,7 @@ #include #include +#include "stftxtexport.h" #include "notebookview.h" #define VIEW_MARGIN 2 @@ -121,7 +122,7 @@ QRect NotebookView::getCurPageTrim() const return _nb->getPageTrim(_curPage); } -QImage NotebookView::exportPage(int pageNum) const +QImage NotebookView::exportPageAsImage(int pageNum) const { const QRect pageTrim = _nb->getPageTrim(pageNum); QImage image(pageTrim.width() / 4, pageTrim.height() / 4, QImage::Format_RGB32); @@ -139,6 +140,12 @@ void NotebookView::renderPage(QPainter *painter, int pageNum, const QRectF &targ scene.render(painter, target, source, Qt::KeepAspectRatio); } +void NotebookView::exportPageAsStrokeList(QIODevice *device, int pageNum) +{ + StfTxtExport writer(_nb); + writer.exportStrokeList(device, pageNum); +} + void NotebookView::requestPaperReplay(const QString &file, qint64 time) { emit paperReplayRequested(file, time); diff --git a/notebookview.h b/notebookview.h index 720a1a2..4e557d1 100644 --- a/notebookview.h +++ b/notebookview.h @@ -53,9 +53,11 @@ public: QSize getCurPageSize() const; QRect getCurPageTrim() const; - QImage exportPage(int pageNum) const; + QImage exportPageAsImage(int pageNum) const; void renderPage(QPainter *painter, int pageNum, const QRectF &target = QRectF(), const QRectF &source = QRectF()) const; + void exportPageAsStrokeList(QIODevice *device, int pageNum); + void requestPaperReplay(const QString &file, qint64 time); signals: diff --git a/scribiu.pro b/scribiu.pro index 2393158..1c82948 100644 --- a/scribiu.pro +++ b/scribiu.pro @@ -28,6 +28,7 @@ SOURCES += main.cc \ afdnotebook.cc \ pageitem.cc \ stfgraphicsitem.cc \ + stftxtexport.cc \ paperreplay.cc \ afdpageaddress.cc \ stfstrokeitem.cc \ @@ -43,6 +44,7 @@ HEADERS += mainwindow.h \ afdnotebook.h \ pageitem.h \ stfgraphicsitem.h \ + stftxtexport.h \ paperreplay.h \ afdpageaddress.h \ stfstrokeitem.h \ diff --git a/stfgraphicsitem.cc b/stfgraphicsitem.cc index 75c9dfa..7ba173f 100644 --- a/stfgraphicsitem.cc +++ b/stfgraphicsitem.cc @@ -28,7 +28,7 @@ class StfToGraphicsPathItems : public StfReader::StrokeHandler { QGraphicsItem *parent; PaperReplay::SessionList replays; PaperReplay::Session replay; - qint64 startTime, lastTime; + qint64 startTime; QPainterPath path; QRectF bound; @@ -37,9 +37,6 @@ public: : parent(parent), replays(replays), path(), bound(0.0, 0.0, 1.0, 1.0) { } - ~StfToGraphicsPathItems() { - } - bool startStroke(const QPoint& p, int force, qint64 time) { Q_UNUSED(force); QList sessions = replays.sessionsDuringTime(time); @@ -49,7 +46,6 @@ public: replay = PaperReplay::Session(); } startTime = time; - lastTime = time; path = QPainterPath(QPointF(p)); return true; } @@ -57,14 +53,13 @@ public: bool strokePoint(const QPoint& p, int force, qint64 time) { Q_UNUSED(force); Q_UNUSED(time); - lastTime = time; path.lineTo(QPointF(p)); return true; } - bool endStroke() { + bool endStroke(qint64 time) { bound |= path.boundingRect(); - new StfStrokeItem(path, replay, startTime, lastTime, parent); + new StfStrokeItem(path, replay, startTime, time, parent); /* Parent will take the child down with him when deleted. */ return true; } diff --git a/stfreader.cc b/stfreader.cc index 09967cc..ff5e4f4 100644 --- a/stfreader.cc +++ b/stfreader.cc @@ -110,7 +110,7 @@ bool StfReader::parseV1(BitReader& br) if (time == 0) { if (handler) { - bool res = handler->endStroke(); + bool res = handler->endStroke(cur_time); if (!res) return false; } break; diff --git a/stfreader.h b/stfreader.h index ec7c306..45e7376 100644 --- a/stfreader.h +++ b/stfreader.h @@ -31,7 +31,7 @@ public: virtual ~StrokeHandler(); virtual bool startStroke(const QPoint& p, int force, qint64 time) = 0; virtual bool strokePoint(const QPoint& p, int force, qint64 time) = 0; - virtual bool endStroke() = 0; + virtual bool endStroke(qint64 time) = 0; }; protected: diff --git a/stftxtexport.cc b/stftxtexport.cc new file mode 100644 index 0000000..0163848 --- /dev/null +++ b/stftxtexport.cc @@ -0,0 +1,79 @@ +/* + * scribiu -- read notebooks and voice memos from Livescribe pens + * Copyright (C) 2021 Javier S. Pedro + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#include +#include +#include "stftxtexport.h" + +class StfToTxtStrokeList : public StfReader::StrokeHandler { + QTextStream _out; + QPoint _lastP; + qint64 _lastTime; + +public: + StfToTxtStrokeList(QIODevice *out) + : _out(out) { + } + + bool startStroke(const QPoint& p, int force, qint64 time) { + _out << time << " penDown " << p.x() << ' ' << p.y() << ' ' << force << '\n'; + _lastP = p; + _lastTime = time; + return true; + } + + bool strokePoint(const QPoint& p, int force, qint64 time) { + _out << time << " penMove " << p.x() << ' ' << p.y() << ' ' << force << '\n'; + _lastP = p; + _lastTime = time; + return true; + } + + bool endStroke(qint64 time) { + _out << time << " penUp " << _lastP.x() << ' ' << _lastP.y() << ' ' << 0 << '\n'; + return true; + } +}; + +StfTxtExport::StfTxtExport(AfdNotebook *nb) + : _nb(nb) +{ +} + +void StfTxtExport::exportStrokeList(QIODevice *out, int pageNum) +{ + QStringList pens = _nb->penSerials(); + if (pens.isEmpty()) return; + + QStringList strokeFiles = _nb->strokeFiles(pens.first(), pageNum); + foreach (const QString &strokeFile, strokeFiles) { + QFile in(strokeFile); + if (!in.open(QIODevice::ReadOnly)) { + qWarning() << "Could not open stroke file:" << strokeFile; + continue; + } + + StfToTxtStrokeList h(out); + StfReader r; + r.setStrokeHandler(&h); + if (!r.parse(&in)) { + qWarning() << "Could not open parse file:" << strokeFile; + continue; + } + } +} diff --git a/stftxtexport.h b/stftxtexport.h new file mode 100644 index 0000000..90a83e0 --- /dev/null +++ b/stftxtexport.h @@ -0,0 +1,35 @@ +/* + * scribiu -- read notebooks and voice memos from Livescribe pens + * Copyright (C) 2021 Javier S. Pedro + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#ifndef STFTXTEXPORT_H +#define STFTXTEXPORT_H + +#include "afdnotebook.h" + +class StfTxtExport +{ +public: + explicit StfTxtExport(AfdNotebook *nb); + + void exportStrokeList(QIODevice *out, int pageNum); + +private: + AfdNotebook *_nb; +}; + +#endif // STFTXTEXPORT_H -- cgit v1.2.3