mirror of
				https://github.com/JakubMelka/PDF4QT.git
				synced 2025-06-05 21:59:17 +02:00 
			
		
		
		
	Ink coverage dialog
This commit is contained in:
		| @@ -1,4 +1,4 @@ | ||||
| //    Copyright (C) 2019-2020 Jakub Melka | ||||
| //    Copyright (C) 2019-2021 Jakub Melka | ||||
| // | ||||
| //    This file is part of Pdf4Qt. | ||||
| // | ||||
| @@ -54,7 +54,7 @@ void PDFProgress::step() | ||||
|  | ||||
|     if (emitSignal) | ||||
|     { | ||||
|         progressStep(newPercentage); | ||||
|         emit progressStep(newPercentage); | ||||
|     } | ||||
| } | ||||
|  | ||||
|   | ||||
| @@ -3853,12 +3853,14 @@ PDFInkCoverageCalculator::PDFInkCoverageCalculator(const PDFDocument* document, | ||||
|                                                    const PDFCMSManager* cmsManager, | ||||
|                                                    const PDFOptionalContentActivity* optionalContentActivity, | ||||
|                                                    const PDFInkMapper* inkMapper, | ||||
|                                                    PDFProgress* progress, | ||||
|                                                    PDFTransparencyRendererSettings settings) : | ||||
|     m_document(document), | ||||
|     m_fontCache(fontCache), | ||||
|     m_cmsManager(cmsManager), | ||||
|     m_optionalContentActivity(optionalContentActivity), | ||||
|     m_inkMapper(inkMapper), | ||||
|     m_progress(progress), | ||||
|     m_settings(settings) | ||||
| { | ||||
|     Q_ASSERT(m_document); | ||||
| @@ -3876,6 +3878,11 @@ void PDFInkCoverageCalculator::perform(QSize size, const std::vector<PDFInteger> | ||||
|         return; | ||||
|     } | ||||
|  | ||||
|     if (m_progress) | ||||
|     { | ||||
|         m_progress->start(pages.size(), ProgressStartupInfo()); | ||||
|     } | ||||
|  | ||||
|     auto calculatePageCoverage = [this, size](PDFInteger pageIndex) | ||||
|     { | ||||
|         if (pageIndex >= PDFInteger(m_document->getCatalog()->getPageCount())) | ||||
| @@ -3971,11 +3978,27 @@ void PDFInkCoverageCalculator::perform(QSize size, const std::vector<PDFInteger> | ||||
|             results.emplace_back(qMove(info)); | ||||
|         } | ||||
|  | ||||
|         if (m_progress) | ||||
|         { | ||||
|             m_progress->step(); | ||||
|         } | ||||
|  | ||||
|         QMutexLocker lock(&m_mutex); | ||||
|         m_inkCoverageResults[pageIndex] = qMove(results); | ||||
|     }; | ||||
|  | ||||
|     PDFExecutionPolicy::execute(PDFExecutionPolicy::Scope::Page, pages.begin(), pages.end(), calculatePageCoverage); | ||||
|  | ||||
|     if (m_progress) | ||||
|     { | ||||
|         m_progress->finish(); | ||||
|     } | ||||
| } | ||||
|  | ||||
| void PDFInkCoverageCalculator::clear() | ||||
| { | ||||
|     QMutexLocker lock(&m_mutex); | ||||
|     m_inkCoverageResults.clear(); | ||||
| } | ||||
|  | ||||
| const std::vector<PDFInkCoverageCalculator::InkCoverageChannelInfo>* PDFInkCoverageCalculator::getInkCoverage(PDFInteger pageIndex) const | ||||
| @@ -3990,4 +4013,27 @@ const std::vector<PDFInkCoverageCalculator::InkCoverageChannelInfo>* PDFInkCover | ||||
|     return &dummy; | ||||
| } | ||||
|  | ||||
| const PDFInkCoverageCalculator::InkCoverageChannelInfo* PDFInkCoverageCalculator::findCoverageInfoByName(const std::vector<PDFInkCoverageCalculator::InkCoverageChannelInfo>& infos, | ||||
|                                                                                                          const QByteArray& name) | ||||
| { | ||||
|     auto it = std::find_if(infos.cbegin(), infos.cend(), [&name](const auto& info) { return info.name == name; }); | ||||
|     if (it != infos.cend()) | ||||
|     { | ||||
|         return &*it; | ||||
|     } | ||||
|  | ||||
|     return nullptr; | ||||
| } | ||||
|  | ||||
| PDFInkCoverageCalculator::InkCoverageChannelInfo* PDFInkCoverageCalculator::findCoverageInfoByName(std::vector<PDFInkCoverageCalculator::InkCoverageChannelInfo>& infos, const QByteArray& name) | ||||
| { | ||||
|     auto it = std::find_if(infos.begin(), infos.end(), [&name](const auto& info) { return info.name == name; }); | ||||
|     if (it != infos.cend()) | ||||
|     { | ||||
|         return &*it; | ||||
|     } | ||||
|  | ||||
|     return nullptr; | ||||
| } | ||||
|  | ||||
| }   // namespace pdf | ||||
|   | ||||
| @@ -23,6 +23,7 @@ | ||||
| #include "pdfpagecontentprocessor.h" | ||||
| #include "pdfconstants.h" | ||||
| #include "pdfutils.h" | ||||
| #include "pdfprogress.h" | ||||
|  | ||||
| #include <QImage> | ||||
|  | ||||
| @@ -934,6 +935,7 @@ public: | ||||
|                              const PDFCMSManager* cmsManager, | ||||
|                              const PDFOptionalContentActivity* optionalContentActivity, | ||||
|                              const PDFInkMapper* inkMapper, | ||||
|                              PDFProgress* progress, | ||||
|                              PDFTransparencyRendererSettings settings); | ||||
|  | ||||
|     struct InkCoverageChannelInfo | ||||
| @@ -953,17 +955,35 @@ public: | ||||
|     /// \param pages Page indices | ||||
|     void perform(QSize size, const std::vector<PDFInteger>& pages); | ||||
|  | ||||
|     /// Clear all calculated ink coverage results | ||||
|     void clear(); | ||||
|  | ||||
|     /// Clears calculated ink coverage for all pages. If ink coverage is not | ||||
|     /// calculated for given page index, empty vector is returned. | ||||
|     /// \param pageIndex Page index | ||||
|     const std::vector<InkCoverageChannelInfo>* getInkCoverage(PDFInteger pageIndex) const; | ||||
|  | ||||
|     /// Find coverage info in vector by colorant name. If coverage info with a given colorant | ||||
|     /// name is not found, then nullptr is returned. | ||||
|     /// \param infos Vector of coverage info | ||||
|     /// \param name Colornant name | ||||
|     /// \returns Info for a given colorant name, or nullptr, if it is not found | ||||
|     static const InkCoverageChannelInfo* findCoverageInfoByName(const std::vector<InkCoverageChannelInfo>& infos, const QByteArray& name); | ||||
|  | ||||
|     /// Find coverage info in vector by colorant name. If coverage info with a given colorant | ||||
|     /// name is not found, then nullptr is returned. | ||||
|     /// \param infos Vector of coverage info | ||||
|     /// \param name Colornant name | ||||
|     /// \returns Info for a given colorant name, or nullptr, if it is not found | ||||
|     static InkCoverageChannelInfo* findCoverageInfoByName(std::vector<InkCoverageChannelInfo>& infos, const QByteArray& name); | ||||
|  | ||||
| private: | ||||
|     const PDFDocument* m_document; | ||||
|     const PDFFontCache* m_fontCache; | ||||
|     const PDFCMSManager* m_cmsManager; | ||||
|     const PDFOptionalContentActivity* m_optionalContentActivity; | ||||
|     const PDFInkMapper* m_inkMapper; | ||||
|     PDFProgress* m_progress; | ||||
|     PDFTransparencyRendererSettings m_settings; | ||||
|  | ||||
|     QMutex m_mutex; | ||||
|   | ||||
| @@ -3,5 +3,5 @@ | ||||
|     "Author" : "Jakub Melka", | ||||
|     "Version" : "1.0.0", | ||||
|     "License" : "LGPL v3", | ||||
|     "Description" : "View prepress output preview (overprint, spot colors, advanced transparency)." | ||||
|     "Description" : "View prepress output preview (overprint, spot colors, advanced transparency). Measure ink coverage for process and spot colors for all pages." | ||||
| } | ||||
|   | ||||
| @@ -33,11 +33,13 @@ DESTDIR = $$OUT_PWD/../../pdfplugins | ||||
| CONFIG += c++11 | ||||
|  | ||||
| SOURCES += \ | ||||
|     inkcoveragedialog.cpp \ | ||||
|     outputpreviewdialog.cpp \ | ||||
|     outputpreviewplugin.cpp \ | ||||
|     outputpreviewwidget.cpp | ||||
|  | ||||
| HEADERS += \ | ||||
|     inkcoveragedialog.h \ | ||||
|     outputpreviewdialog.h \ | ||||
|     outputpreviewplugin.h \ | ||||
|     outputpreviewwidget.h | ||||
| @@ -51,4 +53,5 @@ RESOURCES += \ | ||||
|     icons.qrc | ||||
|  | ||||
| FORMS += \ | ||||
|     inkcoveragedialog.ui \ | ||||
|     outputpreviewdialog.ui | ||||
|   | ||||
| @@ -1,5 +1,6 @@ | ||||
| <RCC> | ||||
|     <qresource prefix="/pdfplugins/outputpreview"> | ||||
|         <file>preview.svg</file> | ||||
|         <file>ink-coverage.svg</file> | ||||
|     </qresource> | ||||
| </RCC> | ||||
|   | ||||
							
								
								
									
										148
									
								
								Pdf4QtViewerPlugins/OutputPreviewPlugin/ink-coverage.svg
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										148
									
								
								Pdf4QtViewerPlugins/OutputPreviewPlugin/ink-coverage.svg
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,148 @@ | ||||
| <?xml version="1.0" encoding="UTF-8" standalone="no"?> | ||||
| <!-- Created with Inkscape (http://www.inkscape.org/) --> | ||||
|  | ||||
| <svg | ||||
|    xmlns:dc="http://purl.org/dc/elements/1.1/" | ||||
|    xmlns:cc="http://creativecommons.org/ns#" | ||||
|    xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" | ||||
|    xmlns:svg="http://www.w3.org/2000/svg" | ||||
|    xmlns="http://www.w3.org/2000/svg" | ||||
|    xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" | ||||
|    xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" | ||||
|    width="30mm" | ||||
|    height="30mm" | ||||
|    viewBox="0 0 30 30" | ||||
|    version="1.1" | ||||
|    id="svg8" | ||||
|    inkscape:version="0.92.4 (5da689c313, 2019-01-14)" | ||||
|    sodipodi:docname="ink-coverage.svg" | ||||
|    enable-background="new"> | ||||
|   <defs | ||||
|      id="defs2"> | ||||
|     <inkscape:path-effect | ||||
|        effect="spiro" | ||||
|        id="path-effect831" | ||||
|        is_visible="true" /> | ||||
|   </defs> | ||||
|   <sodipodi:namedview | ||||
|      id="base" | ||||
|      pagecolor="#ffffff" | ||||
|      bordercolor="#666666" | ||||
|      borderopacity="1.0" | ||||
|      inkscape:pageopacity="0.0" | ||||
|      inkscape:pageshadow="2" | ||||
|      inkscape:zoom="3.959798" | ||||
|      inkscape:cx="353.90161" | ||||
|      inkscape:cy="22.898892" | ||||
|      inkscape:document-units="mm" | ||||
|      inkscape:current-layer="layer1" | ||||
|      showgrid="false" | ||||
|      inkscape:window-width="3840" | ||||
|      inkscape:window-height="2035" | ||||
|      inkscape:window-x="-13" | ||||
|      inkscape:window-y="-13" | ||||
|      inkscape:window-maximized="1" /> | ||||
|   <metadata | ||||
|      id="metadata5"> | ||||
|     <rdf:RDF> | ||||
|       <cc:Work | ||||
|          rdf:about=""> | ||||
|         <dc:format>image/svg+xml</dc:format> | ||||
|         <dc:type | ||||
|            rdf:resource="http://purl.org/dc/dcmitype/StillImage" /> | ||||
|         <dc:title></dc:title> | ||||
|         <cc:license | ||||
|            rdf:resource="http://creativecommons.org/licenses/by-sa/4.0/" /> | ||||
|         <dc:creator> | ||||
|           <cc:Agent> | ||||
|             <dc:title>Jakub Melka</dc:title> | ||||
|           </cc:Agent> | ||||
|         </dc:creator> | ||||
|       </cc:Work> | ||||
|       <cc:License | ||||
|          rdf:about="http://creativecommons.org/licenses/by-sa/4.0/"> | ||||
|         <cc:permits | ||||
|            rdf:resource="http://creativecommons.org/ns#Reproduction" /> | ||||
|         <cc:permits | ||||
|            rdf:resource="http://creativecommons.org/ns#Distribution" /> | ||||
|         <cc:requires | ||||
|            rdf:resource="http://creativecommons.org/ns#Notice" /> | ||||
|         <cc:requires | ||||
|            rdf:resource="http://creativecommons.org/ns#Attribution" /> | ||||
|         <cc:permits | ||||
|            rdf:resource="http://creativecommons.org/ns#DerivativeWorks" /> | ||||
|         <cc:requires | ||||
|            rdf:resource="http://creativecommons.org/ns#ShareAlike" /> | ||||
|       </cc:License> | ||||
|     </rdf:RDF> | ||||
|   </metadata> | ||||
|   <g | ||||
|      inkscape:label="Vrstva 1" | ||||
|      inkscape:groupmode="layer" | ||||
|      id="layer1" | ||||
|      transform="translate(0,-267)"> | ||||
|     <rect | ||||
|        style="opacity:1;fill:none;fill-opacity:1;stroke:#000000;stroke-width:1.06046581;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke fill markers" | ||||
|        id="rect4534" | ||||
|        width="23.724977" | ||||
|        height="11.795169" | ||||
|        x="3.0676022" | ||||
|        y="281.75931" | ||||
|        ry="0.0470865" /> | ||||
|     <path | ||||
|        sodipodi:type="spiral" | ||||
|        style="fill:none;fill-rule:evenodd;stroke:#000000;stroke-width:0.26458332" | ||||
|        id="path4536" | ||||
|        sodipodi:cx="6.8319197" | ||||
|        sodipodi:cy="287.80103" | ||||
|        sodipodi:expansion="1" | ||||
|        sodipodi:revolution="3" | ||||
|        sodipodi:radius="2.2576218" | ||||
|        sodipodi:argument="-18.617268" | ||||
|        sodipodi:t0="0" | ||||
|        d="m 6.8319197,287.80103 c 0.1101534,0.026 0.01922,0.16134 -0.04331,0.18308 -0.1694529,0.0589 -0.3112585,-0.11718 -0.3228548,-0.2697 -0.020743,-0.27284 0.2420036,-0.46852 0.4960934,-0.46263 0.372887,0.009 0.6288465,0.36795 0.6024,0.72248 -0.035249,0.47254 -0.494221,0.79039 -0.9488772,0.74218 -0.5721383,-0.0607 -0.9525297,-0.62063 -0.8819452,-1.17527 0.085487,-0.67175 0.7471009,-1.11503 1.401661,-1.02172 0.7713764,0.10996 1.2777336,0.87362 1.1614904,1.62805 -0.1342073,0.87102 -1.0001713,1.44059 -1.8544448,1.30127 -0.9706798,-0.15832 -1.6035477,-1.12675 -1.4410356,-2.08084 0.1823141,-1.07035 1.2533288,-1.76658 2.3072286,-1.58081 1.1700285,0.20624 1.9296674,1.37993 1.7205808,2.53362" | ||||
|        transform="matrix(1.5963587,0,0,1.64111,-3.4226782,-184.59737)" /> | ||||
|     <path | ||||
|        sodipodi:type="spiral" | ||||
|        style="fill:none;fill-rule:evenodd;stroke:#000000;stroke-width:0.26458332" | ||||
|        id="path4536-3" | ||||
|        sodipodi:cx="6.8319197" | ||||
|        sodipodi:cy="287.80103" | ||||
|        sodipodi:expansion="1" | ||||
|        sodipodi:revolution="3" | ||||
|        sodipodi:radius="2.2576218" | ||||
|        sodipodi:argument="-18.617268" | ||||
|        sodipodi:t0="0" | ||||
|        d="m 6.8319197,287.80103 c 0.1101534,0.026 0.01922,0.16134 -0.04331,0.18308 -0.1694529,0.0589 -0.3112585,-0.11718 -0.3228548,-0.2697 -0.020743,-0.27284 0.2420036,-0.46852 0.4960934,-0.46263 0.372887,0.009 0.6288465,0.36795 0.6024,0.72248 -0.035249,0.47254 -0.494221,0.79039 -0.9488772,0.74218 -0.5721383,-0.0607 -0.9525297,-0.62063 -0.8819452,-1.17527 0.085487,-0.67175 0.7471009,-1.11503 1.401661,-1.02172 0.7713764,0.10996 1.2777336,0.87362 1.1614904,1.62805 -0.1342073,0.87102 -1.0001713,1.44059 -1.8544448,1.30127 -0.9706798,-0.15832 -1.6035477,-1.12675 -1.4410356,-2.08084 0.1823141,-1.07035 1.2533288,-1.76658 2.3072286,-1.58081 1.1700285,0.20624 1.9296674,1.37993 1.7205808,2.53362" | ||||
|        transform="matrix(1.5963587,0,0,1.64111,4.1022508,-184.64367)" /> | ||||
|     <path | ||||
|        sodipodi:type="spiral" | ||||
|        style="fill:none;fill-rule:evenodd;stroke:#000000;stroke-width:0.26458332" | ||||
|        id="path4536-6" | ||||
|        sodipodi:cx="6.8319197" | ||||
|        sodipodi:cy="287.80103" | ||||
|        sodipodi:expansion="1" | ||||
|        sodipodi:revolution="3" | ||||
|        sodipodi:radius="2.2576218" | ||||
|        sodipodi:argument="-18.617268" | ||||
|        sodipodi:t0="0" | ||||
|        d="m 6.8319197,287.80103 c 0.1101534,0.026 0.01922,0.16134 -0.04331,0.18308 -0.1694529,0.0589 -0.3112585,-0.11718 -0.3228548,-0.2697 -0.020743,-0.27284 0.2420036,-0.46852 0.4960934,-0.46263 0.372887,0.009 0.6288465,0.36795 0.6024,0.72248 -0.035249,0.47254 -0.494221,0.79039 -0.9488772,0.74218 -0.5721383,-0.0607 -0.9525297,-0.62063 -0.8819452,-1.17527 0.085487,-0.67175 0.7471009,-1.11503 1.401661,-1.02172 0.7713764,0.10996 1.2777336,0.87362 1.1614904,1.62805 -0.1342073,0.87102 -1.0001713,1.44059 -1.8544448,1.30127 -0.9706798,-0.15832 -1.6035477,-1.12675 -1.4410356,-2.08084 0.1823141,-1.07035 1.2533288,-1.76658 2.3072286,-1.58081 1.1700285,0.20624 1.9296674,1.37993 1.7205808,2.53362" | ||||
|        transform="matrix(1.5963587,0,0,1.64111,11.378292,-184.69091)" /> | ||||
|     <rect | ||||
|        style="opacity:1;fill:none;fill-opacity:1;stroke:#000000;stroke-width:1;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke fill markers" | ||||
|        id="rect4559" | ||||
|        width="10.924642" | ||||
|        height="6.8821898" | ||||
|        x="9.9223804" | ||||
|        y="274.85004" | ||||
|        ry="0.047246911" /> | ||||
|     <rect | ||||
|        style="opacity:1;fill:#000000;fill-opacity:1;stroke:#000000;stroke-width:1;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke fill markers" | ||||
|        id="rect4561" | ||||
|        width="15.167545" | ||||
|        height="3.3742776" | ||||
|        x="8.0849028" | ||||
|        y="271.40894" | ||||
|        ry="0.047246911" /> | ||||
|   </g> | ||||
| </svg> | ||||
| After Width: | Height: | Size: 7.0 KiB | 
							
								
								
									
										381
									
								
								Pdf4QtViewerPlugins/OutputPreviewPlugin/inkcoveragedialog.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										381
									
								
								Pdf4QtViewerPlugins/OutputPreviewPlugin/inkcoveragedialog.cpp
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,381 @@ | ||||
| //    Copyright (C) 2021 Jakub Melka | ||||
| // | ||||
| //    This file is part of Pdf4Qt. | ||||
| // | ||||
| //    Pdf4Qt is free software: you can redistribute it and/or modify | ||||
| //    it under the terms of the GNU Lesser General Public License as published by | ||||
| //    the Free Software Foundation, either version 3 of the License, or | ||||
| //    (at your option) any later version. | ||||
| // | ||||
| //    Pdf4Qt 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 Lesser General Public License for more details. | ||||
| // | ||||
| //    You should have received a copy of the GNU Lesser General Public License | ||||
| //    along with Pdf4Qt.  If not, see <https://www.gnu.org/licenses/>. | ||||
|  | ||||
| #include "inkcoveragedialog.h" | ||||
| #include "ui_inkcoveragedialog.h" | ||||
|  | ||||
| #include "pdfdrawspacecontroller.h" | ||||
| #include "pdfwidgetutils.h" | ||||
|  | ||||
| #include <QCloseEvent> | ||||
| #include <QtConcurrent/QtConcurrent> | ||||
|  | ||||
| namespace pdfplugin | ||||
| { | ||||
|  | ||||
| InkCoverageDialog::InkCoverageDialog(const pdf::PDFDocument* document, pdf::PDFWidget* widget, QWidget* parent) : | ||||
|     QDialog(parent, Qt::Dialog | Qt::WindowMaximizeButtonHint | Qt::WindowCloseButtonHint), | ||||
|     ui(new Ui::InkCoverageDialog), | ||||
|     m_inkMapper(widget->getCMSManager(), document), | ||||
|     m_document(document), | ||||
|     m_widget(widget), | ||||
|     m_model(nullptr), | ||||
|     m_futureWatcher(nullptr) | ||||
| { | ||||
|     ui->setupUi(this); | ||||
|  | ||||
|     m_inkMapper.createSpotColors(true); | ||||
|  | ||||
|     m_model = new InkCoverageStatisticsModel(this); | ||||
|     ui->coverageTableView->setModel(m_model); | ||||
|     ui->coverageTableView->horizontalHeader()->setSectionResizeMode(QHeaderView::Stretch); | ||||
|  | ||||
|     setMinimumSize(pdf::PDFWidgetUtils::scaleDPI(this, QSize(800, 600))); | ||||
|     updateInkCoverage(); | ||||
| } | ||||
|  | ||||
| InkCoverageDialog::~InkCoverageDialog() | ||||
| { | ||||
|     delete ui; | ||||
| } | ||||
|  | ||||
| void InkCoverageDialog::updateInkCoverage() | ||||
| { | ||||
|     Q_ASSERT(!m_future.isRunning()); | ||||
|     Q_ASSERT(!m_futureWatcher); | ||||
|  | ||||
|     auto calculateInkCoverage = [this]() -> InkCoverageResults | ||||
|     { | ||||
|         InkCoverageResults results; | ||||
|  | ||||
|         pdf::PDFTransparencyRendererSettings settings; | ||||
|  | ||||
|         // Jakub Melka: debug is very slow, use multithreading | ||||
| #ifdef QT_DEBUG | ||||
|         settings.flags.setFlag(pdf::PDFTransparencyRendererSettings::MultithreadedPathSampler, true); | ||||
| #endif | ||||
|  | ||||
|         settings.flags.setFlag(pdf::PDFTransparencyRendererSettings::ActiveColorMask, false); | ||||
|         settings.flags.setFlag(pdf::PDFTransparencyRendererSettings::SeparationSimulation, m_inkMapper.getActiveSpotColorCount() > 0); | ||||
|         settings.flags.setFlag(pdf::PDFTransparencyRendererSettings::SaveOriginalProcessImage, true); | ||||
|  | ||||
|         pdf::PDFInkCoverageCalculator calculator(m_document, | ||||
|                                                  m_widget->getDrawWidgetProxy()->getFontCache(), | ||||
|                                                  m_widget->getCMSManager(), | ||||
|                                                  m_widget->getDrawWidgetProxy()->getOptionalContentActivity(), | ||||
|                                                  &m_inkMapper, | ||||
|                                                  m_widget->getDrawWidgetProxy()->getProgress(), | ||||
|                                                  settings); | ||||
|  | ||||
|         std::vector<pdf::PDFInteger> pageIndices; | ||||
|         pageIndices.resize(m_document->getCatalog()->getPageCount(), 0); | ||||
|         std::iota(pageIndices.begin(), pageIndices.end(), 0); | ||||
|         calculator.perform(QSize(RESOLUTION, RESOLUTION), pageIndices); | ||||
|  | ||||
|         CoverageInfo coverageInfo; | ||||
|  | ||||
|         for (const pdf::PDFInteger pageIndex : pageIndices) | ||||
|         { | ||||
|             const std::vector<pdf::PDFInkCoverageCalculator::InkCoverageChannelInfo>* coverage = calculator.getInkCoverage(pageIndex); | ||||
|  | ||||
|             if (!coverage) | ||||
|             { | ||||
|                 // Jakub Melka: Something bad happened? | ||||
|                 continue; | ||||
|             } | ||||
|  | ||||
|             for (const auto& info : *coverage) | ||||
|             { | ||||
|                 if (!pdf::PDFInkCoverageCalculator::findCoverageInfoByName(coverageInfo,  info.name)) | ||||
|                 { | ||||
|                     coverageInfo.push_back(info); | ||||
|                     coverageInfo.back().coveredArea = 0.0; | ||||
|                     coverageInfo.back().ratio = 0.0; | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         CoverageInfo templateInfo = coverageInfo; | ||||
|         CoverageInfo sumInfo = coverageInfo; | ||||
|  | ||||
|         for (const pdf::PDFInteger pageIndex : pageIndices) | ||||
|         { | ||||
|             const std::vector<pdf::PDFInkCoverageCalculator::InkCoverageChannelInfo>* coverage = calculator.getInkCoverage(pageIndex); | ||||
|             results.pageInfo.push_back(templateInfo); | ||||
|  | ||||
|             if (!coverage) | ||||
|             { | ||||
|                 // Jakub Melka: Something bad happened? | ||||
|                 continue; | ||||
|             } | ||||
|  | ||||
|             CoverageInfo& currentInfo = results.pageInfo.back(); | ||||
|  | ||||
|             for (const auto& info : *coverage) | ||||
|             { | ||||
|                 pdf::PDFInkCoverageCalculator::InkCoverageChannelInfo* channelInfo = pdf::PDFInkCoverageCalculator::findCoverageInfoByName(currentInfo,  info.name); | ||||
|                 channelInfo->coveredArea = info.coveredArea; | ||||
|                 channelInfo->ratio = info.ratio; | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         results.sumInfo = qMove(sumInfo); | ||||
|  | ||||
|         return results; | ||||
|     }; | ||||
|  | ||||
|     m_future = QtConcurrent::run(calculateInkCoverage); | ||||
|     m_futureWatcher = new QFutureWatcher<InkCoverageResults>(); | ||||
|     connect(m_futureWatcher, &QFutureWatcher<InkCoverageResults>::finished, this, &InkCoverageDialog::onInkCoverageCalculated); | ||||
|     m_futureWatcher->setFuture(m_future); | ||||
| } | ||||
|  | ||||
| void InkCoverageDialog::closeEvent(QCloseEvent* event) | ||||
| { | ||||
|     if (!isInkCoverageCalculated()) | ||||
|     { | ||||
|         event->ignore(); | ||||
|         return; | ||||
|     } | ||||
|  | ||||
|     BaseClass::closeEvent(event); | ||||
| } | ||||
|  | ||||
| void InkCoverageDialog::accept() | ||||
| { | ||||
|     if (!isInkCoverageCalculated()) | ||||
|     { | ||||
|         return; | ||||
|     } | ||||
|  | ||||
|     BaseClass::accept(); | ||||
| } | ||||
|  | ||||
| void InkCoverageDialog::reject() | ||||
| { | ||||
|     if (!isInkCoverageCalculated()) | ||||
|     { | ||||
|         return; | ||||
|     } | ||||
|  | ||||
|     BaseClass::reject(); | ||||
| } | ||||
|  | ||||
| void InkCoverageDialog::onInkCoverageCalculated() | ||||
| { | ||||
|     Q_ASSERT(m_future.isFinished()); | ||||
|     InkCoverageResults results = m_future.result(); | ||||
|     m_model->setInkCoverageResults(qMove(results)); | ||||
| } | ||||
|  | ||||
| bool InkCoverageDialog::isInkCoverageCalculated() const | ||||
| { | ||||
|     return !(m_futureWatcher && m_futureWatcher->isRunning()); | ||||
| } | ||||
|  | ||||
| InkCoverageStatisticsModel::InkCoverageStatisticsModel(QObject* parent) : | ||||
|     BaseClass(parent) | ||||
| { | ||||
|  | ||||
| } | ||||
|  | ||||
| QModelIndex InkCoverageStatisticsModel::index(int row, int column, const QModelIndex& parent) const | ||||
| { | ||||
|     Q_UNUSED(parent); | ||||
|     return createIndex(row, column, nullptr); | ||||
| } | ||||
|  | ||||
| QModelIndex InkCoverageStatisticsModel::parent(const QModelIndex& child) const | ||||
| { | ||||
|     Q_UNUSED(child); | ||||
|  | ||||
|     return QModelIndex(); | ||||
| } | ||||
|  | ||||
| int InkCoverageStatisticsModel::rowCount(const QModelIndex& parent) const | ||||
| { | ||||
|     Q_UNUSED(parent); | ||||
|  | ||||
|     if (m_inkCoverageResults.pageInfo.empty()) | ||||
|     { | ||||
|         return 0; | ||||
|     } | ||||
|  | ||||
|     return int(m_inkCoverageResults.pageInfo.size() + 1); | ||||
| } | ||||
|  | ||||
| int InkCoverageStatisticsModel::columnCount(const QModelIndex& parent) const | ||||
| { | ||||
|     Q_UNUSED(parent); | ||||
|  | ||||
|     return LastStandardColumn + getChannelCount() * LastChannelColumn; | ||||
| } | ||||
|  | ||||
| QVariant InkCoverageStatisticsModel::data(const QModelIndex& index, int role) const | ||||
| { | ||||
|     if (!index.isValid()) | ||||
|     { | ||||
|         return QVariant(); | ||||
|     } | ||||
|  | ||||
|     switch (role) | ||||
|     { | ||||
|         case Qt::DisplayRole: | ||||
|         { | ||||
|             const int row = index.row(); | ||||
|             QLocale locale; | ||||
|  | ||||
|             if (index.column() == StandardColumnPageIndex) | ||||
|             { | ||||
|                 return locale.toString(row + 1); | ||||
|             } | ||||
|  | ||||
|             Q_ASSERT(index.column() >= LastStandardColumn); | ||||
|  | ||||
|             const CoverageInfo* info = nullptr; | ||||
|             if (row < m_inkCoverageResults.pageInfo.size()) | ||||
|             { | ||||
|                 info = &m_inkCoverageResults.pageInfo[row]; | ||||
|             } | ||||
|             else | ||||
|             { | ||||
|                 info = &m_inkCoverageResults.sumInfo; | ||||
|             } | ||||
|  | ||||
|             const int channelIndex = getChannelIndex(index.column()); | ||||
|             EChannelColumn channelColumn = getChannelColumn(index.column()); | ||||
|             ChannelCoverageInfo channelInfo = info->at(channelIndex); | ||||
|  | ||||
|             switch (channelColumn) | ||||
|             { | ||||
|                 case pdfplugin::InkCoverageStatisticsModel::ChannelColumnColorant: | ||||
|                     return channelInfo.coveredArea > 0.0 ? channelInfo.textName : QString(); | ||||
|                 case pdfplugin::InkCoverageStatisticsModel::ChannelColumnCoverageArea: | ||||
|                     return locale.toString(channelInfo.coveredArea, 'f', 2); | ||||
|                 case pdfplugin::InkCoverageStatisticsModel::ChannelColumnCoverageRatio: | ||||
|                     return locale.toString(channelInfo.ratio * 100.0, 'f', 0); | ||||
|  | ||||
|                 default: | ||||
|                     Q_ASSERT(false); | ||||
|                     break; | ||||
|             } | ||||
|  | ||||
|             break; | ||||
|         } | ||||
|  | ||||
|         case Qt::TextAlignmentRole: | ||||
|         { | ||||
|             if (index.column() == StandardColumnPageIndex) | ||||
|             { | ||||
|                 return int(Qt::AlignCenter); | ||||
|             } | ||||
|  | ||||
|             Q_ASSERT(index.column() >= LastStandardColumn); | ||||
|  | ||||
|             EChannelColumn channelColumn = getChannelColumn(index.column()); | ||||
|             switch (channelColumn) | ||||
|             { | ||||
|                 case pdfplugin::InkCoverageStatisticsModel::ChannelColumnColorant: | ||||
|                     return int(Qt::AlignLeft | Qt::AlignVCenter); | ||||
|  | ||||
|                 case pdfplugin::InkCoverageStatisticsModel::ChannelColumnCoverageArea: | ||||
|                 case pdfplugin::InkCoverageStatisticsModel::ChannelColumnCoverageRatio: | ||||
|                     return int(Qt::AlignRight | Qt::AlignVCenter); | ||||
|  | ||||
|                 default: | ||||
|                     Q_ASSERT(false); | ||||
|                     break; | ||||
|             } | ||||
|         } | ||||
|  | ||||
|         default: | ||||
|             break; | ||||
|     } | ||||
|  | ||||
|     return QVariant(); | ||||
| } | ||||
|  | ||||
| QVariant InkCoverageStatisticsModel::headerData(int section, Qt::Orientation orientation, int role) const | ||||
| { | ||||
|     if (role != Qt::DisplayRole || orientation != Qt::Horizontal) | ||||
|     { | ||||
|         return QVariant(); | ||||
|     } | ||||
|  | ||||
|     if (section < LastStandardColumn) | ||||
|     { | ||||
|         Q_ASSERT(section == StandardColumnPageIndex); | ||||
|         return tr("Page Index"); | ||||
|     } | ||||
|  | ||||
|     const EChannelColumn channelColumn = getChannelColumn(section); | ||||
|  | ||||
|     switch (channelColumn) | ||||
|     { | ||||
|         case ChannelColumnColorant: | ||||
|         { | ||||
|             const int channelIndex = getChannelIndex(section); | ||||
|             return m_inkCoverageResults.sumInfo[channelIndex].textName; | ||||
|         } | ||||
|  | ||||
|         case ChannelColumnCoverageArea: | ||||
|             return tr("[ mm² ]"); | ||||
|  | ||||
|         case ChannelColumnCoverageRatio: | ||||
|             return tr("[ % ]"); | ||||
|  | ||||
|         case LastChannelColumn: | ||||
|             Q_ASSERT(false); | ||||
|             break; | ||||
|  | ||||
|         default: | ||||
|             Q_ASSERT(false); | ||||
|             break; | ||||
|     } | ||||
|  | ||||
|     return QVariant(); | ||||
| } | ||||
|  | ||||
| void InkCoverageStatisticsModel::setInkCoverageResults(InkCoverageResults inkCoverageResults) | ||||
| { | ||||
|     beginResetModel(); | ||||
|     m_inkCoverageResults = qMove(inkCoverageResults); | ||||
|     endResetModel(); | ||||
| } | ||||
|  | ||||
| int InkCoverageStatisticsModel::getChannelCount() const | ||||
| { | ||||
|     return int(m_inkCoverageResults.sumInfo.size()); | ||||
| } | ||||
|  | ||||
| InkCoverageStatisticsModel::EChannelColumn InkCoverageStatisticsModel::getChannelColumn(int index) const | ||||
| { | ||||
|     Q_ASSERT(index >= LastStandardColumn); | ||||
|  | ||||
|     index -= LastStandardColumn; | ||||
|     return static_cast<EChannelColumn>(index % LastChannelColumn); | ||||
| } | ||||
|  | ||||
| int InkCoverageStatisticsModel::getChannelIndex(int index) const | ||||
| { | ||||
|     Q_ASSERT(index >= LastStandardColumn); | ||||
|  | ||||
|     index -= LastStandardColumn; | ||||
|     return index / LastChannelColumn; | ||||
| } | ||||
|  | ||||
| }   // pdfplugin | ||||
							
								
								
									
										123
									
								
								Pdf4QtViewerPlugins/OutputPreviewPlugin/inkcoveragedialog.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										123
									
								
								Pdf4QtViewerPlugins/OutputPreviewPlugin/inkcoveragedialog.h
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,123 @@ | ||||
| //    Copyright (C) 2021 Jakub Melka | ||||
| // | ||||
| //    This file is part of Pdf4Qt. | ||||
| // | ||||
| //    Pdf4Qt is free software: you can redistribute it and/or modify | ||||
| //    it under the terms of the GNU Lesser General Public License as published by | ||||
| //    the Free Software Foundation, either version 3 of the License, or | ||||
| //    (at your option) any later version. | ||||
| // | ||||
| //    Pdf4Qt 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 Lesser General Public License for more details. | ||||
| // | ||||
| //    You should have received a copy of the GNU Lesser General Public License | ||||
| //    along with Pdf4Qt.  If not, see <https://www.gnu.org/licenses/>. | ||||
|  | ||||
| #ifndef INKCOVERAGEDIALOG_H | ||||
| #define INKCOVERAGEDIALOG_H | ||||
|  | ||||
| #include "pdfdocument.h" | ||||
| #include "pdfdrawwidget.h" | ||||
| #include "pdftransparencyrenderer.h" | ||||
|  | ||||
| #include <QDialog> | ||||
| #include <QAbstractItemModel> | ||||
|  | ||||
| namespace Ui | ||||
| { | ||||
| class InkCoverageDialog; | ||||
| } | ||||
|  | ||||
| namespace pdfplugin | ||||
| { | ||||
| class InkCoverageStatisticsModel; | ||||
|  | ||||
| using ChannelCoverageInfo = pdf::PDFInkCoverageCalculator::InkCoverageChannelInfo; | ||||
| using CoverageInfo = std::vector<ChannelCoverageInfo>; | ||||
|  | ||||
| struct InkCoverageResults | ||||
| { | ||||
|     std::vector<CoverageInfo> pageInfo; | ||||
|     CoverageInfo sumInfo; | ||||
| }; | ||||
|  | ||||
| class InkCoverageDialog : public QDialog | ||||
| { | ||||
|     Q_OBJECT | ||||
|  | ||||
| private: | ||||
|     using BaseClass = QDialog; | ||||
|  | ||||
| public: | ||||
|     explicit InkCoverageDialog(const pdf::PDFDocument* document, pdf::PDFWidget* widget, QWidget* parent); | ||||
|     virtual ~InkCoverageDialog() override; | ||||
|  | ||||
|     void updateInkCoverage(); | ||||
|  | ||||
|     virtual void closeEvent(QCloseEvent* event) override; | ||||
|  | ||||
|     virtual void accept() override; | ||||
|     virtual void reject() override; | ||||
|  | ||||
| private: | ||||
|     Ui::InkCoverageDialog* ui; | ||||
|  | ||||
|     static constexpr int RESOLUTION = 1920; | ||||
|  | ||||
|     void onInkCoverageCalculated(); | ||||
|     bool isInkCoverageCalculated() const; | ||||
|  | ||||
|     pdf::PDFInkMapper m_inkMapper; | ||||
|     const pdf::PDFDocument* m_document; | ||||
|     pdf::PDFWidget* m_widget; | ||||
|     InkCoverageStatisticsModel* m_model; | ||||
|  | ||||
|     QFuture<InkCoverageResults> m_future; | ||||
|     QFutureWatcher<InkCoverageResults>* m_futureWatcher; | ||||
| }; | ||||
|  | ||||
| class InkCoverageStatisticsModel : public QAbstractItemModel | ||||
| { | ||||
|     Q_OBJECT | ||||
|  | ||||
| private: | ||||
|     using BaseClass = QAbstractItemModel; | ||||
|  | ||||
| public: | ||||
|     explicit InkCoverageStatisticsModel(QObject* parent); | ||||
|  | ||||
|     enum EStandardColumn | ||||
|     { | ||||
|         StandardColumnPageIndex, | ||||
|         LastStandardColumn | ||||
|     }; | ||||
|  | ||||
|     enum EChannelColumn | ||||
|     { | ||||
|         ChannelColumnColorant, | ||||
|         ChannelColumnCoverageArea, | ||||
|         ChannelColumnCoverageRatio, | ||||
|         LastChannelColumn | ||||
|     }; | ||||
|  | ||||
|     virtual QModelIndex index(int row, int column, const QModelIndex& parent) const override; | ||||
|     virtual QModelIndex parent(const QModelIndex& child) const override; | ||||
|     virtual int rowCount(const QModelIndex& parent) const override; | ||||
|     virtual int columnCount(const QModelIndex& parent) const override; | ||||
|     virtual QVariant data(const QModelIndex& index, int role) const override; | ||||
|     virtual QVariant headerData(int section, Qt::Orientation orientation, int role) const override; | ||||
|  | ||||
|     void setInkCoverageResults(InkCoverageResults inkCoverageResults); | ||||
|     int getChannelCount() const; | ||||
|     EChannelColumn getChannelColumn(int index) const; | ||||
|     int getChannelIndex(int index) const; | ||||
|  | ||||
| private: | ||||
|     InkCoverageResults m_inkCoverageResults; | ||||
| }; | ||||
|  | ||||
| }   // namespace pdfplugin | ||||
|  | ||||
| #endif // INKCOVERAGEDIALOG_H | ||||
							
								
								
									
										88
									
								
								Pdf4QtViewerPlugins/OutputPreviewPlugin/inkcoveragedialog.ui
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										88
									
								
								Pdf4QtViewerPlugins/OutputPreviewPlugin/inkcoveragedialog.ui
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,88 @@ | ||||
| <?xml version="1.0" encoding="UTF-8"?> | ||||
| <ui version="4.0"> | ||||
|  <class>InkCoverageDialog</class> | ||||
|  <widget class="QDialog" name="InkCoverageDialog"> | ||||
|   <property name="geometry"> | ||||
|    <rect> | ||||
|     <x>0</x> | ||||
|     <y>0</y> | ||||
|     <width>715</width> | ||||
|     <height>551</height> | ||||
|    </rect> | ||||
|   </property> | ||||
|   <property name="windowTitle"> | ||||
|    <string>Ink Coverage Calculator</string> | ||||
|   </property> | ||||
|   <layout class="QVBoxLayout" name="verticalLayout"> | ||||
|    <item> | ||||
|     <widget class="QLabel" name="coverageLabel"> | ||||
|      <property name="text"> | ||||
|       <string>Ink Coverage</string> | ||||
|      </property> | ||||
|     </widget> | ||||
|    </item> | ||||
|    <item> | ||||
|     <widget class="Line" name="line"> | ||||
|      <property name="orientation"> | ||||
|       <enum>Qt::Horizontal</enum> | ||||
|      </property> | ||||
|     </widget> | ||||
|    </item> | ||||
|    <item> | ||||
|     <widget class="QTableView" name="coverageTableView"> | ||||
|      <attribute name="horizontalHeaderMinimumSectionSize"> | ||||
|       <number>40</number> | ||||
|      </attribute> | ||||
|      <attribute name="verticalHeaderVisible"> | ||||
|       <bool>false</bool> | ||||
|      </attribute> | ||||
|     </widget> | ||||
|    </item> | ||||
|    <item> | ||||
|     <widget class="QDialogButtonBox" name="buttonBox"> | ||||
|      <property name="orientation"> | ||||
|       <enum>Qt::Horizontal</enum> | ||||
|      </property> | ||||
|      <property name="standardButtons"> | ||||
|       <set>QDialogButtonBox::Close</set> | ||||
|      </property> | ||||
|     </widget> | ||||
|    </item> | ||||
|   </layout> | ||||
|  </widget> | ||||
|  <resources/> | ||||
|  <connections> | ||||
|   <connection> | ||||
|    <sender>buttonBox</sender> | ||||
|    <signal>accepted()</signal> | ||||
|    <receiver>InkCoverageDialog</receiver> | ||||
|    <slot>accept()</slot> | ||||
|    <hints> | ||||
|     <hint type="sourcelabel"> | ||||
|      <x>248</x> | ||||
|      <y>254</y> | ||||
|     </hint> | ||||
|     <hint type="destinationlabel"> | ||||
|      <x>157</x> | ||||
|      <y>274</y> | ||||
|     </hint> | ||||
|    </hints> | ||||
|   </connection> | ||||
|   <connection> | ||||
|    <sender>buttonBox</sender> | ||||
|    <signal>rejected()</signal> | ||||
|    <receiver>InkCoverageDialog</receiver> | ||||
|    <slot>reject()</slot> | ||||
|    <hints> | ||||
|     <hint type="sourcelabel"> | ||||
|      <x>316</x> | ||||
|      <y>260</y> | ||||
|     </hint> | ||||
|     <hint type="destinationlabel"> | ||||
|      <x>286</x> | ||||
|      <y>274</y> | ||||
|     </hint> | ||||
|    </hints> | ||||
|   </connection> | ||||
|  </connections> | ||||
| </ui> | ||||
| @@ -17,6 +17,7 @@ | ||||
|  | ||||
| #include "outputpreviewplugin.h" | ||||
| #include "outputpreviewdialog.h" | ||||
| #include "inkcoveragedialog.h" | ||||
| #include "pdfdrawwidget.h" | ||||
|  | ||||
| #include <QAction> | ||||
| @@ -26,7 +27,8 @@ namespace pdfplugin | ||||
|  | ||||
| OutputPreviewPlugin::OutputPreviewPlugin() : | ||||
|     pdf::PDFPlugin(nullptr), | ||||
|     m_outputPreviewAction(nullptr) | ||||
|     m_outputPreviewAction(nullptr), | ||||
|     m_inkCoverageAction(nullptr) | ||||
| { | ||||
|  | ||||
| } | ||||
| @@ -39,8 +41,11 @@ void OutputPreviewPlugin::setWidget(pdf::PDFWidget* widget) | ||||
|  | ||||
|     m_outputPreviewAction = new QAction(QIcon(":/pdfplugins/outputpreview/preview.svg"), tr("Output Preview"), this); | ||||
|     m_outputPreviewAction->setObjectName("actionOutputPreview_OutputPreview"); | ||||
|     m_inkCoverageAction = new QAction(QIcon(":/pdfplugins/outputpreview/ink-coverage.svg"), tr("Ink Coverage"), this); | ||||
|     m_inkCoverageAction->setObjectName("actionOutputPreview_InkCoverage"); | ||||
|  | ||||
|     connect(m_outputPreviewAction, &QAction::triggered, this, &OutputPreviewPlugin::onOutputPreviewTriggered); | ||||
|     connect(m_inkCoverageAction, &QAction::triggered, this, &OutputPreviewPlugin::onInkCoverageTriggered); | ||||
|  | ||||
|     updateActions(); | ||||
| } | ||||
| @@ -57,7 +62,7 @@ void OutputPreviewPlugin::setDocument(const pdf::PDFModifiedDocument& document) | ||||
|  | ||||
| std::vector<QAction*> OutputPreviewPlugin::getActions() const | ||||
| { | ||||
|     return { m_outputPreviewAction }; | ||||
|     return { m_outputPreviewAction, m_inkCoverageAction }; | ||||
| } | ||||
|  | ||||
| void OutputPreviewPlugin::onOutputPreviewTriggered() | ||||
| @@ -66,9 +71,16 @@ void OutputPreviewPlugin::onOutputPreviewTriggered() | ||||
|     dialog.exec(); | ||||
| } | ||||
|  | ||||
| void OutputPreviewPlugin::onInkCoverageTriggered() | ||||
| { | ||||
|     InkCoverageDialog dialog(m_document, m_widget, m_widget); | ||||
|     dialog.exec(); | ||||
| } | ||||
|  | ||||
| void OutputPreviewPlugin::updateActions() | ||||
| { | ||||
|     m_outputPreviewAction->setEnabled(m_widget && m_document); | ||||
|     m_inkCoverageAction->setEnabled(m_widget && m_document); | ||||
| } | ||||
|  | ||||
| } | ||||
|   | ||||
| @@ -42,9 +42,11 @@ public: | ||||
|  | ||||
| private: | ||||
|     void onOutputPreviewTriggered(); | ||||
|     void onInkCoverageTriggered(); | ||||
|     void updateActions(); | ||||
|  | ||||
|     QAction* m_outputPreviewAction; | ||||
|     QAction* m_inkCoverageAction; | ||||
| }; | ||||
|  | ||||
| }   // namespace pdfplugin | ||||
|   | ||||
		Reference in New Issue
	
	Block a user