summaryrefslogtreecommitdiffstats
path: root/src/printsupport/kernel
diff options
context:
space:
mode:
authorJohn Layt <jlayt@kde.org>2014-01-20 17:59:57 +0100
committerThe Qt Project <gerrit-noreply@qt-project.org>2014-03-17 13:46:04 +0100
commitab42391cd0b4cb0be03d0083f4e0d2b039a85a19 (patch)
tree871f8f394d1a31d1c8264bfa5ff8efc89702bd9f /src/printsupport/kernel
parent4eb36ad5971240a9a934bef7be2c6297e092b797 (diff)
QPrintEngine - Switch Windows to QPlatformPrintDevice
Change the Windows QPrintEngine implementation to use the QPlatformPrintDevice to obtain device information, and use QPageSize to obtain page size conversions. A following change will use QPageLayout to store that page size. Change-Id: I990943e2b62ab6dab2c4d4a292c7ed7261beadf2 Reviewed-by: Lars Knoll <lars.knoll@digia.com>
Diffstat (limited to 'src/printsupport/kernel')
-rw-r--r--src/printsupport/kernel/qprintengine_win.cpp531
-rw-r--r--src/printsupport/kernel/qprintengine_win_p.h29
-rw-r--r--src/printsupport/kernel/qprinter.cpp14
3 files changed, 170 insertions, 404 deletions
diff --git a/src/printsupport/kernel/qprintengine_win.cpp b/src/printsupport/kernel/qprintengine_win.cpp
index c5f5057b14..6aec4919fd 100644
--- a/src/printsupport/kernel/qprintengine_win.cpp
+++ b/src/printsupport/kernel/qprintengine_win.cpp
@@ -50,6 +50,9 @@
#include <private/qfontengine_p.h>
#include <private/qpainter_p.h>
+#include <qpa/qplatformprintplugin.h>
+#include <qpa/qplatformprintersupport.h>
+
#include <qbitmap.h>
#include <qdebug.h>
#include <qvector.h>
@@ -67,164 +70,12 @@ QT_BEGIN_NAMESPACE
Q_GUI_EXPORT HBITMAP qt_pixmapToWinHBITMAP(const QPixmap &p, int hbitmapFormat = 0);
extern QPainterPath qt_regionToPath(const QRegion &region);
-Q_PRINTSUPPORT_EXPORT QSizeF qt_SizeFromUnitToMillimeter(const QSizeF &, QPrinter::Unit, double);
-Q_PRINTSUPPORT_EXPORT double qt_multiplierForUnit(QPrinter::Unit unit, int resolution);
// #define QT_DEBUG_DRAW
static void draw_text_item_win(const QPointF &_pos, const QTextItemInt &ti, HDC hdc,
bool convertToText, const QTransform &xform, const QPointF &topLeft);
-static const struct {
- int winSizeName;
- QPrinter::PaperSize qtSizeName;
-} dmMapping[] = {
- { DMPAPER_LETTER, QPrinter::Letter },
- { DMPAPER_LETTERSMALL, QPrinter::Letter },
- { DMPAPER_TABLOID, QPrinter::Tabloid },
- { DMPAPER_LEDGER, QPrinter::Ledger },
- { DMPAPER_LEGAL, QPrinter::Legal },
- { DMPAPER_EXECUTIVE, QPrinter::Executive },
- { DMPAPER_A3, QPrinter::A3 },
- { DMPAPER_A4, QPrinter::A4 },
- { DMPAPER_A4SMALL, QPrinter::A4 },
- { DMPAPER_A5, QPrinter::A5 },
- { DMPAPER_B4, QPrinter::B4 },
- { DMPAPER_B5, QPrinter::B5 },
- { DMPAPER_A4_PLUS, QPrinter::Folio },
- { DMPAPER_ENV_10, QPrinter::Comm10E },
- { DMPAPER_ENV_DL, QPrinter::DLE },
- { DMPAPER_ENV_C3, QPrinter::C5E },
- { DMPAPER_LETTER_EXTRA, QPrinter::Letter },
- { DMPAPER_LEGAL_EXTRA, QPrinter::Legal },
- { DMPAPER_TABLOID_EXTRA, QPrinter::Tabloid },
- { DMPAPER_A4_EXTRA, QPrinter::A4},
- { DMPAPER_LETTER_TRANSVERSE, QPrinter::Letter},
- { DMPAPER_A4_TRANSVERSE, QPrinter::A4},
- { DMPAPER_LETTER_EXTRA_TRANSVERSE, QPrinter::Letter },
- { DMPAPER_A_PLUS, QPrinter::A4 },
- { DMPAPER_B_PLUS, QPrinter::A3 },
- { DMPAPER_LETTER_PLUS, QPrinter::Letter },
- { DMPAPER_A5_TRANSVERSE, QPrinter::A5 },
- { DMPAPER_B5_TRANSVERSE, QPrinter::B5 },
- { DMPAPER_A3_EXTRA, QPrinter::A3 },
- { DMPAPER_A5_EXTRA, QPrinter::A5 },
- { DMPAPER_B5_EXTRA, QPrinter::B5 },
- { DMPAPER_A2, QPrinter::A2 },
- { DMPAPER_A3_TRANSVERSE, QPrinter::A3 },
- { DMPAPER_A3_EXTRA_TRANSVERSE,QPrinter::A3 },
- { 0, QPrinter::Custom }
-};
-
-// Return a list of printer paper sizes in millimeters with the corresponding dmPaperSize value
-static QList<QPair<QSizeF, int> > printerPaperSizes(const QString &printerName)
-{
- QList<QPair<QSizeF, int> > result;
- const wchar_t *name = reinterpret_cast<const wchar_t*>(printerName.utf16());
- DWORD paperNameCount = DeviceCapabilities(name, NULL, DC_PAPERS, NULL, NULL);
- if ((int)paperNameCount > 0) {
- // If they are not equal, then there seems to be a problem with the driver
- if (paperNameCount != DeviceCapabilities(name, NULL, DC_PAPERSIZE, NULL, NULL))
- return result;
- QScopedArrayPointer<wchar_t> papersNames(new wchar_t[paperNameCount]);
- paperNameCount = DeviceCapabilities(name, NULL, DC_PAPERS, papersNames.data(), NULL);
- result.reserve(paperNameCount);
- QScopedArrayPointer<POINT> paperSizes(new POINT[paperNameCount]);
- paperNameCount = DeviceCapabilities(name, NULL, DC_PAPERSIZE, (wchar_t *)paperSizes.data(), NULL);
- for (int i=0; i <(int)paperNameCount; i++)
- result.push_back(qMakePair(QSizeF(paperSizes[i].x / 10, paperSizes[i].y / 10), papersNames[i]));
- }
- return result;
-}
-
-// Find the best-matching printer paper for size in millimeters.
-static inline int findCustomPaperSize(const QSizeF &needlePt, const QString &printerName)
-{
- const QList<QPair<QSizeF, int> > sizes = printerPaperSizes(printerName);
- const qreal nw = needlePt.width();
- const qreal nh = needlePt.height();
- for (int i = 0; i < sizes.size(); ++i) {
- if (qAbs(nw - sizes.at(i).first.width()) <= 1 && qAbs(nh - sizes.at(i).first.height()) <= 1)
- return sizes.at(i).second;
- }
- return -1;
-}
-
-static inline void setDevModePaperFlags(DEVMODE *devMode, bool custom)
-{
- if (custom) {
- devMode->dmPaperSize = DMPAPER_USER;
- devMode->dmFields |= DM_PAPERLENGTH | DM_PAPERWIDTH;
- } else {
- devMode->dmFields &= ~(DM_PAPERLENGTH | DM_PAPERWIDTH);
- devMode->dmPaperLength = 0;
- devMode->dmPaperWidth = 0;
- }
-}
-
-QPrinter::PaperSize mapDevmodePaperSize(int s)
-{
- int i = 0;
- while ((dmMapping[i].winSizeName > 0) && (dmMapping[i].winSizeName != s))
- i++;
- return dmMapping[i].qtSizeName;
-}
-
-static int mapPaperSizeDevmode(QPrinter::PaperSize s)
-{
- int i = 0;
- while ((dmMapping[i].winSizeName > 0) && (dmMapping[i].qtSizeName != s))
- i++;
- return dmMapping[i].winSizeName;
-}
-
-static const struct {
- int winSourceName;
- QPrinter::PaperSource qtSourceName;
-} sources[] = {
- { DMBIN_UPPER, QPrinter::Upper }, // = DBMIN_ONLYONE
- { DMBIN_LOWER, QPrinter::Lower },
- { DMBIN_MIDDLE, QPrinter::Middle },
- { DMBIN_MANUAL, QPrinter::Manual },
- { DMBIN_ENVELOPE, QPrinter::Envelope },
- { DMBIN_ENVMANUAL, QPrinter::EnvelopeManual },
- { DMBIN_AUTO, QPrinter::Auto },
- { DMBIN_TRACTOR, QPrinter::Tractor },
- { DMBIN_SMALLFMT, QPrinter::SmallFormat },
- { DMBIN_LARGEFMT, QPrinter::LargeFormat },
- { DMBIN_LARGECAPACITY, QPrinter::LargeCapacity },
- { DMBIN_CASSETTE, QPrinter::Cassette },
- { DMBIN_FORMSOURCE, QPrinter::FormSource },
- { DMBIN_USER, QPrinter::CustomSource },
- { 0, (QPrinter::PaperSource) -1 }
-};
-
-static QPrinter::PaperSource mapDevmodePaperSource(int s)
-{
- int i = 0;
- while ((sources[i].winSourceName > 0) && (sources[i].winSourceName != s))
- i++;
- return sources[i].winSourceName ? sources[i].qtSourceName : (QPrinter::PaperSource) s;
-}
-
-static int mapPaperSourceDevmode(QPrinter::PaperSource s)
-{
- int i = 0;
- while ((sources[i].qtSourceName >= 0) && (sources[i].qtSourceName != s))
- i++;
- return sources[i].winSourceName ? sources[i].winSourceName : s;
-}
-
-static inline uint qwcsnlen(const wchar_t *str, uint maxlen)
-{
- uint length = 0;
- if (str) {
- while (length < maxlen && *str++)
- length++;
- }
- return length;
-}
-
QWin32PrintEngine::QWin32PrintEngine(QPrinter::PrinterMode mode)
: QAlphaPaintEngine(*(new QWin32PrintEnginePrivate),
PaintEngineFeatures(PrimitiveTransform
@@ -236,7 +87,10 @@ QWin32PrintEngine::QWin32PrintEngine(QPrinter::PrinterMode mode)
{
Q_D(QWin32PrintEngine);
d->mode = mode;
- d->queryDefault();
+ QPlatformPrinterSupport *ps = QPlatformPrinterSupportPlugin::get();
+ if (ps)
+ d->m_printDevice = ps->createDefaultPrintDevice();
+ d->m_pageSize = d->m_printDevice.defaultPageSize();
d->initialize();
}
@@ -1035,11 +889,6 @@ void QWin32PrintEngine::drawPolygon(const QPointF *points, int pointCount, Polyg
d->has_brush = has_brush;
}
-void QWin32PrintEnginePrivate::queryDefault()
-{
- QWin32PrintEngine::queryDefaultPrinter(name);
-}
-
QWin32PrintEnginePrivate::~QWin32PrintEnginePrivate()
{
if (hdc)
@@ -1055,12 +904,12 @@ void QWin32PrintEnginePrivate::initialize()
Q_ASSERT(!devMode);
Q_ASSERT(!pInfo);
- if (name.isEmpty())
+ if (!m_printDevice.isValid())
return;
txop = QTransform::TxNone;
- bool ok = OpenPrinter((LPWSTR)name.utf16(), (LPHANDLE)&hPrinter, 0);
+ bool ok = OpenPrinter((LPWSTR)m_printDevice.id().utf16(), (LPHANDLE)&hPrinter, 0);
if (!ok) {
qErrnoWarning("QWin32PrintEngine::initialize: OpenPrinter failed");
return;
@@ -1086,7 +935,7 @@ void QWin32PrintEnginePrivate::initialize()
}
devMode = pInfo->pDevMode;
- hdc = CreateDC(NULL, reinterpret_cast<const wchar_t *>(name.utf16()), 0, devMode);
+ hdc = CreateDC(NULL, reinterpret_cast<const wchar_t *>(m_printDevice.id().utf16()), 0, devMode);
Q_ASSERT(hPrinter);
Q_ASSERT(pInfo);
@@ -1094,6 +943,7 @@ void QWin32PrintEnginePrivate::initialize()
if (devMode) {
num_copies = devMode->dmCopies;
devMode->dmCollate = DMCOLLATE_TRUE;
+ updatePageSize();
}
initHDC();
@@ -1208,31 +1058,6 @@ void QWin32PrintEnginePrivate::release()
devMode = 0;
}
-QList<QVariant> QWin32PrintEnginePrivate::queryResolutions() const
-{
- // Read the supported resolutions of the printer.
- QList<QVariant> list;
-
- DWORD numRes = DeviceCapabilities(reinterpret_cast<const wchar_t *>(name.utf16()), NULL,
- DC_ENUMRESOLUTIONS, 0, 0);
- if (numRes == (DWORD)-1)
- return list;
-
- LONG *enumRes = (LONG*)malloc(numRes * 2 * sizeof(LONG));
- DWORD errRes = DeviceCapabilities(reinterpret_cast<const wchar_t *>(name.utf16()), NULL,
- DC_ENUMRESOLUTIONS, (LPWSTR)enumRes, 0);
-
- if (errRes == (DWORD)-1) {
- qErrnoWarning("QWin32PrintEngine::queryResolutions: DeviceCapabilities failed");
- return list;
- }
-
- for (uint i=0; i<numRes; ++i)
- list.append(int(enumRes[i * 2]));
-
- return list;
-}
-
void QWin32PrintEnginePrivate::doReinit()
{
if (state == QPrinter::Active) {
@@ -1364,74 +1189,56 @@ void QWin32PrintEngine::setProperty(PrintEnginePropertyKey key, const QVariant &
}
break;
- case PPK_PaperSize:
+ case PPK_PageSize: {
if (!d->devMode)
break;
- d->devMode->dmPaperSize = mapPaperSizeDevmode(QPrinter::PaperSize(value.toInt()));
- d->has_custom_paper_size = (QPrinter::PaperSize(value.toInt()) == QPrinter::Custom);
- setDevModePaperFlags(d->devMode, d->has_custom_paper_size);
- d->doReinit();
+ const QPageSize pageSize = QPageSize(QPageSize::PageSizeId(value.toInt()));
+ if (pageSize.isValid()) {
+ d->setPageSize(pageSize);
+ d->doReinit();
+ }
break;
+ }
- case PPK_PaperName:
- {
- if (!d->devMode)
- break;
- const wchar_t *name = reinterpret_cast<const wchar_t*>(d->name.utf16());
- DWORD size = DeviceCapabilities(name, NULL, DC_PAPERNAMES, NULL, NULL);
- if ((int)size > 0) {
- QScopedArrayPointer<wchar_t> paperNames(new wchar_t[size*64]);
- if (size != DeviceCapabilities(name, NULL, DC_PAPERNAMES, paperNames.data(), NULL))
- break;
- int paperPos = -1;
- for (int i = 0; i < (int)size; ++i) {
- wchar_t *copyOfPaper = paperNames.data() + (i * 64);
- if (value.toString() == QString::fromWCharArray(copyOfPaper, qwcsnlen(copyOfPaper, 64))) {
- paperPos = i;
- break;
- }
- }
- size = DeviceCapabilities(name, NULL, DC_PAPERS, NULL, NULL);
- if ((int)size > 0) {
- QScopedArrayPointer<wchar_t> papers(new wchar_t[size]);
- size = DeviceCapabilities(name, NULL, DC_PAPERS, papers.data(), NULL);
- QScopedArrayPointer<POINT> paperSizes(new POINT[size]);
- DWORD paperNameCount = DeviceCapabilities(name, NULL, DC_PAPERSIZE, (wchar_t *)paperSizes.data(), NULL);
- if (paperNameCount == size) {
- const double multiplier = qt_multiplierForUnit(QPrinter::Millimeter, d->resolution);
- d->paper_size = QSizeF((paperSizes[paperPos].x / 10.0) * multiplier, (paperSizes[paperPos].y / 10.0) * multiplier);
- // Our sizes may not match the paper name's size exactly
- // So we treat it as custom so we know the paper size is correct
- d->has_custom_paper_size = true;
- d->devMode->dmPaperSize = papers[paperPos];
- setDevModePaperFlags(d->devMode, false);
- d->doReinit();
- }
- }
- }
+ case PPK_PaperName: {
+ if (!d->devMode)
+ break;
+ // Get the named page size from the printer if supported
+ const QPageSize pageSize = d->m_printDevice.supportedPageSize(value.toString());
+ if (pageSize.isValid()) {
+ d->setPageSize(pageSize);
+ d->doReinit();
}
break;
- case PPK_PaperSource:
- {
- if (!d->devMode)
- break;
- int dmMapped = DMBIN_AUTO;
-
- QList<QVariant> v = property(PPK_PaperSources).toList();
- if (v.contains(value))
- dmMapped = mapPaperSourceDevmode(QPrinter::PaperSource(value.toInt()));
+ }
- d->devMode->dmDefaultSource = dmMapped;
- d->doReinit();
+ case PPK_PaperSource: {
+ if (!d->devMode)
+ break;
+ QPrint::InputSlotId inputSlotId = QPrint::InputSlotId(value.toInt());
+ foreach (const QPrint::InputSlot &inputSlot, d->m_printDevice.supportedInputSlots()) {
+ if (inputSlot.id == inputSlotId) {
+ d->devMode->dmDefaultSource = inputSlot.windowsId;
+ d->doReinit();
+ break;
+ }
}
break;
+ }
- case PPK_PrinterName:
- d->name = value.toString();
- if (d->name.isEmpty())
- d->queryDefault();
- d->initialize();
+ case PPK_PrinterName: {
+ QString id = value.toString();
+ const QPlatformPrinterSupport *ps = QPlatformPrinterSupportPlugin::get();
+ if (!ps)
+ return;
+ QPrintDevice printDevice = ps->createPrintDevice(id.isEmpty() ? ps->defaultPrintDeviceId() : id);
+ if (printDevice.isValid()) {
+ d->m_printDevice = printDevice;
+ // TODO Do we need to check if the page size is valid on new printer?
+ d->initialize();
+ }
break;
+ }
case PPK_Resolution:
{
@@ -1442,33 +1249,26 @@ void QWin32PrintEngine::setProperty(PrintEnginePropertyKey key, const QVariant &
}
break;
- case PPK_WindowsPageSize:
+ case PPK_WindowsPageSize: {
if (!d->devMode)
break;
- d->has_custom_paper_size = false;
- d->devMode->dmPaperSize = value.toInt();
- setDevModePaperFlags(d->devMode, d->has_custom_paper_size);
- d->doReinit();
+ const QPageSize pageSize = QPageSize(QPageSize::id(value.toInt()));
+ if (pageSize.isValid()) {
+ d->setPageSize(pageSize);
+ d->doReinit();
+ break;
+ }
break;
+ }
- case PPK_CustomPaperSize:
- {
- d->has_custom_paper_size = true;
- d->paper_size = value.toSizeF();
+ case PPK_CustomPaperSize: {
if (!d->devMode)
break;
- const QSizeF sizeMM = qt_SizeFromUnitToMillimeter(d->paper_size, QPrinter::Point, d->resolution);
- const int match = findCustomPaperSize(sizeMM, d->name);
- setDevModePaperFlags(d->devMode, (match >= 0) ? false : true);
- if (match >= 0) {
- d->devMode->dmPaperSize = match;
- if (d->devMode->dmOrientation != DMORIENT_PORTRAIT)
- qSwap(d->paper_size.rwidth(), d->paper_size.rheight());
- } else {
- d->devMode->dmPaperLength = qRound(sizeMM.height() * 10.0);
- d->devMode->dmPaperWidth = qRound(sizeMM.width() * 10.0);
+ const QPageSize pageSize = QPageSize(value.toSizeF(), QPageSize::Point);
+ if (pageSize.isValid()) {
+ d->setPageSize(pageSize);
+ d->doReinit();
}
- d->doReinit();
break;
}
@@ -1587,16 +1387,8 @@ QVariant QWin32PrintEngine::property(PrintEnginePropertyKey key) const
}
break;
- case PPK_PaperSize:
- if (d->has_custom_paper_size) {
- value = QPrinter::Custom;
- } else {
- if (!d->devMode) {
- value = QPrinter::A4;
- } else {
- value = mapDevmodePaperSize(d->devMode->dmPaperSize);
- }
- }
+ case PPK_PageSize:
+ value = d->m_pageSize.id();
break;
case PPK_PaperRect:
@@ -1610,88 +1402,57 @@ QVariant QWin32PrintEngine::property(PrintEnginePropertyKey key) const
break;
case PPK_PaperName:
- if (!d->devMode) {
- value = QLatin1String("A4");
- } else {
- const wchar_t *name = reinterpret_cast<const wchar_t*>(d->name.utf16());
- DWORD size = DeviceCapabilities(name, NULL, DC_PAPERS, NULL, NULL);
- int paperSizePos = -1;
- if ((int)size > 0) {
- QScopedArrayPointer<wchar_t> papers(new wchar_t[size]);
- if (size != DeviceCapabilities(name, NULL, DC_PAPERS, papers.data(), NULL))
- break;
- for (int i=0;i<(int)size;i++) {
- if (papers[i] == d->devMode->dmPaperSize) {
- paperSizePos = i;
- break;
- }
- }
- }
- if (paperSizePos != -1) {
- size = DeviceCapabilities(name, NULL, DC_PAPERNAMES, NULL, NULL);
- if ((int)size > 0) {
- QScopedArrayPointer<wchar_t> paperNames(new wchar_t[size*64]);
- size = DeviceCapabilities(name, NULL, DC_PAPERNAMES, paperNames.data(), NULL);
- wchar_t *copyOfPaper = paperNames.data() + (paperSizePos * 64);
- value = QString::fromWCharArray(copyOfPaper, qwcsnlen(copyOfPaper, 64));
- }
- }
- }
+ value = d->m_pageSize.name();
break;
case PPK_PaperSource:
if (!d->devMode) {
- value = QPrinter::Auto;
+ value = d->m_printDevice.defaultInputSlot().id;
} else {
- value = mapDevmodePaperSource(d->devMode->dmDefaultSource);
+ value = QPrint::Auto;
+ foreach (const QPrint::InputSlot inputSlot, d->m_printDevice.supportedInputSlots()) {
+ if (inputSlot.windowsId == d->devMode->dmDefaultSource) {
+ value = inputSlot.id;
+ break;
+ }
+ }
}
break;
case PPK_PrinterName:
- value = d->name;
+ value = d->m_printDevice.id();
break;
case PPK_Resolution:
- if (d->resolution || !d->name.isEmpty())
+ if (d->resolution || d->m_printDevice.isValid())
value = d->resolution;
break;
- case PPK_SupportedResolutions:
- value = d->queryResolutions();
+ case PPK_SupportedResolutions: {
+ QList<QVariant> list;
+ foreach (int resolution, d->m_printDevice.supportedResolutions())
+ list << resolution;
+ value = list;
break;
+ }
case PPK_WindowsPageSize:
- if (!d->devMode) {
- value = -1;
- } else {
- value = d->devMode->dmPaperSize;
- }
+ value = d->m_pageSize.windowsId();
break;
- case PPK_PaperSources:
- {
- int available = DeviceCapabilities((const wchar_t *)d->name.utf16(), NULL, DC_BINS, 0, d->devMode);
-
- if (available <= 0)
- break;
-
- wchar_t *data = new wchar_t[available];
- int count = DeviceCapabilities((const wchar_t *)d->name.utf16(), NULL, DC_BINS, data, d->devMode);
-
- QList<QVariant> out;
- for (int i=0; i<count; ++i) {
- QPrinter::PaperSource src = mapDevmodePaperSource(data[i]);
- if (src != -1)
- out << (int) src;
- }
- value = out;
-
- delete [] data;
- }
+ case PPK_PaperSources: {
+ QList<QVariant> out;
+ foreach (const QPrint::InputSlot inputSlot, d->m_printDevice.supportedInputSlots())
+ out << inputSlot.id;
+ value = out;
break;
+ }
case PPK_CustomPaperSize:
- value = d->paper_size;
+ if (property(PPK_Orientation) == QPrinter::Landscape)
+ value = d->m_pageSize.sizePoints().transposed();
+ else
+ value = d->m_pageSize.sizePoints();
break;
case PPK_PageMargins:
@@ -1733,33 +1494,11 @@ void QWin32PrintEngine::releaseDC(HDC) const
}
-void QWin32PrintEngine::queryDefaultPrinter(QString &name)
-{
- /* Read the default printer name, driver and port with the intuitive function
- * Strings "windows" and "device" are specified in the MSDN under EnumPrinters()
- */
- QString noPrinters(QLatin1String("qt_no_printers"));
- wchar_t buffer[256];
- GetProfileString(L"windows", L"device",
- reinterpret_cast<const wchar_t *>(noPrinters.utf16()),
- buffer, 256);
- QString output = QString::fromWCharArray(buffer);
- if (output.isEmpty() || output == noPrinters) // no printers
- return;
-
- QStringList info = output.split(QLatin1Char(','));
- int infoSize = info.size();
- if (infoSize > 0) {
- if (name.isEmpty())
- name = info.at(0);
- }
-}
-
HGLOBAL *QWin32PrintEngine::createGlobalDevNames()
{
Q_D(QWin32PrintEngine);
- int size = sizeof(DEVNAMES) + d->name.length() * 2 + 2;
+ int size = sizeof(DEVNAMES) + d->m_printDevice.id().length() * 2 + 2;
HGLOBAL *hGlobal = (HGLOBAL *) GlobalAlloc(GMEM_MOVEABLE, size);
DEVNAMES *dn = (DEVNAMES*) GlobalLock(hGlobal);
@@ -1767,7 +1506,7 @@ HGLOBAL *QWin32PrintEngine::createGlobalDevNames()
dn->wDeviceOffset = sizeof(DEVNAMES) / sizeof(wchar_t);
dn->wOutputOffset = 0;
- memcpy((ushort*)dn + dn->wDeviceOffset, d->name.utf16(), d->name.length() * 2 + 2);
+ memcpy((ushort*)dn + dn->wDeviceOffset, d->m_printDevice.id().utf16(), d->m_printDevice.id().length() * 2 + 2);
dn->wDefault = 0;
GlobalUnlock(hGlobal);
@@ -1779,7 +1518,10 @@ void QWin32PrintEngine::setGlobalDevMode(HGLOBAL globalDevNames, HGLOBAL globalD
Q_D(QWin32PrintEngine);
if (globalDevNames) {
DEVNAMES *dn = (DEVNAMES*) GlobalLock(globalDevNames);
- d->name = QString::fromWCharArray((wchar_t*)(dn) + dn->wDeviceOffset);
+ QString id = QString::fromWCharArray((wchar_t*)(dn) + dn->wDeviceOffset);
+ QPlatformPrinterSupport *ps = QPlatformPrinterSupportPlugin::get();
+ if (ps)
+ d->m_printDevice = ps->createPrintDevice(id.isEmpty() ? ps->defaultPrintDeviceId() : id);
GlobalUnlock(globalDevNames);
}
@@ -1788,12 +1530,12 @@ void QWin32PrintEngine::setGlobalDevMode(HGLOBAL globalDevNames, HGLOBAL globalD
d->release();
d->globalDevMode = globalDevMode;
d->devMode = dm;
- d->hdc = CreateDC(NULL, reinterpret_cast<const wchar_t *>(d->name.utf16()), 0, dm);
+ d->hdc = CreateDC(NULL, reinterpret_cast<const wchar_t *>(d->m_printDevice.id().utf16()), 0, dm);
d->num_copies = d->devMode->dmCopies;
- d->updateCustomPaperSize();
+ d->updatePageSize();
- if (!OpenPrinter((wchar_t*)d->name.utf16(), &d->hPrinter, 0))
+ if (!OpenPrinter((wchar_t*)d->m_printDevice.id().utf16(), &d->hPrinter, 0))
qWarning("QPrinter: OpenPrinter() failed after reading DEVMODE.");
}
@@ -1807,6 +1549,54 @@ HGLOBAL QWin32PrintEngine::globalDevMode()
return d->globalDevMode;
}
+
+void QWin32PrintEnginePrivate::setPageSize(const QPageSize &pageSize)
+{
+ if (!pageSize.isValid())
+ return;
+
+ // Use the printer page size if supported
+ QPageSize printerPageSize = m_printDevice.supportedPageSize(pageSize);
+ m_pageSize = printerPageSize.isValid() ? printerPageSize : pageSize;
+
+ if (devMode->dmOrientation == DMORIENT_LANDSCAPE)
+ paper_size = pageSize.size(QPage::Point).transposed();
+ else
+ paper_size = pageSize.size(QPage::Point);
+
+ // Setup if Windows custom size, i.e. not a known Windows ID
+ if (printerPageSize.isValid()) {
+ has_custom_paper_size = false;
+ devMode->dmPaperSize = m_pageSize.windowsId();
+ devMode->dmFields &= ~(DM_PAPERLENGTH | DM_PAPERWIDTH);
+ devMode->dmPaperWidth = 0;
+ devMode->dmPaperLength = 0;
+ } else {
+ has_custom_paper_size = true;
+ devMode->dmPaperSize = DMPAPER_USER;
+ devMode->dmFields |= DM_PAPERLENGTH | DM_PAPERWIDTH;
+ // Size in tenths of a millimeter
+ const QSizeF sizeMM = m_pageSize.size(QPage::Millimeter);
+ devMode->dmPaperWidth = qRound(sizeMM.width() * 10.0);
+ devMode->dmPaperLength = qRound(sizeMM.height() * 10.0);
+ }
+}
+
+// Called by print dialogs after devMode updated with new page size
+// Know devMode->dmPaperSize is valid, refresh QPageSize to match
+void QWin32PrintEnginePrivate::updatePageSize()
+{
+ if (devMode->dmPaperSize >= DMPAPER_USER) {
+ // Is a custom size
+ QPageSize pageSize = QPageSize(QSizeF(devMode->dmPaperWidth / 10.0f, devMode->dmPaperLength / 10.0f),
+ QPage::Millimeter);
+ setPageSize(pageSize);
+ } else {
+ // Is a supported size
+ setPageSize(QPageSize(QPageSize::id(devMode->dmPaperSize)));
+ }
+}
+
static void draw_text_item_win(const QPointF &pos, const QTextItemInt &ti, HDC hdc,
bool convertToText, const QTransform &xform, const QPointF &topLeft)
{
@@ -1922,27 +1712,6 @@ static void draw_text_item_win(const QPointF &pos, const QTextItemInt &ti, HDC h
SelectObject(hdc, old_font);
}
-void QWin32PrintEnginePrivate::updateCustomPaperSize()
-{
- const uint paperSize = devMode->dmPaperSize;
- const double multiplier = qt_multiplierForUnit(QPrinter::Millimeter, resolution);
- has_custom_paper_size = false;
- if (paperSize == DMPAPER_USER) {
- has_custom_paper_size = true;
- paper_size = QSizeF((devMode->dmPaperWidth / 10.0) * multiplier, (devMode->dmPaperLength / 10.0) * multiplier);
- } else if (mapDevmodePaperSize(paperSize) == QPrinter::Custom) {
- has_custom_paper_size = true;
- const QList<QPair<QSizeF, int> > paperSizes = printerPaperSizes(name);
- for (int i=0; i<paperSizes.size(); i++) {
- if ((uint)paperSizes.at(i).second == paperSize) {
- paper_size = paperSizes.at(i).first * multiplier;
- has_custom_paper_size = false;
- break;
- }
- }
- }
-}
-
QT_END_NAMESPACE
#endif // QT_NO_PRINTER
diff --git a/src/printsupport/kernel/qprintengine_win_p.h b/src/printsupport/kernel/qprintengine_win_p.h
index a749d9be42..61bf63346b 100644
--- a/src/printsupport/kernel/qprintengine_win_p.h
+++ b/src/printsupport/kernel/qprintengine_win_p.h
@@ -58,10 +58,11 @@
#ifndef QT_NO_PRINTER
#include <QtGui/qpaintengine.h>
+#include <QtGui/qpagelayout.h>
#include <QtPrintSupport/QPrintEngine>
#include <QtPrintSupport/QPrinter>
-#include <QtPrintSupport/QPrinterInfo>
#include <private/qpaintengine_alpha_p.h>
+#include <private/qprintdevice_p.h>
#include <QtCore/qt_windows.h>
QT_BEGIN_NAMESPACE
@@ -105,7 +106,10 @@ public:
HDC getDC() const;
void releaseDC(HDC) const;
- static void queryDefaultPrinter(QString &name);
+ /* Used by print/page setup dialogs */
+ void setGlobalDevMode(HGLOBAL globalDevNames, HGLOBAL globalDevMode);
+ HGLOBAL *createGlobalDevNames();
+ HGLOBAL globalDevMode();
private:
friend class QPrintDialog;
@@ -137,10 +141,6 @@ public:
~QWin32PrintEnginePrivate();
- /* Reads the default printer name and its driver (printerProgram) into
- the engines private data. */
- void queryDefault();
-
/* Initializes the printer data based on the current printer name. This
function creates a DEVMODE struct, HDC and a printer handle. If these
structures are already in use, they are freed using release
@@ -155,10 +155,6 @@ public:
etc and resets the corresponding members to 0. */
void release();
- /* Queries the resolutions for the current printer, and returns them
- in a list. */
- QList<QVariant> queryResolutions() const;
-
/* Resets the DC with changes in devmode. If the printer is active
this function only sets the reinit variable to true so it
is handled in the next begin or newpage. */
@@ -176,12 +172,14 @@ public:
void fillPath_dev(const QPainterPath &path, const QColor &color);
void strokePath_dev(const QPainterPath &path, const QColor &color, qreal width);
+ void setPageSize(const QPageSize &pageSize);
+ void updatePageSize();
+
void updateOrigin();
void initDevRects();
void setPageMargins(int margin_left, int margin_top, int margin_right, int margin_bottom);
QRect getPageMargins() const;
- void updateCustomPaperSize();
// Windows GDI printer references.
HANDLE hPrinter;
@@ -195,8 +193,8 @@ public:
QPrinter::PrinterMode mode;
- // Printer info
- QString name;
+ // Print Device
+ QPrintDevice m_printDevice;
// Document info
QString docName;
@@ -206,6 +204,9 @@ public:
QPrinter::PrinterState state;
int resolution;
+ // Page Layout
+ QPageSize m_pageSize;
+
// This QRect is used to store the exact values
// entered into the PageSetup Dialog because those are
// entered in mm but are since converted to device coordinates.
@@ -243,7 +244,7 @@ public:
QColor brush_color;
QPen pen;
QColor pen_color;
- QSizeF paper_size;
+ QSizeF paper_size; // In points
QTransform painterMatrix;
QTransform matrix;
diff --git a/src/printsupport/kernel/qprinter.cpp b/src/printsupport/kernel/qprinter.cpp
index 878dac60d5..9e10f5c636 100644
--- a/src/printsupport/kernel/qprinter.cpp
+++ b/src/printsupport/kernel/qprinter.cpp
@@ -151,15 +151,11 @@ Q_PRINTSUPPORT_EXPORT QSizeF qt_printerPaperSize(QPrinter::Orientation orientati
QPrinter::Unit unit,
int resolution)
{
- int width_index = 0;
- int height_index = 1;
- if (orientation == QPrinter::Landscape) {
- width_index = 1;
- height_index = 0;
- }
- const qreal multiplier = qt_multiplierForUnit(unit, resolution);
- return QSizeF((qt_paperSizes[paperSize][width_index] * 72 / 25.4) / multiplier,
- (qt_paperSizes[paperSize][height_index] * 72 / 25.4) / multiplier);
+ QPageSize pageSize = QPageSize(QPageSize::PageSizeId(paperSize));
+ if (orientation == QPrinter::Landscape)
+ return pageSize.size(QPage::Unit(unit), resolution).transposed();
+ else
+ return pageSize.size(QPage::Unit(unit), resolution);
}
QPrinterInfo QPrinterPrivate::findValidPrinter(const QPrinterInfo &printer)