1// Copyright (C) 2016 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3
4#ifndef QPDF_P_H
5#define QPDF_P_H
6
7//
8// W A R N I N G
9// -------------
10//
11// This file is not part of the Qt API. It exists purely as an
12// implementation detail. This header file may change from version to
13// version without notice, or even be removed.
14//
15// We mean it.
16//
17
18#include <QtGui/private/qtguiglobal_p.h>
19
20#ifndef QT_NO_PDF
21
22#include "QtCore/qlist.h"
23#include "QtCore/qstring.h"
24#include "QtCore/quuid.h"
25#include "private/qfontengine_p.h"
26#include "private/qfontsubset_p.h"
27#include "private/qpaintengine_p.h"
28#include "private/qstroker_p.h"
29#include "qpagelayout.h"
30#include "qpdfoutputintent.h"
31
32QT_BEGIN_NAMESPACE
33
34const char *qt_real_to_string(qreal val, char *buf);
35const char *qt_int_to_string(int val, char *buf);
36
37namespace QPdf {
38
39 class ByteStream
40 {
41 public:
42 // fileBacking means that ByteStream will buffer the contents on disk
43 // if the size exceeds a certain threshold. In this case, if a byte
44 // array was passed in, its contents may no longer correspond to the
45 // ByteStream contents.
46 explicit ByteStream(bool fileBacking = false);
47 explicit ByteStream(QByteArray *ba, bool fileBacking = false);
48 ~ByteStream();
49 ByteStream &operator <<(char chr);
50 ByteStream &operator <<(const char *str);
51 ByteStream &operator <<(const QByteArray &str);
52 ByteStream &operator <<(const ByteStream &src);
53 ByteStream &operator <<(qreal val);
54 ByteStream &operator <<(int val);
55 ByteStream &operator <<(uint val) { return (*this << int(val)); }
56 ByteStream &operator <<(qint64 val) { return (*this << int(val)); }
57 ByteStream &operator <<(const QPointF &p);
58 // Note that the stream may be invalidated by calls that insert data.
59 QIODevice *stream();
60 void clear();
61
62 static inline int maxMemorySize() { return 100000000; }
63 static inline int chunkSize() { return 10000000; }
64
65 private:
66 void prepareBuffer();
67
68 private:
69 QIODevice *dev;
70 QByteArray ba;
71 bool fileBackingEnabled;
72 bool fileBackingActive;
73 bool handleDirty;
74 };
75
76 enum PathFlags {
77 ClipPath,
78 FillPath,
79 StrokePath,
80 FillAndStrokePath
81 };
82 QByteArray generatePath(const QPainterPath &path, const QTransform &matrix, PathFlags flags);
83 QByteArray generateMatrix(const QTransform &matrix);
84 QByteArray generateDashes(const QPen &pen);
85 QByteArray patternForBrush(const QBrush &b);
86
87 struct Stroker {
88 Stroker();
89 void setPen(const QPen &pen, QPainter::RenderHints hints);
90 void strokePath(const QPainterPath &path);
91 ByteStream *stream;
92 bool first;
93 QTransform matrix;
94 bool cosmeticPen;
95 private:
96 QStroker basicStroker;
97 QDashStroker dashStroker;
98 QStrokerOps *stroker;
99 };
100
101 QByteArray ascii85Encode(const QByteArray &input);
102
103 const char *toHex(ushort u, char *buffer);
104 const char *toHex(uchar u, char *buffer);
105
106}
107
108
109class QPdfPage : public QPdf::ByteStream
110{
111public:
112 QPdfPage();
113
114 QList<uint> images;
115 QList<uint> graphicStates;
116 QList<uint> patterns;
117 QList<uint> fonts;
118 QList<uint> annotations;
119
120 void streamImage(int w, int h, uint object);
121
122 QSize pageSize;
123private:
124};
125
126class QPdfWriter;
127class QPdfEnginePrivate;
128
129class Q_GUI_EXPORT QPdfEngine : public QPaintEngine
130{
131 Q_DECLARE_PRIVATE(QPdfEngine)
132 friend class QPdfWriter;
133public:
134 // keep in sync with QPagedPaintDevice::PdfVersion and QPdfEnginePrivate::writeHeader()::mapping!
135 enum PdfVersion
136 {
137 Version_1_4,
138 Version_A1b,
139 Version_1_6,
140 Version_X4,
141 };
142
143 QPdfEngine();
144 explicit QPdfEngine(QPdfEnginePrivate &d);
145 ~QPdfEngine() {}
146
147 void setOutputFilename(const QString &filename);
148
149 void setResolution(int resolution);
150 int resolution() const;
151
152 void setPdfVersion(PdfVersion version);
153
154 void setDocumentXmpMetadata(const QByteArray &xmpMetadata);
155 QByteArray documentXmpMetadata() const;
156
157 void addFileAttachment(const QString &fileName, const QByteArray &data, const QString &mimeType);
158
159 // keep in sync with QPdfWriter
160 enum class ColorModel
161 {
162 RGB,
163 Grayscale,
164 CMYK,
165 Auto,
166 };
167
168 ColorModel colorModel() const;
169 void setColorModel(ColorModel model);
170
171 // reimplementations QPaintEngine
172 bool begin(QPaintDevice *pdev) override;
173 bool end() override;
174
175 void drawPoints(const QPointF *points, int pointCount) override;
176 void drawLines(const QLineF *lines, int lineCount) override;
177 void drawRects(const QRectF *rects, int rectCount) override;
178 void drawPolygon(const QPointF *points, int pointCount, PolygonDrawMode mode) override;
179 void drawPath (const QPainterPath & path) override;
180
181 void drawTextItem(const QPointF &p, const QTextItem &textItem) override;
182
183 void drawPixmap (const QRectF & rectangle, const QPixmap & pixmap, const QRectF & sr) override;
184 void drawImage(const QRectF &r, const QImage &pm, const QRectF &sr,
185 Qt::ImageConversionFlags flags = Qt::AutoColor) override;
186 void drawTiledPixmap (const QRectF & rectangle, const QPixmap & pixmap, const QPointF & point) override;
187
188 void drawHyperlink(const QRectF &r, const QUrl &url);
189
190 void updateState(const QPaintEngineState &state) override;
191
192 int metric(QPaintDevice::PaintDeviceMetric metricType) const;
193 Type type() const override;
194 // end reimplementations QPaintEngine
195
196 // Printer stuff...
197 bool newPage();
198
199 // Page layout stuff
200 void setPageLayout(const QPageLayout &pageLayout);
201 void setPageSize(const QPageSize &pageSize);
202 void setPageOrientation(QPageLayout::Orientation orientation);
203 void setPageMargins(const QMarginsF &margins, QPageLayout::Unit units = QPageLayout::Point);
204
205 QPageLayout pageLayout() const;
206
207 void setPen();
208 void setBrush();
209 void setupGraphicsState(QPaintEngine::DirtyFlags flags);
210
211private:
212 void updateClipPath(const QPainterPath & path, Qt::ClipOperation op);
213};
214
215class Q_GUI_EXPORT QPdfEnginePrivate : public QPaintEnginePrivate
216{
217 Q_DECLARE_PUBLIC(QPdfEngine)
218public:
219 QPdfEnginePrivate();
220 ~QPdfEnginePrivate();
221
222 inline uint requestObject() { return currentObject++; }
223
224 void writeHeader();
225 void writeTail();
226
227 int addImage(const QImage &image, bool *bitmap, bool lossless, qint64 serial_no);
228 int addConstantAlphaObject(int brushAlpha, int penAlpha = 255);
229 int addBrushPattern(const QTransform &matrix, bool *specifyColor, int *gStateObject);
230
231 void drawTextItem(const QPointF &p, const QTextItemInt &ti);
232
233 QTransform pageMatrix() const;
234
235 void newPage();
236
237 int currentObject;
238
239 QPdfPage* currentPage;
240 QPdf::Stroker stroker;
241
242 QPointF brushOrigin;
243 QBrush brush;
244 QPen pen;
245 QList<QPainterPath> clips;
246 bool clipEnabled;
247 bool allClipped;
248 bool hasPen;
249 bool hasBrush;
250 bool simplePen;
251 bool needsTransform;
252 qreal opacity;
253 QPdfEngine::PdfVersion pdfVersion;
254 QPdfEngine::ColorModel colorModel;
255
256 QHash<QFontEngine::FaceId, QFontSubset *> fonts;
257
258 QPaintDevice *pdev;
259
260 // the device the output is in the end streamed to.
261 QIODevice *outDevice;
262 bool ownsDevice;
263
264 // printer options
265 QString outputFileName;
266 QString title;
267 QString creator;
268 QUuid documentId = QUuid::createUuid();
269 bool embedFonts;
270 int resolution;
271 QPdfOutputIntent outputIntent;
272
273 // Page layout: size, orientation and margins
274 QPageLayout m_pageLayout;
275
276private:
277 int gradientBrush(const QBrush &b, const QTransform &matrix, int *gStateObject);
278 int generateGradientShader(const QGradient *gradient, const QTransform &matrix, bool alpha = false);
279 int generateLinearGradientShader(const QLinearGradient *lg, const QTransform &matrix, bool alpha);
280 int generateRadialGradientShader(const QRadialGradient *gradient, const QTransform &matrix, bool alpha);
281 struct ShadingFunctionResult
282 {
283 int function;
284 QPdfEngine::ColorModel colorModel;
285 void writeColorSpace(QPdf::ByteStream *stream) const;
286 };
287 ShadingFunctionResult createShadingFunction(const QGradient *gradient, int from, int to, bool reflect, bool alpha);
288
289 enum class ColorDomain {
290 Stroking,
291 NonStroking,
292 NonStrokingPattern,
293 };
294
295 QPdfEngine::ColorModel colorModelForColor(const QColor &color) const;
296 void writeColor(ColorDomain domain, const QColor &color);
297 void writeInfo(const QDateTime &date);
298 int writeXmpDocumentMetaData(const QDateTime &date);
299 int writeOutputIntent();
300 void writePageRoot();
301 void writeDestsRoot();
302 void writeAttachmentRoot();
303 void writeNamesRoot();
304 void writeFonts();
305 void embedFont(QFontSubset *font);
306 qreal calcUserUnit() const;
307
308 QList<int> xrefPositions;
309 QDataStream* stream;
310 int streampos;
311
312 enum class WriteImageOption
313 {
314 Monochrome,
315 Grayscale,
316 RGB,
317 CMYK,
318 };
319
320 int writeImage(const QByteArray &data, int width, int height, WriteImageOption option,
321 int maskObject, int softMaskObject, bool dct = false, bool isMono = false);
322 void writePage();
323
324 int addXrefEntry(int object, bool printostr = true);
325 void printString(QStringView string);
326 void xprintf(const char* fmt, ...);
327 inline void write(QByteArrayView data) {
328 stream->writeRawData(data.constData(), len: data.size());
329 streampos += data.size();
330 }
331
332 int writeCompressed(const char *src, int len);
333 inline int writeCompressed(const QByteArray &data) { return writeCompressed(src: data.constData(), len: data.size()); }
334 int writeCompressed(QIODevice *dev);
335
336 struct AttachmentInfo
337 {
338 AttachmentInfo (const QString &fileName, const QByteArray &data, const QString &mimeType)
339 : fileName(fileName), data(data), mimeType(mimeType) {}
340 QString fileName;
341 QByteArray data;
342 QString mimeType;
343 };
344
345 struct DestInfo
346 {
347 QString anchor;
348 uint pageObj;
349 QPointF coords;
350 };
351
352 // various PDF objects
353 int pageRoot, namesRoot, destsRoot, attachmentsRoot, catalog, info;
354 int graphicsState;
355 int patternColorSpaceRGB;
356 int patternColorSpaceGrayscale;
357 int patternColorSpaceCMYK;
358 QList<uint> pages;
359 QHash<qint64, uint> imageCache;
360 QHash<QPair<uint, uint>, uint > alphaCache;
361 QList<DestInfo> destCache;
362 QList<AttachmentInfo> fileCache;
363 QByteArray xmpDocumentMetadata;
364};
365
366QT_END_NAMESPACE
367
368#endif // QT_NO_PDF
369
370#endif // QPDF_P_H
371
372

Provided by KDAB

Privacy Policy
Learn to use CMake with our Intro Training
Find out more

source code of qtbase/src/gui/painting/qpdf_p.h