2019-12-01 22:27:00 +03:00
|
|
|
#include "ippprinter.h"
|
2022-01-15 00:44:55 +03:00
|
|
|
#include "ippdiscovery.h"
|
2020-05-03 15:13:44 +03:00
|
|
|
#include "mimer.h"
|
2020-05-16 16:17:42 +03:00
|
|
|
#include "papersizes.h"
|
2021-05-25 20:37:49 +03:00
|
|
|
#include "overrider.h"
|
2021-06-19 18:47:11 +03:00
|
|
|
#include "settings.h"
|
2022-06-04 15:43:53 +03:00
|
|
|
#include <fstream>
|
2019-12-01 22:27:00 +03:00
|
|
|
|
2021-07-14 16:07:55 +03:00
|
|
|
Q_DECLARE_METATYPE(QMargins)
|
|
|
|
|
2022-01-15 00:49:38 +03:00
|
|
|
IppPrinter::IppPrinter() : _worker(this)
|
2019-12-01 22:27:00 +03:00
|
|
|
{
|
|
|
|
QObject::connect(this, &IppPrinter::urlChanged, this, &IppPrinter::onUrlChanged);
|
2020-05-01 14:49:17 +03:00
|
|
|
qRegisterMetaType<QTemporaryFile*>("QTemporaryFile*");
|
2020-05-01 16:02:29 +03:00
|
|
|
|
2022-01-15 00:49:38 +03:00
|
|
|
_worker.moveToThread(&_workerThread);
|
2020-05-01 16:02:29 +03:00
|
|
|
|
2022-01-15 00:49:38 +03:00
|
|
|
connect(this, &IppPrinter::doDoGetPrinterAttributes, &_worker, &PrinterWorker::getPrinterAttributes);
|
|
|
|
connect(this, &IppPrinter::doGetJobs, &_worker, &PrinterWorker::getJobs);
|
|
|
|
connect(this, &IppPrinter::doCancelJob, &_worker, &PrinterWorker::cancelJob);
|
2022-05-16 21:29:53 +03:00
|
|
|
connect(this, &IppPrinter::doIdentify, &_worker, &PrinterWorker::identify);
|
2022-01-15 00:49:38 +03:00
|
|
|
connect(this, &IppPrinter::doJustUpload, &_worker, &PrinterWorker::justUpload);
|
2022-05-02 22:10:03 +03:00
|
|
|
connect(this, &IppPrinter::doFixupPlaintext, &_worker, &PrinterWorker::fixupPlaintext);
|
2022-05-26 12:57:16 +03:00
|
|
|
connect(this, &IppPrinter::doPrintImageAsImage, &_worker, &PrinterWorker::printImageAsImage);
|
2021-08-28 23:16:26 +03:00
|
|
|
|
2022-01-15 00:49:38 +03:00
|
|
|
connect(this, &IppPrinter::doConvertPdf, &_worker, &PrinterWorker::convertPdf);
|
|
|
|
connect(this, &IppPrinter::doConvertImage, &_worker, &PrinterWorker::convertImage);
|
|
|
|
connect(this, &IppPrinter::doConvertOfficeDocument, &_worker, &PrinterWorker::convertOfficeDocument);
|
|
|
|
connect(this, &IppPrinter::doConvertPlaintext, &_worker, &PrinterWorker::convertPlaintext);
|
2022-01-15 00:14:06 +03:00
|
|
|
|
2022-01-15 00:49:38 +03:00
|
|
|
connect(this, &IppPrinter::doGetStrings, &_worker, &PrinterWorker::getStrings);
|
2022-02-19 19:33:59 +03:00
|
|
|
connect(this, &IppPrinter::doGetImage, &_worker, &PrinterWorker::getImage);
|
2022-01-15 00:14:06 +03:00
|
|
|
|
2022-01-15 00:49:38 +03:00
|
|
|
connect(&_worker, &PrinterWorker::progress, this, &IppPrinter::setProgress);
|
|
|
|
connect(&_worker, &PrinterWorker::busyMessage, this, &IppPrinter::setBusyMessage);
|
|
|
|
connect(&_worker, &PrinterWorker::failed, this, &IppPrinter::convertFailed);
|
2020-05-01 16:02:29 +03:00
|
|
|
|
2021-07-14 16:07:55 +03:00
|
|
|
qRegisterMetaType<QMargins>();
|
|
|
|
|
2020-05-01 16:02:29 +03:00
|
|
|
_workerThread.start();
|
2019-12-01 22:27:00 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
IppPrinter::~IppPrinter() {
|
2021-08-28 23:16:26 +03:00
|
|
|
|
2019-12-12 22:53:46 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
QJsonObject IppPrinter::opAttrs() {
|
2020-08-02 12:44:38 +03:00
|
|
|
QString name = qgetenv("USER");
|
2019-12-12 22:53:46 +03:00
|
|
|
QJsonObject o
|
|
|
|
{
|
|
|
|
{"attributes-charset", QJsonObject {{"tag", IppMsg::Charset}, {"value", "utf-8"}}},
|
|
|
|
{"attributes-natural-language", QJsonObject {{"tag", IppMsg::NaturalLanguage}, {"value", "en-us"}}},
|
2020-01-03 18:36:24 +03:00
|
|
|
{"printer-uri", QJsonObject {{"tag", IppMsg::Uri}, {"value", _url.toString()}}},
|
2020-08-02 12:44:38 +03:00
|
|
|
{"requesting-user-name", QJsonObject {{"tag", IppMsg::NameWithoutLanguage}, {"value", name}}},
|
2019-12-12 22:53:46 +03:00
|
|
|
};
|
|
|
|
return o;
|
2019-12-01 22:27:00 +03:00
|
|
|
}
|
|
|
|
|
2020-01-03 18:36:24 +03:00
|
|
|
void IppPrinter::setUrl(QString url_s)
|
2019-12-01 22:27:00 +03:00
|
|
|
{
|
2020-01-03 18:36:24 +03:00
|
|
|
QUrl url = QUrl(url_s);
|
|
|
|
|
2021-06-19 19:16:42 +03:00
|
|
|
// If not already a good scheme, try to fixup, or give an empty url
|
|
|
|
if(url.scheme() != "ipp" && url.scheme() != "ipps" && url.scheme() != "file")
|
2020-01-03 18:36:24 +03:00
|
|
|
{
|
|
|
|
if(url.scheme() == "")
|
|
|
|
{
|
|
|
|
url = QUrl("ipp://"+url_s); // Why isn't setScheme working?
|
|
|
|
}
|
|
|
|
else if (url.scheme() == "http") {
|
|
|
|
url.setScheme("ipp");
|
|
|
|
}
|
2021-06-19 19:16:42 +03:00
|
|
|
else if (url.scheme() == "https") {
|
|
|
|
url.setScheme("ipps");
|
|
|
|
}
|
2020-01-03 18:36:24 +03:00
|
|
|
else {
|
|
|
|
url = QUrl();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
qDebug() << url_s << url;
|
|
|
|
|
2019-12-01 22:27:00 +03:00
|
|
|
if(url != _url)
|
|
|
|
{
|
|
|
|
_url = url;
|
|
|
|
emit urlChanged();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void IppPrinter::onUrlChanged()
|
|
|
|
{
|
2019-12-17 22:20:09 +03:00
|
|
|
refresh();
|
|
|
|
}
|
|
|
|
|
|
|
|
void IppPrinter::refresh() {
|
2021-06-19 19:16:42 +03:00
|
|
|
|
2021-02-13 16:59:38 +03:00
|
|
|
if(_url.scheme() == "file")
|
|
|
|
{
|
2021-03-20 14:30:49 +03:00
|
|
|
_attrs = QJsonObject();
|
2022-06-04 15:43:53 +03:00
|
|
|
QString localFile = _url.toLocalFile();
|
2021-03-20 14:30:49 +03:00
|
|
|
|
2022-06-04 15:43:53 +03:00
|
|
|
if(localFile.endsWith(".raw") || localFile.endsWith(".bin"))
|
2021-02-13 16:59:38 +03:00
|
|
|
{
|
2022-06-04 15:43:53 +03:00
|
|
|
try
|
|
|
|
{
|
|
|
|
std::ifstream ifs = std::ifstream(localFile.toStdString(), std::ios::in | std::ios::binary);
|
|
|
|
Bytestream InBts(ifs);
|
|
|
|
IppMsg resp(InBts);
|
|
|
|
qDebug() << resp.getStatus() << resp.getOpAttrs() << resp.getPrinterAttrs();
|
|
|
|
_attrs = resp.getPrinterAttrs();
|
|
|
|
}
|
|
|
|
catch(const std::exception& e)
|
|
|
|
{
|
|
|
|
qDebug() << e.what();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
QFile file(localFile);
|
|
|
|
if(file.open(QIODevice::ReadOnly))
|
|
|
|
{
|
|
|
|
QJsonDocument JsonDocument = QJsonDocument::fromJson(file.readAll());
|
|
|
|
_attrs = JsonDocument.object();
|
|
|
|
file.close();
|
|
|
|
}
|
2021-02-13 16:59:38 +03:00
|
|
|
}
|
2022-06-04 15:43:53 +03:00
|
|
|
_attrs.remove("printer-icons");
|
|
|
|
Overrider::instance()->apply(_attrs);
|
2021-02-13 16:59:38 +03:00
|
|
|
emit attrsChanged();
|
2022-01-15 00:14:06 +03:00
|
|
|
|
2022-02-19 19:33:59 +03:00
|
|
|
// MaybeGetStrings(); - for testing fake file-prinetrs with a strings file hosted elsewhere
|
2021-02-13 16:59:38 +03:00
|
|
|
UpdateAdditionalDocumentFormats();
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
QJsonObject o = opAttrs();
|
2019-12-01 22:27:00 +03:00
|
|
|
|
2021-02-13 16:59:38 +03:00
|
|
|
IppMsg msg = IppMsg(o);
|
2022-01-07 22:36:21 +03:00
|
|
|
emit doDoGetPrinterAttributes(msg.encode(IppMsg::GetPrinterAttrs));
|
2021-02-13 16:59:38 +03:00
|
|
|
}
|
2019-12-01 22:27:00 +03:00
|
|
|
}
|
|
|
|
|
2022-01-15 00:14:06 +03:00
|
|
|
void IppPrinter::MaybeGetStrings()
|
|
|
|
{
|
|
|
|
if(_attrs.contains("printer-strings-uri") && _strings.empty())
|
|
|
|
{
|
2022-01-15 00:44:55 +03:00
|
|
|
QUrl url(_attrs["printer-strings-uri"].toObject()["value"].toString());
|
2022-05-26 15:42:01 +03:00
|
|
|
resolveUrl(url);
|
2022-05-15 22:21:32 +03:00
|
|
|
if(isAllowedAddress(url))
|
|
|
|
{
|
|
|
|
emit doGetStrings(url);
|
|
|
|
}
|
2022-01-15 00:14:06 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2022-02-19 19:33:59 +03:00
|
|
|
void IppPrinter::MaybeGetIcon(bool retry)
|
|
|
|
{
|
2022-05-19 21:49:57 +03:00
|
|
|
if(_attrs.contains("printer-icons") && (_icon.isNull() || retry) && !_iconRetried)
|
2022-02-19 19:33:59 +03:00
|
|
|
{
|
|
|
|
QUrl url;
|
|
|
|
QJsonArray icons = _attrs["printer-icons"].toObject()["value"].toArray();
|
|
|
|
|
|
|
|
if(retry)
|
|
|
|
{ // If there were more than one icon, try the last one on the retry
|
|
|
|
if(icons.size() > 1)
|
|
|
|
{
|
|
|
|
url = icons.last().toString();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
if(icons.size() == 3)
|
|
|
|
{ // If there are 3 icons, the first will be the 48px one, ignore it
|
|
|
|
url = icons.at(1).toString();
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
url = icons.at(0).toString();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2022-05-26 15:42:01 +03:00
|
|
|
resolveUrl(url);
|
|
|
|
|
2022-05-15 22:21:32 +03:00
|
|
|
if(isAllowedAddress(url))
|
2022-02-19 19:33:59 +03:00
|
|
|
{
|
|
|
|
emit doGetImage(url);
|
|
|
|
}
|
|
|
|
}
|
2022-05-19 21:49:57 +03:00
|
|
|
_iconRetried = retry;
|
2022-02-19 19:33:59 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2021-02-13 16:59:38 +03:00
|
|
|
void IppPrinter::UpdateAdditionalDocumentFormats()
|
2019-12-01 22:27:00 +03:00
|
|
|
{
|
2020-10-11 17:27:46 +03:00
|
|
|
_additionalDocumentFormats = QStringList();
|
|
|
|
|
2020-06-05 21:05:48 +03:00
|
|
|
if(_attrs.contains("printer-device-id"))
|
|
|
|
{
|
|
|
|
QJsonArray supportedMimeTypes = _attrs["document-format-supported"].toObject()["value"].toArray();
|
|
|
|
QStringList printerDeviceId = _attrs["printer-device-id"].toObject()["value"].toString().split(";");
|
|
|
|
for (QStringList::iterator it = printerDeviceId.begin(); it != printerDeviceId.end(); it++)
|
|
|
|
{
|
|
|
|
QStringList kv = it->split(":");
|
2020-06-13 14:05:33 +03:00
|
|
|
if(kv.length()==2 && (kv[0]=="CMD" || kv[0]=="COMMAND SET"))
|
2020-06-05 21:05:48 +03:00
|
|
|
{
|
2021-03-04 23:49:27 +03:00
|
|
|
if(!supportedMimeTypes.contains(Mimer::PDF) && kv[1].contains("PDF"))
|
2020-06-05 21:05:48 +03:00
|
|
|
{
|
2021-03-04 23:49:27 +03:00
|
|
|
_additionalDocumentFormats.append(Mimer::PDF);
|
2020-06-05 21:05:48 +03:00
|
|
|
}
|
2021-03-04 23:49:27 +03:00
|
|
|
if(!supportedMimeTypes.contains(Mimer::Postscript) &&
|
2020-06-13 14:05:33 +03:00
|
|
|
kv[1].contains("Postscript", Qt::CaseInsensitive))
|
2020-06-05 21:05:48 +03:00
|
|
|
{
|
2021-03-04 23:49:27 +03:00
|
|
|
_additionalDocumentFormats.append(Mimer::Postscript);
|
2020-06-05 21:05:48 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
qDebug() << "additionalDocumentFormats" << _additionalDocumentFormats;
|
|
|
|
}
|
2021-02-13 16:59:38 +03:00
|
|
|
emit additionalDocumentFormatsChanged();
|
|
|
|
}
|
|
|
|
|
2021-12-14 22:01:52 +03:00
|
|
|
void IppPrinter::getPrinterAttributesFinished(CURLcode res, Bytestream data)
|
2021-02-13 16:59:38 +03:00
|
|
|
{
|
2021-08-28 23:16:26 +03:00
|
|
|
qDebug() << res;
|
2021-02-13 16:59:38 +03:00
|
|
|
_attrs = QJsonObject();
|
|
|
|
|
2021-08-28 23:16:26 +03:00
|
|
|
if(res == CURLE_OK)
|
2021-02-13 16:59:38 +03:00
|
|
|
{
|
|
|
|
try {
|
2021-08-28 23:16:26 +03:00
|
|
|
IppMsg resp(data);
|
2021-02-13 16:59:38 +03:00
|
|
|
qDebug() << resp.getStatus() << resp.getOpAttrs() << resp.getPrinterAttrs();
|
|
|
|
_attrs = resp.getPrinterAttrs();
|
2021-05-25 20:37:49 +03:00
|
|
|
Overrider::instance()->apply(_attrs);
|
|
|
|
|
2021-02-13 16:59:38 +03:00
|
|
|
}
|
|
|
|
catch(const std::exception& e)
|
|
|
|
{
|
|
|
|
qDebug() << e.what();
|
|
|
|
}
|
|
|
|
}
|
2020-06-05 21:05:48 +03:00
|
|
|
|
2019-12-15 13:24:36 +03:00
|
|
|
emit attrsChanged();
|
2020-10-11 17:27:46 +03:00
|
|
|
|
2022-01-15 00:14:06 +03:00
|
|
|
MaybeGetStrings();
|
2022-02-19 19:33:59 +03:00
|
|
|
MaybeGetIcon();
|
2021-02-13 16:59:38 +03:00
|
|
|
UpdateAdditionalDocumentFormats();
|
2019-12-01 22:27:00 +03:00
|
|
|
}
|
|
|
|
|
2021-12-14 22:01:52 +03:00
|
|
|
void IppPrinter::printRequestFinished(CURLcode res, Bytestream data)
|
2019-12-01 22:27:00 +03:00
|
|
|
{
|
2019-12-17 22:18:57 +03:00
|
|
|
_jobAttrs = QJsonObject();
|
|
|
|
bool status = false;
|
2021-08-28 23:16:26 +03:00
|
|
|
|
|
|
|
if(res == CURLE_OK)
|
2019-12-01 22:27:00 +03:00
|
|
|
{
|
|
|
|
try {
|
2021-08-28 23:16:26 +03:00
|
|
|
IppMsg resp(data);
|
2019-12-06 22:18:48 +03:00
|
|
|
qDebug() << resp.getStatus() << resp.getOpAttrs() << resp.getJobAttrs();
|
2019-12-08 15:55:56 +03:00
|
|
|
_jobAttrs = resp.getJobAttrs()[0].toObject();
|
2020-06-12 18:02:24 +03:00
|
|
|
if(resp.getOpAttrs().keys().contains("status-message"))
|
|
|
|
{ // Sometimes there are no response attributes at all,
|
|
|
|
// maybe status-message from the operation attributes is somewhat useful
|
|
|
|
_jobAttrs["status-message"] = resp.getOpAttrs()["status-message"];
|
|
|
|
}
|
2019-12-17 22:18:57 +03:00
|
|
|
status = resp.getStatus() <= 0xff;
|
2019-12-01 22:27:00 +03:00
|
|
|
}
|
2020-08-29 18:32:11 +03:00
|
|
|
catch(const std::exception& e)
|
2019-12-01 22:27:00 +03:00
|
|
|
{
|
|
|
|
qDebug() << e.what();
|
|
|
|
}
|
|
|
|
}
|
2019-12-17 22:18:57 +03:00
|
|
|
else {
|
2020-06-13 14:05:33 +03:00
|
|
|
_jobAttrs.insert("job-state-message", QJsonObject {{"tag", IppMsg::TextWithoutLanguage},
|
|
|
|
{"value", "Network error"}});
|
2019-12-17 22:18:57 +03:00
|
|
|
}
|
2021-08-28 23:16:26 +03:00
|
|
|
|
2019-12-17 22:18:57 +03:00
|
|
|
emit jobAttrsChanged();
|
2020-04-04 14:56:36 +03:00
|
|
|
emit jobFinished(status);
|
2019-12-01 22:27:00 +03:00
|
|
|
}
|
|
|
|
|
2021-12-14 22:01:52 +03:00
|
|
|
void IppPrinter::getJobsRequestFinished(CURLcode res, Bytestream data)
|
2019-12-08 15:55:56 +03:00
|
|
|
{
|
2021-08-28 23:16:26 +03:00
|
|
|
if(res == CURLE_OK)
|
2019-12-08 15:55:56 +03:00
|
|
|
{
|
|
|
|
try {
|
2021-08-28 23:16:26 +03:00
|
|
|
IppMsg resp(data);
|
2019-12-08 15:55:56 +03:00
|
|
|
qDebug() << resp.getStatus() << resp.getOpAttrs() << resp.getJobAttrs();
|
|
|
|
_jobs = resp.getJobAttrs();
|
|
|
|
emit jobsChanged();
|
|
|
|
}
|
2020-08-29 18:32:11 +03:00
|
|
|
catch(const std::exception& e)
|
2019-12-08 15:55:56 +03:00
|
|
|
{
|
|
|
|
qDebug() << e.what();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-12-01 22:27:00 +03:00
|
|
|
|
2021-12-14 22:01:52 +03:00
|
|
|
void IppPrinter::cancelJobFinished(CURLcode res, Bytestream data)
|
2019-12-12 22:53:46 +03:00
|
|
|
{
|
2020-02-23 15:11:28 +03:00
|
|
|
bool status = false;
|
2021-08-28 23:16:26 +03:00
|
|
|
if(res == CURLE_OK)
|
2019-12-12 22:53:46 +03:00
|
|
|
{
|
|
|
|
try {
|
2021-08-28 23:16:26 +03:00
|
|
|
IppMsg resp(data);
|
2019-12-12 22:53:46 +03:00
|
|
|
qDebug() << resp.getStatus() << resp.getOpAttrs() << resp.getJobAttrs();
|
2020-02-23 15:11:28 +03:00
|
|
|
status = resp.getStatus() <= 0xff;
|
2019-12-12 22:53:46 +03:00
|
|
|
}
|
2020-08-29 18:32:11 +03:00
|
|
|
catch(const std::exception& e)
|
2019-12-12 22:53:46 +03:00
|
|
|
{
|
|
|
|
qDebug() << e.what();
|
|
|
|
}
|
|
|
|
}
|
2020-02-23 15:11:28 +03:00
|
|
|
emit cancelStatus(status);
|
2019-12-12 22:53:46 +03:00
|
|
|
getJobs();
|
|
|
|
}
|
|
|
|
|
2022-05-16 21:29:53 +03:00
|
|
|
void IppPrinter::identifyFinished(CURLcode /*res*/, Bytestream /*data*/)
|
|
|
|
{
|
|
|
|
|
|
|
|
}
|
|
|
|
|
2022-01-15 00:14:06 +03:00
|
|
|
void IppPrinter::getStringsFinished(CURLcode res, Bytestream data)
|
|
|
|
{
|
|
|
|
qDebug() << res << data.size();
|
|
|
|
if(res == CURLE_OK)
|
|
|
|
{
|
|
|
|
QByteArray ba((char*)data.raw(), data.size());
|
|
|
|
// "media-type.com.epson-coated" = "Epson Photo Quality Ink Jet";
|
|
|
|
QRegularExpression re("^\\\"(.*)\\\"\\s*=\\s*\\\"(.*)\\\";");
|
|
|
|
QList<QByteArray> bl = ba.split('\n');
|
2022-05-22 12:00:32 +03:00
|
|
|
for(QByteArray l : bl)
|
2022-01-15 00:14:06 +03:00
|
|
|
{
|
|
|
|
QRegularExpressionMatch match = re.match(l);
|
|
|
|
if(match.hasMatch())
|
|
|
|
{
|
|
|
|
_strings[match.captured(1)] = match.captured(2);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2021-06-26 14:27:32 +03:00
|
|
|
|
2022-02-19 19:33:59 +03:00
|
|
|
void IppPrinter::getImageFinished(CURLcode res, Bytestream data)
|
|
|
|
{
|
|
|
|
qDebug() << res << data.size();
|
|
|
|
if(res == CURLE_OK)
|
|
|
|
{
|
|
|
|
QImage tmp;
|
|
|
|
if(tmp.loadFromData(data.raw(), data.size(), "PNG"))
|
|
|
|
{
|
|
|
|
_icon = tmp;
|
|
|
|
qDebug() << "image loaded" << _icon;
|
|
|
|
emit iconChanged();
|
|
|
|
|
|
|
|
if(tmp.size().width() < 128)
|
|
|
|
{
|
|
|
|
MaybeGetIcon(true);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-05-14 22:00:37 +03:00
|
|
|
void IppPrinter::convertFailed(QString message)
|
2020-05-01 16:02:29 +03:00
|
|
|
{
|
|
|
|
_jobAttrs = QJsonObject();
|
2020-05-14 22:00:37 +03:00
|
|
|
_jobAttrs.insert("job-state-message", QJsonObject {{"tag", IppMsg::TextWithoutLanguage}, {"value", message}});
|
2020-05-01 16:02:29 +03:00
|
|
|
emit jobAttrsChanged();
|
|
|
|
emit jobFinished(false);
|
|
|
|
}
|
2020-01-04 13:55:22 +03:00
|
|
|
|
2020-06-05 21:41:45 +03:00
|
|
|
QString firstMatch(QJsonArray supported, QStringList wanted)
|
|
|
|
{
|
|
|
|
for(QStringList::iterator it = wanted.begin(); it != wanted.end(); it++)
|
|
|
|
{
|
|
|
|
if(supported.contains(*it))
|
|
|
|
{
|
|
|
|
return *it;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return "";
|
|
|
|
}
|
|
|
|
|
2021-03-21 19:10:40 +03:00
|
|
|
QString targetFormatIfAuto(QString documentFormat, QString mimeType, QJsonArray supportedMimeTypes)
|
2020-06-05 21:41:45 +03:00
|
|
|
{
|
2021-03-21 19:10:40 +03:00
|
|
|
if(documentFormat == Mimer::OctetStream)
|
2020-06-05 21:41:45 +03:00
|
|
|
{
|
2022-05-02 22:10:03 +03:00
|
|
|
QStringList PdfPrioList = {Mimer::PDF, Mimer::Postscript, Mimer::PWG, Mimer::URF};
|
|
|
|
if(mimeType == Mimer::PDF)
|
2020-06-05 21:41:45 +03:00
|
|
|
{
|
2022-05-02 22:10:03 +03:00
|
|
|
return firstMatch(supportedMimeTypes, PdfPrioList);
|
2020-06-05 21:41:45 +03:00
|
|
|
}
|
2021-03-04 23:49:27 +03:00
|
|
|
else if(mimeType == Mimer::Postscript)
|
2021-02-13 23:59:46 +03:00
|
|
|
{
|
2021-03-04 23:49:27 +03:00
|
|
|
return firstMatch(supportedMimeTypes, {Mimer::Postscript});
|
2021-02-13 23:59:46 +03:00
|
|
|
}
|
2022-05-02 22:10:03 +03:00
|
|
|
else if(mimeType == Mimer::Plaintext)
|
|
|
|
{
|
|
|
|
return firstMatch(supportedMimeTypes, PdfPrioList << Mimer::Plaintext);
|
|
|
|
}
|
2021-03-06 18:42:13 +03:00
|
|
|
else if(Mimer::isOffice(mimeType))
|
|
|
|
{
|
2022-05-02 22:10:03 +03:00
|
|
|
return firstMatch(supportedMimeTypes, PdfPrioList);
|
2021-03-06 18:42:13 +03:00
|
|
|
}
|
2022-05-29 16:54:11 +03:00
|
|
|
else if(documentFormat == Mimer::SVG)
|
|
|
|
{
|
|
|
|
QStringList SvgPrioList {Mimer::PWG, Mimer::URF, Mimer::PDF, Mimer::Postscript};
|
|
|
|
return firstMatch(supportedMimeTypes, SvgPrioList);
|
|
|
|
}
|
2021-03-04 23:49:27 +03:00
|
|
|
else if(Mimer::isImage(mimeType))
|
2020-06-05 21:41:45 +03:00
|
|
|
{
|
2021-06-13 14:56:44 +03:00
|
|
|
QStringList ImageFormatPrioList {Mimer::PNG, Mimer::PWG, Mimer::URF, Mimer::PDF, Mimer::Postscript, Mimer::JPEG};
|
2021-03-04 23:49:27 +03:00
|
|
|
if(mimeType == Mimer::JPEG)
|
2020-09-10 21:01:21 +03:00
|
|
|
{
|
|
|
|
// Prioritize transferring JPEG as JPEG, as it will not be transcoded
|
|
|
|
// Normally, it is the last choice (as the others are lossless)
|
|
|
|
ImageFormatPrioList.prepend(mimeType);
|
|
|
|
}
|
|
|
|
return firstMatch(supportedMimeTypes, ImageFormatPrioList);
|
2020-06-05 21:41:45 +03:00
|
|
|
}
|
|
|
|
return documentFormat;
|
|
|
|
}
|
|
|
|
return documentFormat;
|
|
|
|
}
|
|
|
|
|
2022-03-26 18:35:21 +03:00
|
|
|
void IppPrinter::adjustRasterSettings(QString documentFormat, QJsonObject& jobAttrs, PrintParameters& Params)
|
2020-06-04 22:31:46 +03:00
|
|
|
{
|
2021-06-26 15:58:14 +03:00
|
|
|
if(documentFormat != Mimer::PWG && documentFormat != Mimer::URF)
|
|
|
|
{
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2021-06-27 17:23:27 +03:00
|
|
|
//TODO? jobAttrs.remove("printer-resolution");
|
|
|
|
|
|
|
|
if(documentFormat == Mimer::PWG)
|
|
|
|
{
|
|
|
|
quint32 diff = std::numeric_limits<quint32>::max();
|
2022-03-26 18:35:21 +03:00
|
|
|
quint32 AdjustedHwResX = Params.hwResW;
|
|
|
|
quint32 AdjustedHwResY = Params.hwResH;
|
2022-05-22 12:00:32 +03:00
|
|
|
for(QJsonValue res : _attrs["pwg-raster-document-resolution-supported"].toObject()["value"].toArray())
|
2021-06-27 17:23:27 +03:00
|
|
|
{
|
|
|
|
QJsonObject resObj = res.toObject();
|
|
|
|
if(resObj["units"] != 3)
|
|
|
|
{
|
|
|
|
continue;
|
|
|
|
}
|
2022-03-26 18:35:21 +03:00
|
|
|
quint32 tmpDiff = std::abs(int(Params.hwResW-resObj["x"].toInt())) + std::abs(int(Params.hwResH-resObj["y"].toInt()));
|
2021-06-27 17:23:27 +03:00
|
|
|
if(tmpDiff < diff)
|
|
|
|
{
|
|
|
|
diff = tmpDiff;
|
|
|
|
AdjustedHwResX = resObj["x"].toInt();
|
|
|
|
AdjustedHwResY = resObj["y"].toInt();
|
|
|
|
}
|
|
|
|
}
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.hwResW = AdjustedHwResX;
|
|
|
|
Params.hwResH = AdjustedHwResY;
|
2021-06-27 17:23:27 +03:00
|
|
|
}
|
|
|
|
|
2021-06-26 14:42:54 +03:00
|
|
|
if(documentFormat == Mimer::URF)
|
|
|
|
{ // Ensure symmetric resolution for URF
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.hwResW = Params.hwResH = std::min(Params.hwResW, Params.hwResH);
|
2021-06-26 14:42:54 +03:00
|
|
|
|
2021-06-27 17:23:27 +03:00
|
|
|
quint32 diff = std::numeric_limits<quint32>::max();
|
2022-03-26 18:35:21 +03:00
|
|
|
quint32 AdjustedHwRes = Params.hwResW;
|
2021-06-27 17:23:27 +03:00
|
|
|
|
|
|
|
QJsonArray urfSupported = _attrs["urf-supported"].toObject()["value"].toArray();
|
2022-05-22 12:00:32 +03:00
|
|
|
for(QJsonValue us : urfSupported)
|
2021-06-26 14:42:54 +03:00
|
|
|
{
|
2021-06-27 17:23:27 +03:00
|
|
|
if(us.toString().startsWith("RS"))
|
|
|
|
{ //RS300[-600]
|
|
|
|
QStringList resolutions = us.toString().mid(2).split("-");
|
2022-05-22 12:00:32 +03:00
|
|
|
for(QString res : resolutions)
|
2021-06-27 17:23:27 +03:00
|
|
|
{
|
|
|
|
int intRes = res.toInt();
|
2022-03-26 18:35:21 +03:00
|
|
|
quint32 tmpDiff = std::abs(int(Params.hwResW - intRes));
|
2021-06-27 17:23:27 +03:00
|
|
|
if(tmpDiff < diff)
|
|
|
|
{
|
|
|
|
diff = tmpDiff;
|
|
|
|
AdjustedHwRes = intRes;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.hwResW = Params.hwResH = AdjustedHwRes;
|
2021-06-27 17:23:27 +03:00
|
|
|
break;
|
|
|
|
}
|
2021-06-26 14:42:54 +03:00
|
|
|
}
|
|
|
|
}
|
2021-06-26 15:58:14 +03:00
|
|
|
|
|
|
|
QString Sides = getAttrOrDefault(jobAttrs, "sides").toString();
|
|
|
|
|
|
|
|
if(Sides != "" && Sides != "one-sided")
|
|
|
|
{
|
|
|
|
if(documentFormat == Mimer::PWG)
|
|
|
|
{
|
|
|
|
QString DocumentSheetBack = _attrs["pwg-raster-document-sheet-back"].toObject()["value"].toString();
|
|
|
|
if(Sides=="two-sided-long-edge")
|
|
|
|
{
|
|
|
|
if(DocumentSheetBack=="flipped")
|
|
|
|
{
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.backVFlip=true;
|
2021-06-26 15:58:14 +03:00
|
|
|
}
|
|
|
|
else if(DocumentSheetBack=="rotated")
|
|
|
|
{
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.backHFlip=true;
|
|
|
|
Params.backVFlip=true;
|
2021-06-26 15:58:14 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
else if(Sides=="two-sided-short-edge")
|
|
|
|
{
|
|
|
|
if(DocumentSheetBack=="flipped")
|
|
|
|
{
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.backHFlip=true;
|
2021-06-26 15:58:14 +03:00
|
|
|
}
|
|
|
|
else if(DocumentSheetBack=="manual-tumble")
|
|
|
|
{
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.backHFlip=true;
|
|
|
|
Params.backVFlip=true;
|
2021-06-26 15:58:14 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if(documentFormat == Mimer::URF)
|
|
|
|
{
|
|
|
|
QJsonArray URfSupported = _attrs["urf-supported"].toObject()["value"].toArray();
|
|
|
|
if(Sides=="two-sided-long-edge")
|
|
|
|
{
|
|
|
|
if(URfSupported.contains("DM2"))
|
|
|
|
{
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.backVFlip=true;
|
2021-06-26 15:58:14 +03:00
|
|
|
}
|
|
|
|
else if(URfSupported.contains("DM3"))
|
|
|
|
{
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.backHFlip=true;
|
|
|
|
Params.backVFlip=true;
|
2021-06-26 15:58:14 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
else if(Sides=="two-sided-short-edge")
|
|
|
|
{
|
|
|
|
if(URfSupported.contains("DM2"))
|
|
|
|
{
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.backHFlip=true;
|
2021-06-26 15:58:14 +03:00
|
|
|
}
|
|
|
|
else if(URfSupported.contains("DM4"))
|
|
|
|
{
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.backHFlip=true;
|
|
|
|
Params.backVFlip=true;
|
2021-06-26 15:58:14 +03:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2021-06-26 14:42:54 +03:00
|
|
|
}
|
|
|
|
|
|
|
|
void IppPrinter::print(QJsonObject jobAttrs, QString filename)
|
|
|
|
{
|
|
|
|
qDebug() << "printing" << filename << jobAttrs;
|
2019-12-01 22:27:00 +03:00
|
|
|
|
2020-06-03 21:42:18 +03:00
|
|
|
_progress = "";
|
|
|
|
emit progressChanged();
|
|
|
|
|
2022-03-19 19:31:55 +03:00
|
|
|
PrintParameters Params;
|
2021-08-28 23:16:26 +03:00
|
|
|
QFileInfo fileinfo(filename);
|
|
|
|
|
|
|
|
if(!fileinfo.exists())
|
2020-04-04 14:56:36 +03:00
|
|
|
{
|
2020-05-14 22:00:37 +03:00
|
|
|
emit convertFailed(tr("Failed to open file"));
|
2020-04-04 14:56:36 +03:00
|
|
|
return;
|
|
|
|
}
|
2019-12-01 22:27:00 +03:00
|
|
|
|
2020-06-05 21:41:45 +03:00
|
|
|
Mimer* mimer = Mimer::instance();
|
|
|
|
QString mimeType = mimer->get_type(filename);
|
|
|
|
|
|
|
|
|
|
|
|
QJsonArray supportedMimeTypes = _attrs["document-format-supported"].toObject()["value"].toArray();
|
|
|
|
for(QStringList::iterator it = _additionalDocumentFormats.begin(); it != _additionalDocumentFormats.end(); it++)
|
|
|
|
{
|
|
|
|
supportedMimeTypes.append(*it);
|
|
|
|
}
|
|
|
|
|
|
|
|
qDebug() << supportedMimeTypes << supportedMimeTypes.contains(mimeType);
|
|
|
|
|
2019-12-12 22:53:46 +03:00
|
|
|
QJsonObject o = opAttrs();
|
|
|
|
o.insert("job-name", QJsonObject {{"tag", IppMsg::NameWithoutLanguage}, {"value", fileinfo.fileName()}});
|
|
|
|
|
2022-03-23 22:34:38 +03:00
|
|
|
Params.paperSizeName = getAttrOrDefault(jobAttrs, "media").toString(Params.paperSizeName.c_str()).toStdString();
|
2020-06-16 21:34:27 +03:00
|
|
|
|
2022-03-19 19:31:55 +03:00
|
|
|
QString targetFormat = getAttrOrDefault(jobAttrs, "document-format").toString();
|
|
|
|
qDebug() << "target format:" << targetFormat;
|
2022-03-19 19:30:52 +03:00
|
|
|
|
|
|
|
QMargins margins(getAttrOrDefault(jobAttrs, "media-left-margin", "media-col").toInt(),
|
|
|
|
getAttrOrDefault(jobAttrs, "media-top-margin", "media-col").toInt(),
|
|
|
|
getAttrOrDefault(jobAttrs, "media-right-margin", "media-col").toInt(),
|
|
|
|
getAttrOrDefault(jobAttrs, "media-bottom-margin", "media-col").toInt());
|
|
|
|
|
|
|
|
// Only keep margin setting for JPEG - but only attemt to remove it if media-col exists
|
2022-05-16 22:52:00 +03:00
|
|
|
if(!mimer->isImage(targetFormat) && jobAttrs.contains("media-col"))
|
2022-03-19 19:30:52 +03:00
|
|
|
{
|
|
|
|
QJsonObject MediaCol = jobAttrs["media-col"].toObject();
|
|
|
|
QJsonObject MediaColValue = MediaCol["value"].toObject();
|
|
|
|
|
|
|
|
MediaColValue.remove("media-left-margin");
|
|
|
|
MediaColValue.remove("media-top-margin");
|
|
|
|
MediaColValue.remove("media-right-margin");
|
|
|
|
MediaColValue.remove("media-bottom-margin");
|
|
|
|
|
|
|
|
if(!MediaColValue.empty())
|
|
|
|
{
|
|
|
|
MediaCol["value"] = MediaColValue;
|
|
|
|
jobAttrs["media-col"] = MediaCol;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
jobAttrs.remove("media-col");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2021-07-31 13:59:51 +03:00
|
|
|
if(jobAttrs.contains("media-col") && jobAttrs.contains("media"))
|
2020-06-16 21:34:27 +03:00
|
|
|
{
|
2022-03-23 22:34:38 +03:00
|
|
|
qDebug() << "moving media to media-col" << Params.paperSizeName.c_str();
|
|
|
|
if(!PaperSizes.contains(Params.paperSizeName.c_str()))
|
2020-06-16 21:34:27 +03:00
|
|
|
{
|
2022-03-23 22:34:38 +03:00
|
|
|
emit convertFailed(tr("Unsupported paper size"));
|
2020-06-16 21:34:27 +03:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
2022-03-23 22:34:38 +03:00
|
|
|
int x = PaperSizes[Params.paperSizeName.c_str()].width()*100;
|
|
|
|
int y = PaperSizes[Params.paperSizeName.c_str()].height()*100;
|
2020-06-16 21:34:27 +03:00
|
|
|
|
|
|
|
QJsonObject Dimensions =
|
|
|
|
{{"tag", IppMsg::BeginCollection},
|
|
|
|
{"value", QJsonObject { {"x-dimension", QJsonObject{{"tag", IppMsg::Integer}, {"value", x}}},
|
|
|
|
{"y-dimension", QJsonObject{{"tag", IppMsg::Integer}, {"value", y}}} }
|
|
|
|
}};
|
|
|
|
|
|
|
|
// TODO: make a setter function
|
2021-06-26 14:42:54 +03:00
|
|
|
QJsonObject MediaCol = jobAttrs["media-col"].toObject();
|
2020-06-16 21:34:27 +03:00
|
|
|
QJsonObject MediaColValue = MediaCol["value"].toObject();
|
|
|
|
MediaColValue["media-size"] = Dimensions;
|
|
|
|
MediaCol["value"] = MediaColValue;
|
2020-06-21 16:49:50 +03:00
|
|
|
MediaCol["tag"] = IppMsg::BeginCollection;
|
2021-06-26 14:42:54 +03:00
|
|
|
jobAttrs["media-col"] = MediaCol;
|
2020-06-16 21:34:27 +03:00
|
|
|
|
2021-06-26 14:42:54 +03:00
|
|
|
jobAttrs.remove("media");
|
2020-06-16 21:34:27 +03:00
|
|
|
}
|
2020-06-04 22:31:46 +03:00
|
|
|
|
2020-06-13 18:56:28 +03:00
|
|
|
// document-format goes in the op-attrs and not the job-attrs
|
2022-03-19 19:31:55 +03:00
|
|
|
o.insert("document-format", QJsonObject {{"tag", IppMsg::MimeMediaType}, {"value", targetFormat}});
|
2021-06-26 14:42:54 +03:00
|
|
|
jobAttrs.remove("document-format");
|
2020-06-13 18:56:28 +03:00
|
|
|
|
2022-03-19 19:31:55 +03:00
|
|
|
targetFormat = targetFormatIfAuto(targetFormat, mimeType, supportedMimeTypes);
|
|
|
|
qDebug() << "adjusted target format:" << targetFormat;
|
2020-06-05 21:41:45 +03:00
|
|
|
|
2022-03-19 19:31:55 +03:00
|
|
|
if(targetFormat == "" || targetFormat == Mimer::OctetStream)
|
2020-06-04 22:31:46 +03:00
|
|
|
{
|
|
|
|
emit convertFailed(tr("Unknown document format"));
|
|
|
|
return;
|
|
|
|
}
|
2019-12-01 22:27:00 +03:00
|
|
|
|
2022-05-26 13:28:29 +03:00
|
|
|
bool knownTargetFormat = true;
|
|
|
|
|
2022-03-19 19:31:55 +03:00
|
|
|
if(targetFormat == Mimer::PDF)
|
|
|
|
{
|
|
|
|
Params.format = PrintParameters::PDF;
|
|
|
|
}
|
|
|
|
else if(targetFormat == Mimer::Postscript)
|
|
|
|
{
|
|
|
|
Params.format = PrintParameters::Postscript;
|
|
|
|
}
|
|
|
|
else if(targetFormat == Mimer::PWG)
|
|
|
|
{
|
|
|
|
Params.format = PrintParameters::PWG;
|
|
|
|
}
|
|
|
|
else if(targetFormat == Mimer::URF)
|
|
|
|
{
|
|
|
|
Params.format = PrintParameters::URF;
|
|
|
|
}
|
2022-05-26 13:28:29 +03:00
|
|
|
else
|
|
|
|
{
|
|
|
|
knownTargetFormat = false;
|
|
|
|
}
|
2022-03-19 19:31:55 +03:00
|
|
|
|
|
|
|
QSizeF size = PaperSizes[Params.paperSizeName.c_str()];
|
|
|
|
Params.paperSizeUnits = PrintParameters::Millimeters;
|
|
|
|
Params.paperSizeW = size.width();
|
|
|
|
Params.paperSizeH = size.height();
|
|
|
|
|
2021-06-26 14:42:54 +03:00
|
|
|
qDebug() << "Printing job" << o << jobAttrs;
|
2020-01-26 14:08:57 +03:00
|
|
|
|
2021-06-26 14:42:54 +03:00
|
|
|
QJsonValue PrinterResolutionRef = getAttrOrDefault(jobAttrs, "printer-resolution");
|
2022-03-26 18:35:21 +03:00
|
|
|
Params.hwResW = PrinterResolutionRef.toObject()["x"].toInt(Params.hwResW);
|
|
|
|
Params.hwResH = PrinterResolutionRef.toObject()["y"].toInt(Params.hwResH);
|
2020-05-05 21:36:01 +03:00
|
|
|
|
2022-03-26 18:35:21 +03:00
|
|
|
adjustRasterSettings(targetFormat, jobAttrs, Params);
|
2020-06-01 22:56:47 +03:00
|
|
|
|
2022-03-19 19:31:55 +03:00
|
|
|
Params.quality = getAttrOrDefault(jobAttrs, "print-quality").toInt();
|
2020-05-09 21:39:50 +03:00
|
|
|
|
2021-06-26 14:42:54 +03:00
|
|
|
QString PrintColorMode = getAttrOrDefault(jobAttrs, "print-color-mode").toString();
|
2022-03-19 19:31:55 +03:00
|
|
|
Params.colors = PrintColorMode.contains("color") ? 3 : PrintColorMode.contains("monochrome") ? 1 : Params.colors;
|
2020-05-05 21:36:01 +03:00
|
|
|
|
2021-06-26 14:42:54 +03:00
|
|
|
if(jobAttrs.contains("page-ranges"))
|
2020-09-23 21:14:33 +03:00
|
|
|
{
|
2021-06-26 14:42:54 +03:00
|
|
|
QJsonObject PageRanges = getAttrOrDefault(jobAttrs, "page-ranges").toObject();
|
2022-03-19 19:31:55 +03:00
|
|
|
Params.fromPage = PageRanges["low"].toInt();
|
|
|
|
Params.toPage = PageRanges["high"].toInt();
|
2021-11-15 23:50:48 +03:00
|
|
|
// Effected locally, unless it is Postscript which we cant't render
|
2022-03-19 19:31:55 +03:00
|
|
|
if(targetFormat != Mimer::Postscript)
|
2021-11-15 23:50:48 +03:00
|
|
|
{
|
|
|
|
jobAttrs.remove("page-ranges");
|
|
|
|
}
|
2020-06-07 16:27:27 +03:00
|
|
|
}
|
2020-06-06 15:59:44 +03:00
|
|
|
|
2020-06-13 18:56:28 +03:00
|
|
|
qDebug() << "Final op attributes:" << o;
|
2021-06-26 14:42:54 +03:00
|
|
|
qDebug() << "Final job attributes:" << jobAttrs;
|
2020-06-06 16:16:46 +03:00
|
|
|
|
2021-06-26 14:42:54 +03:00
|
|
|
IppMsg job = mk_msg(o, jobAttrs);
|
2021-12-14 22:01:52 +03:00
|
|
|
Bytestream contents = job.encode(IppMsg::PrintJob);
|
2020-09-23 21:14:33 +03:00
|
|
|
|
2022-03-06 19:16:07 +03:00
|
|
|
setBusyMessage(tr("Preparing"));
|
|
|
|
|
2022-03-19 19:31:55 +03:00
|
|
|
if((mimeType == targetFormat) && (targetFormat == Mimer::Postscript))
|
2022-03-06 19:16:07 +03:00
|
|
|
{ // Can't process Postscript
|
2021-08-28 23:16:26 +03:00
|
|
|
emit doJustUpload(filename, contents);
|
2020-06-05 21:41:45 +03:00
|
|
|
}
|
2022-05-29 16:54:11 +03:00
|
|
|
else if((mimeType != Mimer::SVG) && mimer->isImage(mimeType) && mimer->isImage(targetFormat))
|
2022-05-16 22:52:00 +03:00
|
|
|
{ // Just make sure the image is in the desired format (and jpeg baseline-encoded), don't resize locally
|
2022-05-26 12:57:16 +03:00
|
|
|
emit doPrintImageAsImage(filename, contents, targetFormat);
|
2022-03-06 19:16:07 +03:00
|
|
|
}
|
2022-05-26 13:28:29 +03:00
|
|
|
else if(knownTargetFormat) // Params.format can be trusted
|
2020-01-26 14:08:57 +03:00
|
|
|
{
|
2021-11-14 23:01:18 +03:00
|
|
|
QString Sides = getAttrOrDefault(jobAttrs, "sides").toString();
|
|
|
|
|
2021-03-06 14:59:47 +03:00
|
|
|
if(Sides=="two-sided-long-edge")
|
|
|
|
{
|
2022-03-19 19:31:55 +03:00
|
|
|
Params.duplex = true;
|
2021-03-06 14:59:47 +03:00
|
|
|
}
|
|
|
|
else if(Sides=="two-sided-short-edge")
|
|
|
|
{
|
2022-03-19 19:31:55 +03:00
|
|
|
Params.duplex = true;
|
|
|
|
Params.tumble = true;
|
2021-03-06 14:59:47 +03:00
|
|
|
}
|
|
|
|
|
2021-03-04 23:49:27 +03:00
|
|
|
if(mimeType == Mimer::PDF)
|
2020-05-13 20:53:44 +03:00
|
|
|
{
|
2022-03-19 19:31:55 +03:00
|
|
|
emit doConvertPdf(filename, contents, Params);
|
2020-05-13 20:53:44 +03:00
|
|
|
}
|
2021-06-12 13:45:58 +03:00
|
|
|
else if(mimeType == Mimer::Plaintext)
|
|
|
|
{
|
2022-05-02 22:10:03 +03:00
|
|
|
if(targetFormat == Mimer::Plaintext)
|
|
|
|
{
|
|
|
|
emit doFixupPlaintext(filename, contents);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
emit doConvertPlaintext(filename, contents, Params);
|
|
|
|
}
|
2021-06-12 13:45:58 +03:00
|
|
|
}
|
2021-03-04 23:49:27 +03:00
|
|
|
else if (Mimer::isImage(mimeType))
|
2020-05-13 20:53:44 +03:00
|
|
|
{
|
2022-05-16 22:52:00 +03:00
|
|
|
emit doConvertImage(filename, contents, Params, margins);
|
2020-05-13 20:53:44 +03:00
|
|
|
}
|
2021-03-06 14:59:47 +03:00
|
|
|
else if(Mimer::isOffice(mimeType))
|
|
|
|
{
|
2022-03-19 19:31:55 +03:00
|
|
|
emit doConvertOfficeDocument(filename, contents, Params);
|
2021-03-06 14:59:47 +03:00
|
|
|
}
|
2020-05-16 17:03:42 +03:00
|
|
|
else
|
|
|
|
{
|
|
|
|
emit convertFailed(tr("Cannot convert this file format"));
|
|
|
|
}
|
2020-01-26 14:08:57 +03:00
|
|
|
}
|
2022-05-26 13:28:29 +03:00
|
|
|
else
|
|
|
|
{
|
|
|
|
emit convertFailed(tr("Cannot convert this file format"));
|
|
|
|
}
|
2020-01-26 14:08:57 +03:00
|
|
|
|
|
|
|
return;
|
2019-12-01 22:27:00 +03:00
|
|
|
}
|
2019-12-08 15:55:56 +03:00
|
|
|
|
|
|
|
bool IppPrinter::getJobs() {
|
|
|
|
|
|
|
|
qDebug() << "getting jobs";
|
2019-12-12 22:53:46 +03:00
|
|
|
QJsonObject o = opAttrs();
|
2020-01-03 15:37:51 +03:00
|
|
|
o.insert("requested-attributes", QJsonObject {{"tag", IppMsg::Keyword}, {"value", "all"}});
|
2019-12-08 15:55:56 +03:00
|
|
|
|
|
|
|
IppMsg job = IppMsg(o, QJsonObject());
|
|
|
|
|
2021-08-28 23:16:26 +03:00
|
|
|
emit doGetJobs(job.encode(IppMsg::GetJobs));
|
2019-12-08 15:55:56 +03:00
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2019-12-12 22:53:46 +03:00
|
|
|
bool IppPrinter::cancelJob(qint32 jobId) {
|
|
|
|
|
2020-02-23 15:11:28 +03:00
|
|
|
qDebug() << "cancelling jobs";
|
2019-12-08 15:55:56 +03:00
|
|
|
|
2019-12-12 22:53:46 +03:00
|
|
|
QJsonObject o = opAttrs();
|
|
|
|
o.insert("job-id", QJsonObject {{"tag", IppMsg::Integer}, {"value", jobId}});
|
|
|
|
|
|
|
|
IppMsg job = IppMsg(o, QJsonObject());
|
|
|
|
|
2021-08-28 23:16:26 +03:00
|
|
|
emit doCancelJob(job.encode(IppMsg::CancelJob));
|
2019-12-12 22:53:46 +03:00
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
2020-01-03 18:36:24 +03:00
|
|
|
|
2022-05-16 21:29:53 +03:00
|
|
|
bool IppPrinter::identify() {
|
|
|
|
|
|
|
|
qDebug() << "identifying";
|
|
|
|
|
|
|
|
QJsonObject o = opAttrs();
|
|
|
|
|
|
|
|
IppMsg job = IppMsg(o, QJsonObject());
|
|
|
|
|
|
|
|
emit doCancelJob(job.encode(IppMsg::IdentifyPrinter));
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2021-06-28 21:15:21 +03:00
|
|
|
bool IppPrinter::correctSuffix()
|
|
|
|
{
|
2022-05-22 12:00:32 +03:00
|
|
|
for(QJsonValue u : _attrs["printer-uri-supported"].toObject()["value"].toArray())
|
2021-06-28 21:15:21 +03:00
|
|
|
{
|
|
|
|
QUrl url(u.toString());
|
|
|
|
if(url.path() == _url.path())
|
|
|
|
{
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
QStringList IppPrinter::suffixes()
|
|
|
|
{
|
|
|
|
QStringList res;
|
2022-05-22 12:00:32 +03:00
|
|
|
for(QJsonValue u : _attrs["printer-uri-supported"].toObject()["value"].toArray())
|
2021-06-28 21:15:21 +03:00
|
|
|
{
|
|
|
|
QUrl url(u.toString());
|
|
|
|
if(!res.contains(url.path()))
|
|
|
|
{
|
|
|
|
res.append(url.path());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
res.sort();
|
|
|
|
return res;
|
|
|
|
}
|
|
|
|
|
2020-01-03 18:36:24 +03:00
|
|
|
QUrl IppPrinter::httpUrl() {
|
2021-06-19 19:16:42 +03:00
|
|
|
qDebug() << _url;
|
2020-01-03 18:36:24 +03:00
|
|
|
QUrl url = _url;
|
2021-06-19 19:16:42 +03:00
|
|
|
if(url.scheme() == "ipps")
|
|
|
|
{
|
|
|
|
url.setScheme("https");
|
|
|
|
if(url.port() == -1) {
|
|
|
|
url.setPort(443);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
url.setScheme("http");
|
|
|
|
if(url.port() == -1) {
|
|
|
|
url.setPort(631);
|
|
|
|
}
|
2020-01-03 18:36:24 +03:00
|
|
|
}
|
|
|
|
return url;
|
|
|
|
}
|
|
|
|
|
2020-05-06 21:46:41 +03:00
|
|
|
void IppPrinter::setBusyMessage(QString msg)
|
|
|
|
{
|
|
|
|
_busyMessage = msg;
|
|
|
|
emit busyMessageChanged();
|
|
|
|
}
|
2020-05-09 21:39:50 +03:00
|
|
|
|
2020-06-03 21:42:18 +03:00
|
|
|
void IppPrinter::setProgress(qint64 sent, qint64 total)
|
|
|
|
{
|
|
|
|
if(total == 0)
|
|
|
|
return;
|
|
|
|
|
|
|
|
_progress = QString::number(100*sent/total);
|
|
|
|
_progress += "%";
|
|
|
|
emit progressChanged();
|
|
|
|
}
|
|
|
|
|
2022-05-15 22:21:32 +03:00
|
|
|
bool IppPrinter::isAllowedAddress(QUrl url)
|
|
|
|
{
|
|
|
|
bool allowed = ((url.host() == _url.host()) || Settings::instance()->allowExternalConnections());
|
|
|
|
qDebug() << url << " is allowed: " << allowed;
|
|
|
|
return allowed;
|
|
|
|
}
|
|
|
|
|
2021-07-14 16:07:55 +03:00
|
|
|
QJsonValue IppPrinter::getAttrOrDefault(QJsonObject jobAttrs, QString name, QString subkey)
|
2020-05-09 21:39:50 +03:00
|
|
|
{
|
2021-07-14 16:07:55 +03:00
|
|
|
if(subkey == "")
|
2020-05-09 21:39:50 +03:00
|
|
|
{
|
2021-07-14 16:07:55 +03:00
|
|
|
if(jobAttrs.contains(name))
|
|
|
|
{
|
|
|
|
return jobAttrs[name].toObject()["value"];
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
return _attrs[name+"-default"].toObject()["value"];
|
|
|
|
}
|
2020-05-09 21:39:50 +03:00
|
|
|
}
|
2021-07-14 16:07:55 +03:00
|
|
|
else
|
|
|
|
{
|
|
|
|
QJsonObject subObj = jobAttrs[subkey].toObject()["value"].toObject();
|
|
|
|
if(subObj.contains(name))
|
|
|
|
{
|
|
|
|
return subObj[name].toObject()["value"];
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
return _attrs[name+"-default"].toObject()["value"];
|
|
|
|
}
|
2020-05-09 21:39:50 +03:00
|
|
|
}
|
|
|
|
}
|
2020-06-13 13:35:51 +03:00
|
|
|
|
|
|
|
IppMsg IppPrinter::mk_msg(QJsonObject opAttrs, QJsonObject jobAttrs)
|
|
|
|
{
|
|
|
|
if(_attrs.contains("ipp-versions-supported") &&
|
|
|
|
_attrs["ipp-versions-supported"].toObject()["value"].toArray().contains("2.0"))
|
|
|
|
{
|
|
|
|
qDebug() << "TWO-POINT-ZERO";
|
|
|
|
return IppMsg(opAttrs, jobAttrs, 2, 0);
|
|
|
|
}
|
|
|
|
return IppMsg(opAttrs, jobAttrs);
|
|
|
|
}
|
2022-05-26 15:42:01 +03:00
|
|
|
|
|
|
|
void IppPrinter::resolveUrl(QUrl& url)
|
|
|
|
{
|
|
|
|
if(!IppDiscovery::instance()->resolve(url))
|
|
|
|
{ // If "proper" resolution fails, cheat...
|
|
|
|
QString host = url.host();
|
|
|
|
|
|
|
|
if(host.endsWith("."))
|
|
|
|
{
|
|
|
|
host.chop(1);
|
|
|
|
}
|
|
|
|
|
|
|
|
QString dnsSdName = _attrs["printer-dns-sd-name"].toObject()["value"].toString();
|
|
|
|
dnsSdName = dnsSdName.append(".local");
|
|
|
|
|
|
|
|
if(host.compare(dnsSdName, Qt::CaseInsensitive) == 0)
|
|
|
|
{ // This could be done unconditionally, but some might want their externally hosted stuff to work
|
|
|
|
url.setHost(_url.host());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|