From c954c2654cc1735d62ab6885829c7e22258a81cd Mon Sep 17 00:00:00 2001 From: Roman Telezhynskyi Date: Thu, 14 May 2015 15:27:04 +0300 Subject: [PATCH] Print/Save functions. --HG-- branch : feature --- src/app/mainwindow.cpp | 40 +- src/app/mainwindow.h | 9 +- src/app/mainwindow.ui | 137 +++- src/app/mainwindowsnogui.cpp | 655 +++++++++++++++++- src/app/mainwindowsnogui.h | 42 ++ src/app/share/resources/icon.qrc | 1 + .../icon/32x32/export_to_picture_document.png | Bin 0 -> 4181 bytes 7 files changed, 863 insertions(+), 21 deletions(-) create mode 100644 src/app/share/resources/icon/32x32/export_to_picture_document.png diff --git a/src/app/mainwindow.cpp b/src/app/mainwindow.cpp index 0aff6c557..b8a16bd18 100644 --- a/src/app/mainwindow.cpp +++ b/src/app/mainwindow.cpp @@ -73,10 +73,10 @@ Q_LOGGING_CATEGORY(vMainWindow, "v.mainwindow") * @param parent parent widget. */ MainWindow::MainWindow(QWidget *parent) - :MainWindowsNoGUI(parent), ui(new Ui::MainWindow), doc(nullptr), currentTool(Tool::Arrow), + :MainWindowsNoGUI(parent), ui(new Ui::MainWindow), currentTool(Tool::Arrow), lastUsedTool(Tool::Arrow), sceneDraw(nullptr), sceneDetails(nullptr), mouseCoordinate(nullptr), helpLabel(nullptr), isInitialized(false), dialogTable(nullptr), dialogTool(nullptr), - dialogHistory(nullptr), comboBoxDraws(nullptr), curFile(QString()), mode(Draw::Calculation), currentDrawIndex(0), + dialogHistory(nullptr), comboBoxDraws(nullptr), mode(Draw::Calculation), currentDrawIndex(0), currentToolBoxIndex(0), drawMode(true), recentFileActs(), separatorAct(nullptr), autoSaveTimer(nullptr), guiEnabled(true), gradationHeights(nullptr), gradationSizes(nullptr), @@ -818,7 +818,7 @@ void MainWindow::ClearLayout() shadows.clear(); papers.clear(); ui->listWidget->clear(); - //EnableActions(false); + SetLayoutModeActions(false); } //--------------------------------------------------------------------------------------------------------------------- @@ -833,7 +833,7 @@ void MainWindow::PrepareSceneList() if (not scenes.isEmpty()) { ui->listWidget->setCurrentRow(0); - //EnableActions(true); + SetLayoutModeActions(true); } } @@ -1804,6 +1804,7 @@ void MainWindow::Layout() { ui->actionDetails->setEnabled(true); ui->actionLayout->setEnabled(true); + SetLayoutModeActions(true); } else { @@ -1811,6 +1812,7 @@ void MainWindow::Layout() ui->actionDetails->setEnabled(false); ui->actionLayout->setEnabled(false); ui->actionDraw->setChecked(true); + SetLayoutModeActions(false); } } @@ -1970,6 +1972,7 @@ void MainWindow::PatternWasModified(bool saved) { setWindowModified(!saved); ui->actionSave->setEnabled(!saved); + isLayoutStale = true; } } @@ -2123,6 +2126,23 @@ void MainWindow::SetEnableTool(bool enable) ui->toolButtonLayoutSettings->setEnabled(layoutTools); } +//--------------------------------------------------------------------------------------------------------------------- +void MainWindow::SetLayoutModeActions(bool enable) +{ + bool value = enable; + if (scenes.isEmpty()) + { + value = false; + } + ui->actionExportAs->setEnabled(value); + ui->actionPrintPreview->setEnabled(value); + ui->actionPrintPreviewTailed->setEnabled(value); + ui->actionSaveAsPDF->setEnabled(value); + ui->actionSaveAsTiledPDF->setEnabled(value); + ui->actionPrint->setEnabled(value); + ui->actionPrintTiled->setEnabled(value); +} + //--------------------------------------------------------------------------------------------------------------------- /** * @brief MinimumScrollBar set scroll bar to minimum. @@ -2524,6 +2544,14 @@ void MainWindow::CreateActions() connect(ui->actionEdit_pattern_code, &QAction::triggered, this, &MainWindow::EditPatternCode); connect(ui->actionCloseWindow, &QAction::triggered, this, &MainWindow::ResetWindow); connect(ui->actionShowCurveDetails, &QAction::triggered, this, &MainWindow::ActionCurveDetailsMode); + + connect(ui->actionExportAs, &QAction::triggered, this, &MainWindow::ExportLayoutAs); + connect(ui->actionPrintPreview, &QAction::triggered, this, &MainWindow::PrintPreviewOrigin); + connect(ui->actionPrintPreviewTailed, &QAction::triggered, this, &MainWindow::PrintPreviewTiled); + connect(ui->actionSaveAsPDF, &QAction::triggered, this, &MainWindow::SaveAsPDF); + connect(ui->actionSaveAsTiledPDF, &QAction::triggered, this, &MainWindow::SaveAsTiledPDF); + connect(ui->actionPrint, &QAction::triggered, this, &MainWindow::PrintOrigin); + connect(ui->actionPrintTiled, &QAction::triggered, this, &MainWindow::PrintTiled); ui->actionEdit_pattern_code->setEnabled(false); //Actions for recent files loaded by a main window application. @@ -2787,12 +2815,12 @@ void MainWindow::ShowPaper(int index) if (index < 0 || index >= scenes.size()) { ui->view->setScene(tempSceneLayout); - //EnableActions(false); + SetLayoutModeActions(false); } else { ui->view->setScene(scenes.at(index)); - //EnableActions(true); + SetLayoutModeActions(true); } ui->view->fitInView(ui->view->scene()->sceneRect(), Qt::KeepAspectRatio); diff --git a/src/app/mainwindow.h b/src/app/mainwindow.h index c140b2451..07288e4bf 100644 --- a/src/app/mainwindow.h +++ b/src/app/mainwindow.h @@ -35,8 +35,6 @@ #include "tools/vtooldetail.h" #include "tools/vtooluniondetails.h" #include "tools/drawTools/drawtools.h" -#include "xml/vdomdocument.h" - namespace Ui { @@ -156,8 +154,7 @@ private: /** @brief ui keeps information about user interface */ Ui::MainWindow *ui; - /** @brief doc dom document container */ - VPattern *doc; + /** @brief tool current tool */ Tool currentTool; @@ -187,9 +184,6 @@ private: /** @brief comboBoxDraws comboc who show name of pattern peaces. */ QComboBox *comboBoxDraws; - /** @brief fileName name current pattern file. */ - QString curFile; - /** @brief mode keep current draw mode. */ Draw mode; @@ -222,6 +216,7 @@ private: void SetEnableWidgets(bool enable); void SetEnableTool(bool enable); + void SetLayoutModeActions(bool enable); void SaveCurrentScene(); void RestoreCurrentScene(); diff --git a/src/app/mainwindow.ui b/src/app/mainwindow.ui index b502d1349..d3f5123c9 100644 --- a/src/app/mainwindow.ui +++ b/src/app/mainwindow.ui @@ -50,7 +50,7 @@ 0 0 - 100 + 105 272 @@ -337,7 +337,7 @@ 0 0 - 100 + 105 58 @@ -413,7 +413,7 @@ 0 0 - 100 + 105 156 @@ -567,7 +567,7 @@ 0 0 - 100 + 105 104 @@ -745,8 +745,8 @@ 0 0 - 87 - 58 + 105 + 380 @@ -815,11 +815,27 @@ &File + + + Layout + + + + + + + + + + + + + @@ -1514,6 +1530,115 @@ F2 + + + false + + + + :/icon/32x32/pdf.png:/icon/32x32/pdf.png + + + Save as PDF + + + Save original layout + + + + + false + + + + :/icon/32x32/pdf.png:/icon/32x32/pdf.png + + + Save as tiled PDF + + + Split and save a layout into smaller pages + + + + + false + + + + + + + + Print + + + Print original a layout + + + + + false + + + + + + + + Print tiled + + + Split and print a layout into smaller pages (for regular printers) + + + + + false + + + + + + + + Print preview + + + Print preview original layout + + + + + false + + + + + + + + Print preview tailed + + + Print preview tailed layout + + + + + false + + + + :/icon/32x32/export_to_picture_document.png:/icon/32x32/export_to_picture_document.png + + + Export As... + + + Export original layout + + diff --git a/src/app/mainwindowsnogui.cpp b/src/app/mainwindowsnogui.cpp index fdbf6360f..f59c1fb1b 100644 --- a/src/app/mainwindowsnogui.cpp +++ b/src/app/mainwindowsnogui.cpp @@ -29,21 +29,36 @@ #include "mainwindowsnogui.h" #include "../core/vapplication.h" #include "../container/vcontainer.h" +#include "../../libs/vobj/vobjpaintdevice.h" #include "../dialogs/app/dialoglayoutsettings.h" #include "../../libs/vlayout/vlayoutgenerator.h" #include "../dialogs/app/dialoglayoutprogress.h" #include "../dialogs/app/dialogsavelayout.h" #include "../../libs/vlayout/vposter.h" +#include +#include #include +#include +#include #include +#include +#include +#include +#include + +#ifdef Q_OS_WIN +# define PDFTOPS "pdftops.exe" +#else +# define PDFTOPS "pdftops" +#endif //--------------------------------------------------------------------------------------------------------------------- MainWindowsNoGUI::MainWindowsNoGUI(QWidget *parent) : QMainWindow(parent), listDetails(QVector()), currentScene(nullptr), tempSceneLayout(nullptr), - pattern(new VContainer()), papers(QList()), shadows(QList()), + pattern(new VContainer()), doc(nullptr), papers(QList()), shadows(QList()), scenes(QList()), details(QList >()), undoAction(nullptr), - redoAction(nullptr), actionDockWidgetToolOptions(nullptr) + redoAction(nullptr), actionDockWidgetToolOptions(nullptr), curFile(QString()), isLayoutStale(true), isTiled(false) { InitTempLayoutScene(); } @@ -92,6 +107,7 @@ void MainWindowsNoGUI::ToolLayoutSettings(bool checked) CreateShadows(); CreateScenes(); PrepareSceneList(); + isLayoutStale = false; break; case LayoutErrors::ProcessStoped: break; @@ -111,6 +127,224 @@ void MainWindowsNoGUI::ToolLayoutSettings(bool checked) } } +//--------------------------------------------------------------------------------------------------------------------- +void MainWindowsNoGUI::ExportLayoutAs() +{ + if (isLayoutStale) + { + if (ContinueIfLayoutStale() == QMessageBox::No) + { + return; + } + } + QMap extByMessage = InitFormates(); + DialogSaveLayout dialog(extByMessage, scenes.size(), FileName(), this); + + if (dialog.exec() == QDialog::Rejected) + { + return; + } + + QString suf = dialog.Formate(); + suf.replace(".", ""); + + const QString path = dialog.Path(); + qApp->getSettings()->SetPathLayout(path); + const QString mask = dialog.FileName(); + + for (int i=0; i < scenes.size(); ++i) + { + QGraphicsRectItem *paper = qgraphicsitem_cast(papers.at(i)); + if (paper) + { + const QString name = path + "/" + mask+QString::number(i+1) + dialog.Formate(); + QBrush *brush = new QBrush(); + brush->setColor( QColor( Qt::white ) ); + scenes[i]->setBackgroundBrush( *brush ); + shadows[i]->setVisible(false); + paper->setPen(QPen(Qt::white, 0.1, Qt::NoPen)); + const QStringList suffix = QStringList() << "svg" << "png" << "pdf" << "eps" << "ps" << "obj"; + switch (suffix.indexOf(suf)) + { + case 0: //svg + paper->setVisible(false); + SvgFile(name, i); + paper->setVisible(true); + break; + case 1: //png + PngFile(name, i); + break; + case 2: //pdf + PdfFile(name, i); + break; + case 3: //eps + EpsFile(name, i); + break; + case 4: //ps + PsFile(name, i); + break; + case 5: //obj + paper->setVisible(false); + ObjFile(name, i); + paper->setVisible(true); + break; + default: + qDebug() << "Can't recognize file suffix." << Q_FUNC_INFO; + break; + } + paper->setPen(QPen(Qt::black, qApp->toPixel(qApp->widthMainLine()))); + brush->setColor( QColor( Qt::gray ) ); + brush->setStyle( Qt::SolidPattern ); + scenes[i]->setBackgroundBrush( *brush ); + shadows[i]->setVisible(true); + delete brush; + } + } +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindowsNoGUI::SaveAsPDF() +{ + if (not isPagesUniform()) + { + qCritical()< images = AllSheets(); + + QVector poster; + if (isTiled) + { + VPoster posterazor(printer); + for (int i=0; i < images.size(); i++) + { + poster += posterazor.Generate(images.at(i), i+1, images.size()); + } + } + else + { + poster = images; + } + + QPainter painter; + if (not painter.begin(printer)) + { // failed to open file + qWarning("failed to open file, is it writable?"); + return; + } + + // Handle the fromPage(), toPage(), supportsMultipleCopies(), and numCopies() values from QPrinter. + int firstPage = printer->fromPage() - 1; + if (firstPage >= poster.size()) + { + return; + } + if (firstPage == -1) + { + firstPage = 0; + } + + int lastPage = printer->toPage() - 1; + if (lastPage == -1 || lastPage >= poster.size()) + { + lastPage = poster.size() - 1; + } + + const int numPages = lastPage - firstPage + 1; + int copyCount = 1; + if (not printer->supportsMultipleCopies()) + { + copyCount = printer->copyCount(); + } + + for (int i = 0; i < copyCount; ++i) + { + for (int j = 0; j < numPages; ++j) + { + if (i != 0 || j != 0) + { + if (not printer->newPage()) + { + qWarning("failed in flushing page to disk, disk full?"); + return; + } + } + int index; + if (printer->pageOrder() == QPrinter::FirstPageFirst) + { + index = firstPage + j; + } + else + { + index = lastPage - j; + } + painter.drawImage(QPointF(), poster.at(index)); + } + } + + painter.end(); +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindowsNoGUI::PrintPreviewOrigin() +{ + if (not isPagesUniform()) + { + qCritical()< *details) { @@ -220,3 +454,420 @@ void MainWindowsNoGUI::CreateScenes() scenes.append(scene); } } + +//--------------------------------------------------------------------------------------------------------------------- +QMap MainWindowsNoGUI::InitFormates() const +{ + QMap extByMessage; + extByMessage[ tr("Svg files (*.svg)") ] = ".svg"; + extByMessage[ tr("PDF files (*.pdf)") ] = ".pdf"; + extByMessage[ tr("Images (*.png)") ] = ".png"; + extByMessage[ tr("Wavefront OBJ (*.obj)") ] = ".obj"; + + QProcess proc; +#if defined(Q_OS_WIN) || defined(Q_OS_OSX) + proc.start(qApp->applicationDirPath()+"/"+PDFTOPS); // Seek pdftops in app bundle or near valentin.exe +#else + proc.start(PDFTOPS); // Seek pdftops in standard path +#endif + if (proc.waitForFinished(15000)) + { + extByMessage[ tr("PS files (*.ps)") ] = ".ps"; + extByMessage[ tr("EPS files (*.eps)") ] = ".eps"; + } + else + { + qDebug()<(papers.at(i)); + if (paper) + { + QSvgGenerator generator; + generator.setFileName(name); + generator.setSize(paper->rect().size().toSize()); + generator.setViewBox(paper->rect()); + generator.setTitle("Valentina. Pattern layout"); + generator.setDescription(doc->GetDescription()); + generator.setResolution(static_cast(qApp->PrintDPI)); + QPainter painter; + painter.begin(&generator); + painter.setFont( QFont( "Arial", 8, QFont::Normal ) ); + painter.setRenderHint(QPainter::Antialiasing, true); + painter.setPen(QPen(Qt::black, qApp->toPixel(qApp->widthHairLine()), Qt::SolidLine, Qt::RoundCap, + Qt::RoundJoin)); + painter.setBrush ( QBrush ( Qt::NoBrush ) ); + scenes.at(i)->render(&painter); + painter.end(); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +/** + * @brief PngFile save layout to png file. + * @param name name layout file. + */ +void MainWindowsNoGUI::PngFile(const QString &name, int i) const +{ + QGraphicsRectItem *paper = qgraphicsitem_cast(papers.at(i)); + if (paper) + { + const QRectF r = paper->rect(); + // Create the image with the exact size of the shrunk scene + QImage image(QSize(static_cast(r.width()), static_cast(r.height())), QImage::Format_ARGB32); + image.fill(Qt::transparent); // Start all pixels transparent + QPainter painter(&image); + painter.setFont( QFont( "Arial", 8, QFont::Normal ) ); + painter.setRenderHint(QPainter::Antialiasing, true); + painter.setPen(QPen(Qt::black, qApp->toPixel(qApp->widthMainLine()), Qt::SolidLine, Qt::RoundCap, + Qt::RoundJoin)); + painter.setBrush ( QBrush ( Qt::NoBrush ) ); + scenes.at(i)->render(&painter, r, r); + image.save(name); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +/** + * @brief PdfFile save layout to pdf file. + * @param name name layout file. + */ +void MainWindowsNoGUI::PdfFile(const QString &name, int i) const +{ + QGraphicsRectItem *paper = qgraphicsitem_cast(papers.at(i)); + if (paper) + { + QPrinter printer; + printer.setCreator(qApp->applicationDisplayName()+" "+qApp->applicationVersion()); + printer.setOutputFormat(QPrinter::PdfFormat); + printer.setOutputFileName(name); + printer.setDocName(FileName()); + const QRectF r = paper->rect(); + printer.setResolution(static_cast(qApp->PrintDPI)); + // Set orientation + if (paper->rect().height()>= paper->rect().width()) + { + printer.setOrientation(QPrinter::Portrait); + } + else + { + printer.setOrientation(QPrinter::Landscape); + } + printer.setPaperSize ( QSizeF(qApp->fromPixel(r.width(), Unit::Mm), qApp->fromPixel(r.height(), Unit::Mm)), + QPrinter::Millimeter ); + QPainter painter; + if (painter.begin( &printer ) == false) + { // failed to open file + qCritical("Can't open printer %s", qPrintable(name)); + return; + } + painter.setFont( QFont( "Arial", 8, QFont::Normal ) ); + painter.setRenderHint(QPainter::Antialiasing, true); + painter.setPen(QPen(Qt::black, qApp->toPixel(qApp->widthMainLine()), Qt::SolidLine, Qt::RoundCap, + Qt::RoundJoin)); + painter.setBrush ( QBrush ( Qt::NoBrush ) ); + scenes.at(i)->render(&painter); + painter.end(); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +/** + * @brief EpsFile save layout to eps file. + * @param name name layout file. + */ +void MainWindowsNoGUI::EpsFile(const QString &name, int i) const +{ + QTemporaryFile tmp; + if (tmp.open()) + { + PdfFile(tmp.fileName(), i); + QStringList params = QStringList() << "-eps" << tmp.fileName() << name; + PdfToPs(params); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +/** + * @brief PsFile save layout to ps file. + * @param name name layout file. + */ +void MainWindowsNoGUI::PsFile(const QString &name, int i) const +{ + QTemporaryFile tmp; + if (tmp.open()) + { + PdfFile(tmp.fileName(), i); + QStringList params = QStringList() << tmp.fileName() << name; + PdfToPs(params); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +/** + * @brief PdfToPs use external tool "pdftops" for converting pdf too eps or ps format. + * @param params string with parameter for tool. Parameters have format: "-eps input_file out_file". Use -eps when + * need create eps file. + */ +void MainWindowsNoGUI::PdfToPs(const QStringList ¶ms) const +{ +#ifndef QT_NO_CURSOR + QApplication::setOverrideCursor(Qt::WaitCursor); +#endif + QProcess proc; + proc.start(PDFTOPS, params); + proc.waitForFinished(15000); +#ifndef QT_NO_CURSOR + QApplication::restoreOverrideCursor(); +#endif + + QFile f(params.last()); + if (f.exists() == false) + { + QString msg = QString(tr("Creating file '%1' failed! %2")).arg(params.last()).arg(proc.errorString()); + QMessageBox msgBox(QMessageBox::Critical, tr("Critical error!"), msg, QMessageBox::Ok | QMessageBox::Default); + msgBox.exec(); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindowsNoGUI::ObjFile(const QString &name, int i) const +{ + QGraphicsRectItem *paper = qgraphicsitem_cast(papers.at(i)); + if (paper) + { + VObjPaintDevice generator; + generator.setFileName(name); + generator.setSize(paper->rect().size().toSize()); + generator.setResolution(static_cast(qApp->PrintDPI)); + QPainter painter; + painter.begin(&generator); + scenes.at(i)->render(&painter); + painter.end(); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +QVector MainWindowsNoGUI::AllSheets() +{ + QVector images; + for (int i=0; i < scenes.size(); ++i) + { + QGraphicsRectItem *paper = qgraphicsitem_cast(papers.at(i)); + if (paper) + { + // Hide shadow and paper border + QBrush *brush = new QBrush(); + brush->setColor( QColor( Qt::white ) ); + scenes[i]->setBackgroundBrush( *brush ); + shadows[i]->setVisible(false); + paper->setPen(QPen(Qt::white, 0.1, Qt::NoPen));// border + + // Render png + const QRectF r = paper->rect(); + // Create the image with the exact size of the shrunk scene + QImage image(QSize(static_cast(r.width()), static_cast(r.height())), QImage::Format_RGB32); + image.fill(Qt::white); + QPainter painter(&image); + painter.setFont( QFont( "Arial", 8, QFont::Normal ) ); + painter.setRenderHint(QPainter::Antialiasing, true); + painter.setPen(QPen(Qt::black, qApp->toPixel(qApp->widthMainLine()), Qt::SolidLine, Qt::RoundCap, + Qt::RoundJoin)); + painter.setBrush ( QBrush ( Qt::NoBrush ) ); + scenes.at(i)->render(&painter); + painter.end(); + images.append(image); + + // Resore + paper->setPen(QPen(Qt::black, qApp->toPixel(qApp->widthMainLine()))); + brush->setColor( QColor( Qt::gray ) ); + brush->setStyle( Qt::SolidPattern ); + scenes[i]->setBackgroundBrush( *brush ); + shadows[i]->setVisible(true); + delete brush; + } + } + return images; +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindowsNoGUI::SaveLayoutAs() +{ + if (isLayoutStale) + { + if (ContinueIfLayoutStale() == QMessageBox::No) + { + return; + } + } + QPrinter printer; + SetPrinterSettings(&printer); + printer.setOutputFormat(QPrinter::PdfFormat); + + QString fileName = QFileDialog::getSaveFileName(this, tr("Print to pdf"), + qApp->getSettings()->GetPathLayout()+"/"+FileName()+".pdf", + tr("PDF file (*.pdf)")); + if (not fileName.isEmpty()) + { + QFileInfo f( fileName ); + if(f.suffix().isEmpty()) + { + fileName.append(".pdf"); + } + qApp->getSettings()->SetPathLayout(f.absolutePath()); + + printer.setOutputFileName(fileName); + printer.setResolution(static_cast(VApplication::PrintDPI)); + PrintPages( &printer ); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindowsNoGUI::PrintPreview() +{ + if (isLayoutStale) + { + if (ContinueIfLayoutStale() == QMessageBox::No) + { + return; + } + } + QPrinterInfo def = QPrinterInfo::defaultPrinter(); + + //if there is no default printer set the print preview won't show + if(def.isNull() || def.printerName().isEmpty()) + { + if(QPrinterInfo::availablePrinters().isEmpty()) + { + QMessageBox::critical(this, tr("Print error"), + tr("Cannot proceed because there are no available printers in your system."), + QMessageBox::Ok); + return; + } + else + { + def = QPrinterInfo::availablePrinters().first(); + } + } + + QPrinter printer(def, QPrinter::ScreenResolution); + printer.setResolution(static_cast(VApplication::PrintDPI)); + SetPrinterSettings(&printer); + // display print preview dialog + QPrintPreviewDialog preview(&printer); + connect(&preview, &QPrintPreviewDialog::paintRequested, this, &MainWindowsNoGUI::PrintPages); + preview.exec(); +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindowsNoGUI::LayoutPrint() +{ + if (isLayoutStale) + { + if (ContinueIfLayoutStale() == QMessageBox::No) + { + return; + } + } + // display print dialog and if accepted print + QPrinter printer(QPrinter::HighResolution); + SetPrinterSettings(&printer); + QPrintDialog dialog( &printer, this ); + // If only user couldn't change page margins we could use method setMinMax(); + dialog.setOption(QPrintDialog::PrintCurrentPage, false); + if ( dialog.exec() == QDialog::Accepted ) + { + printer.setResolution(static_cast(VApplication::PrintDPI)); + PrintPages( &printer ); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindowsNoGUI::SetPrinterSettings(QPrinter *printer) +{ + SCASSERT(printer != nullptr) + printer->setCreator(qApp->applicationDisplayName()+" "+qApp->applicationVersion()); + + // Set orientation + if (papers.size() > 0) + { + QGraphicsRectItem *paper = qgraphicsitem_cast(papers.at(0)); + SCASSERT(paper != nullptr) + if (paper->rect().height()>= paper->rect().width()) + { + printer->setOrientation(QPrinter::Portrait); + } + else + { + printer->setOrientation(QPrinter::Landscape); + } + } + + if (not isTiled && papers.size() > 0) + { + QGraphicsRectItem *paper = qgraphicsitem_cast(papers.at(0)); + SCASSERT(paper != nullptr) + printer->setPaperSize ( QSizeF(qApp->fromPixel(paper->rect().width(), Unit::Mm), + qApp->fromPixel(paper->rect().height(), Unit::Mm)), QPrinter::Millimeter ); + } + + printer->setDocName(FileName()); +} + +//--------------------------------------------------------------------------------------------------------------------- +bool MainWindowsNoGUI::isPagesUniform() const +{ + if (papers.size() < 2) + { + return true; + } + else + { + QGraphicsRectItem *paper = qgraphicsitem_cast(papers.at(0)); + SCASSERT(paper != nullptr) + for (int i=1; i < papers.size(); ++i) + { + QGraphicsRectItem *p = qgraphicsitem_cast(papers.at(i)); + SCASSERT(p != nullptr) + if (paper->rect() != p->rect()) + { + return false; + } + } + } + return true; +} + +//--------------------------------------------------------------------------------------------------------------------- +QString MainWindowsNoGUI::FileName() const +{ + QString fileName; + curFile.isEmpty() ? fileName = tr("unnamed") : fileName = curFile; + return QFileInfo(fileName).baseName(); +} + +//--------------------------------------------------------------------------------------------------------------------- +int MainWindowsNoGUI::ContinueIfLayoutStale() +{ + QMessageBox msgBox(this); + msgBox.setIcon(QMessageBox::Question); + msgBox.setWindowTitle(tr("The layout is stale.")); + msgBox.setText(tr("The layout was not updated since last pattern modification. Do you want to continue?")); + msgBox.setStandardButtons(QMessageBox::Yes|QMessageBox::No); + msgBox.setDefaultButton(QMessageBox::No); + QSpacerItem* horizontalSpacer = new QSpacerItem(500, 0, QSizePolicy::Minimum, QSizePolicy::Expanding); + QGridLayout* layout = static_cast(msgBox.layout()); + SCASSERT(layout != nullptr); + layout->addItem(horizontalSpacer, layout->rowCount(), 0, 1, layout->columnCount()); + msgBox.exec(); + return msgBox.result(); +} diff --git a/src/app/mainwindowsnogui.h b/src/app/mainwindowsnogui.h index 0716d0382..07ac4f0cc 100644 --- a/src/app/mainwindowsnogui.h +++ b/src/app/mainwindowsnogui.h @@ -33,8 +33,10 @@ #include "../geometry/vdetail.h" #include "../libs/vlayout/vlayoutdetail.h" +#include "xml/vpattern.h" class QGraphicsScene; +class QPrinter; class MainWindowsNoGUI : public QMainWindow { @@ -45,6 +47,14 @@ public: public slots: void ToolLayoutSettings(bool checked); + void ExportLayoutAs(); + void SaveAsPDF(); + void SaveAsTiledPDF(); + void PrintPages (QPrinter *printer); + void PrintPreviewOrigin(); + void PrintPreviewTiled(); + void PrintOrigin(); + void PrintTiled(); protected: QVector listDetails; @@ -57,6 +67,9 @@ protected: /** @brief pattern container with data (points, arcs, splines, spline paths, variables) */ VContainer *pattern; + /** @brief doc dom document container */ + VPattern *doc; + QList papers; QList shadows; QList scenes; @@ -66,6 +79,11 @@ protected: QAction *redoAction; QAction *actionDockWidgetToolOptions; + /** @brief fileName name current pattern file. */ + QString curFile; + + bool isLayoutStale; + void PrepareDetailsForLayout(const QHash *details); void InitTempLayoutScene(); @@ -76,9 +94,33 @@ protected: private: Q_DISABLE_COPY(MainWindowsNoGUI) + bool isTiled; + void CreateShadows(); void CreateScenes(); + QMap InitFormates() const; + + void SvgFile(const QString &name, int i)const; + void PngFile(const QString &name, int i)const; + void PdfFile(const QString &name, int i)const; + void EpsFile(const QString &name, int i)const; + void PsFile(const QString &name, int i)const; + void PdfToPs(const QStringList ¶ms)const; + void ObjFile(const QString &name, int i)const; + + QVector AllSheets(); + + void SaveLayoutAs(); + void PrintPreview(); + void LayoutPrint(); + + void SetPrinterSettings(QPrinter *printer); + + bool isPagesUniform() const; + QString FileName() const; + + int ContinueIfLayoutStale(); }; #endif // MAINWINDOWSNOGUI_H diff --git a/src/app/share/resources/icon.qrc b/src/app/share/resources/icon.qrc index e14838f16..4b33c74c8 100644 --- a/src/app/share/resources/icon.qrc +++ b/src/app/share/resources/icon.qrc @@ -60,5 +60,6 @@ icon/16x16/fx.png icon/16x16/roll.png icon/16x16/progress.gif + icon/32x32/export_to_picture_document.png diff --git a/src/app/share/resources/icon/32x32/export_to_picture_document.png b/src/app/share/resources/icon/32x32/export_to_picture_document.png new file mode 100644 index 0000000000000000000000000000000000000000..b2f15bacfde5a1e80e604327c9c75d64cee6d4ed GIT binary patch literal 4181 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 literal 0 HcmV?d00001