From 6a06fa5ffddd47b14d37d7c8a1fd577d7413e1ba Mon Sep 17 00:00:00 2001 From: Anton Thomasson Date: Sun, 31 Jul 2022 19:48:14 +0200 Subject: [PATCH] Add support for client-side copies --- ppm2pwg | 2 +- qml/components/IntegerSetting.qml | 17 +++++++- qml/pages/PrinterPage.qml | 2 + qml/pages/utils.js | 10 +++++ src/ippprinter.cpp | 59 ++++++++++++++++++++++---- src/printerworker.cpp | 19 +++++++-- translations/harbour-seaprint-de.ts | 4 ++ translations/harbour-seaprint-es.ts | 4 ++ translations/harbour-seaprint-fr.ts | 4 ++ translations/harbour-seaprint-nl.ts | 4 ++ translations/harbour-seaprint-pl.ts | 4 ++ translations/harbour-seaprint-zh_CN.ts | 4 ++ translations/harbour-seaprint.ts | 4 ++ 13 files changed, 123 insertions(+), 14 deletions(-) diff --git a/ppm2pwg b/ppm2pwg index faf26f7..89cfaa0 160000 --- a/ppm2pwg +++ b/ppm2pwg @@ -1 +1 @@ -Subproject commit faf26f7042928ec2cbe4b77fafb7ffb50882a0c2 +Subproject commit 89cfaa0b424310f54355ee2415d3bee9ed786255 diff --git a/qml/components/IntegerSetting.qml b/qml/components/IntegerSetting.qml index 72006d9..8936df1 100644 --- a/qml/components/IntegerSetting.qml +++ b/qml/components/IntegerSetting.qml @@ -2,8 +2,21 @@ import QtQuick 2.6 import Sailfish.Silica 1.0 Setting { - property int low: valid ? parent.printer.attrs[name+"-supported"].value.low : 0 - property int high: valid ? parent.printer.attrs[name+"-supported"].value.high : 0 + property int minimum_high: 0 + property int low: _valid ? parent.printer.attrs[name+"-supported"].value.low : (minimum_high != 0) ? 1 : 0 + property int high: _valid ? ensure_minimum(parent.printer.attrs[name+"-supported"].value.high) : minimum_high + + function ensure_minimum(orig) + { + if(orig < minimum_high) + { + return minimum_high; + } + else + { + return orig; + } + } property bool suppressChange: false diff --git a/qml/pages/PrinterPage.qml b/qml/pages/PrinterPage.qml index fb32cbb..9cb5765 100644 --- a/qml/pages/PrinterPage.qml +++ b/qml/pages/PrinterPage.qml @@ -104,6 +104,8 @@ Page { tag: IppMsg.Integer name: "copies" prettyName: qsTr("Copies") + valid: _valid || Utils.supports_raster(printer) + minimum_high: 99 } ChoiceSetting { tag: IppMsg.Keyword diff --git a/qml/pages/utils.js b/qml/pages/utils.js index 01ab4f3..fc6d9a6 100644 --- a/qml/pages/utils.js +++ b/qml/pages/utils.js @@ -63,6 +63,16 @@ function supported_formats(printer, considerAdditionalFormats) return {pdf: pdf, postscript: postscript, plaintext: plaintext, office: office, images: images, mimetypes: mimetypes}; } +function supports_raster(printer) +{ + var formats = printer.attrs["document-format-supported"].value; + if(considerAdditionalFormats) + { + formats=formats+printer.additionalDocumentFormats; + } + return (has(formats, Mimer.Mimer.PWG) || has(formats, Mimer.Mimer.URF)); +} + function has(arrayish, what) { return arrayish.indexOf(what) != -1; diff --git a/src/ippprinter.cpp b/src/ippprinter.cpp index c96a27b..028b369 100644 --- a/src/ippprinter.cpp +++ b/src/ippprinter.cpp @@ -1,6 +1,7 @@ #include "ippprinter.h" #include "ippdiscovery.h" #include "mimer.h" +#include "convertchecker.h" #include "papersizes.h" #include "overrider.h" #include "settings.h" @@ -542,6 +543,27 @@ void IppPrinter::adjustRasterSettings(QString documentFormat, QJsonObject& jobAt } } + int copies_requested = getAttrOrDefault(jobAttrs, "copies").toInt(1); + QJsonArray varying_attributes = _attrs["document-format-varying-attributes"].toObject()["value"].toArray(); + bool supports_copies = _attrs.contains("copies-supported") + && _attrs["copies-supported"].toObject()["value"].toObject()["high"].toInt(1) != 1 + // assume raster formats causes the variation in supported copies + && !(varying_attributes.contains("copies-supported") || varying_attributes.contains("copies")); + + if(copies_requested > 1 && !supports_copies) + { + QString copyMode = getAttrOrDefault(jobAttrs, "multiple-document-handling").toString(); + qDebug() << "Doing local copies" << copyMode << copies_requested; + if(copyMode == "separate-documents-uncollated-copies") + { // Only do silly copies if explicitly requested + Params.pageCopies = copies_requested; + } + else + { + Params.documentCopies = copies_requested; + } + jobAttrs.remove("copies"); + } } void IppPrinter::print(QJsonObject jobAttrs, QString filename) @@ -679,18 +701,19 @@ void IppPrinter::print(QJsonObject jobAttrs, QString filename) Params.hwResW = PrinterResolutionRef.toObject()["x"].toInt(Params.hwResW); Params.hwResH = PrinterResolutionRef.toObject()["y"].toInt(Params.hwResH); - adjustRasterSettings(targetFormat, jobAttrs, Params); - - Params.quality = getAttrOrDefault(jobAttrs, "print-quality").toInt(); - - QString PrintColorMode = getAttrOrDefault(jobAttrs, "print-color-mode").toString(); - Params.colors = PrintColorMode.contains("color") ? 3 : PrintColorMode.contains("monochrome") ? 1 : Params.colors; + bool singlePageRange = false; if(jobAttrs.contains("page-ranges")) { QJsonObject PageRanges = getAttrOrDefault(jobAttrs, "page-ranges").toObject(); - Params.fromPage = PageRanges["low"].toInt(); - Params.toPage = PageRanges["high"].toInt(); + size_t fromPage = PageRanges["low"].toInt(); + size_t toPage = PageRanges["high"].toInt(); + if(fromPage != 0 || toPage != 0) + { + Params.pageRangeList = {{fromPage, toPage}}; + singlePageRange = toPage == fromPage; + } + // Effected locally, unless it is Postscript which we cant't render if(targetFormat != Mimer::Postscript) { @@ -699,6 +722,19 @@ void IppPrinter::print(QJsonObject jobAttrs, QString filename) } QString Sides = getAttrOrDefault(jobAttrs, "sides").toString(); + int copies_requested = getAttrOrDefault(jobAttrs, "copies").toInt(1); + + if((Params.format == PrintParameters::PWG || Params.format == PrintParameters::URF) && + copies_requested > 1 && + Sides != "one-sided" && + (Mimer::instance()->isImage(mimeType) || + (mimeType == Mimer::PDF && (singlePageRange || ConvertChecker::instance()->pdfPages(filename) == 1)))) + { + jobAttrs.insert("sides", QJsonObject {{"tag", IppMsg::Keyword}, {"value", "one-sided"}}); + qDebug() << "Optimizing one-page document to one-sided"; + } + + Sides = getAttrOrDefault(jobAttrs, "sides").toString(); if(Sides=="two-sided-long-edge") { @@ -710,6 +746,13 @@ void IppPrinter::print(QJsonObject jobAttrs, QString filename) Params.tumble = true; } + adjustRasterSettings(targetFormat, jobAttrs, Params); + + Params.quality = getAttrOrDefault(jobAttrs, "print-quality").toInt(); + + QString PrintColorMode = getAttrOrDefault(jobAttrs, "print-color-mode").toString(); + Params.colors = PrintColorMode.contains("color") ? 3 : PrintColorMode.contains("monochrome") ? 1 : Params.colors; + QJsonArray supportedOperations = _attrs["operations-supported"].toObject()["value"].toArray(); if(supportedOperations.contains(IppMsg::CreateJob) && supportedOperations.contains(IppMsg::SendDocument)) diff --git a/src/printerworker.cpp b/src/printerworker.cpp index c2f0a1e..8da8a24 100644 --- a/src/printerworker.cpp +++ b/src/printerworker.cpp @@ -453,6 +453,14 @@ void PrinterWorker::convertImage(QString filename, Bytestream header, PrintParam } else { + size_t total_pages = Params.documentCopies*Params.pageCopies; + + if(total_pages > 1 && Params.duplex) + { // Images are one page by definition - if we need to do client-side copies, they must be one-sided or we'd have to insert backsides + qDebug() << "Inconsistent duplex setting"; + throw ConvertFailedException(tr("Inconsistent duplex setting")); + } + QImage outImage = QImage(Params.getPaperSizeWInPixels(), Params.getPaperSizeHInPixels(), inImage.format()); outImage.fill(Qt::white); QPainter painter(&outImage); @@ -463,7 +471,7 @@ void PrinterWorker::convertImage(QString filename, Bytestream header, PrintParam QBuffer buf; buf.open(QIODevice::ReadWrite); - Bytestream outBts; + Bytestream fileHdr, outBts; if(inImage.allGray()) @@ -488,7 +496,7 @@ void PrinterWorker::convertImage(QString filename, Bytestream header, PrintParam buf.read((char*)(inBts.raw()), inBts.size()); - outBts << (Params.format == PrintParameters::URF ? make_urf_file_hdr(1) : make_pwg_file_hdr()); + fileHdr << (Params.format == PrintParameters::URF ? make_urf_file_hdr(1) : make_pwg_file_hdr()); bool verbose = QLoggingCategory::defaultCategory()->isDebugEnabled(); @@ -499,7 +507,12 @@ void PrinterWorker::convertImage(QString filename, Bytestream header, PrintParam emit busyMessage(tr("Printing")); OK(cr.write((char*)header.raw(), header.size())); - OK(cr.write((char*)(outBts.raw()), outBts.size())); + OK(cr.write((char*)fileHdr.raw(), fileHdr.size())); + for(size_t c = 0; c < total_pages; c++) + { + OK(cr.write((char*)(outBts.raw()), outBts.size())); + emit progress(c+1, total_pages); + } awaitResult(cr, "printRequestFinished"); } diff --git a/translations/harbour-seaprint-de.ts b/translations/harbour-seaprint-de.ts index cf5cee1..9c955a0 100644 --- a/translations/harbour-seaprint-de.ts +++ b/translations/harbour-seaprint-de.ts @@ -520,6 +520,10 @@ auf diesem Drucker Print error + + Inconsistent duplex setting + + RangeSetting diff --git a/translations/harbour-seaprint-es.ts b/translations/harbour-seaprint-es.ts index 372cbba..80dc5b4 100644 --- a/translations/harbour-seaprint-es.ts +++ b/translations/harbour-seaprint-es.ts @@ -519,6 +519,10 @@ Print error + + Inconsistent duplex setting + + RangeSetting diff --git a/translations/harbour-seaprint-fr.ts b/translations/harbour-seaprint-fr.ts index 6b3ba26..860420f 100644 --- a/translations/harbour-seaprint-fr.ts +++ b/translations/harbour-seaprint-fr.ts @@ -520,6 +520,10 @@ sur cette imprimante Print error + + Inconsistent duplex setting + + RangeSetting diff --git a/translations/harbour-seaprint-nl.ts b/translations/harbour-seaprint-nl.ts index aeb318b..74bd65c 100644 --- a/translations/harbour-seaprint-nl.ts +++ b/translations/harbour-seaprint-nl.ts @@ -519,6 +519,10 @@ Print error + + Inconsistent duplex setting + + RangeSetting diff --git a/translations/harbour-seaprint-pl.ts b/translations/harbour-seaprint-pl.ts index 74a16b7..ddfdce7 100644 --- a/translations/harbour-seaprint-pl.ts +++ b/translations/harbour-seaprint-pl.ts @@ -519,6 +519,10 @@ Print error Błąd drukowania + + Inconsistent duplex setting + + RangeSetting diff --git a/translations/harbour-seaprint-zh_CN.ts b/translations/harbour-seaprint-zh_CN.ts index dcabb94..dd1dbb3 100644 --- a/translations/harbour-seaprint-zh_CN.ts +++ b/translations/harbour-seaprint-zh_CN.ts @@ -519,6 +519,10 @@ Print error + + Inconsistent duplex setting + + RangeSetting diff --git a/translations/harbour-seaprint.ts b/translations/harbour-seaprint.ts index 18ba69a..ddd7d6a 100644 --- a/translations/harbour-seaprint.ts +++ b/translations/harbour-seaprint.ts @@ -519,6 +519,10 @@ Unknown target format + + Inconsistent duplex setting + + RangeSetting