Commit f91b21c7d4e99d32be8e0a180821af17c8150140
1 parent
cfd5147d
Preserve input PDF version on pages/split-pages (fixes #610)
Showing
71 changed files
with
63 additions
and
30 deletions
ChangeLog
| 1 | 1 | 2022-02-08 Jay Berkenbilt <ejb@ql.org> |
| 2 | 2 | |
| 3 | + * Bug fix: when splitting pages with --split-pages or selecting | |
| 4 | + pages with --pages, set the output PDF version to the maximum of | |
| 5 | + all the input PDF versions. This is a fix to QPDFJob. If you are | |
| 6 | + creating output PDF files yourself from multiple inputs, you will | |
| 7 | + need to code the same thing. The new PDFVersion object, its | |
| 8 | + updateIfGreater() method, and the new QPDF and QPDFWriter methods | |
| 9 | + described below make this very easy to do. Fixes #610. | |
| 10 | + | |
| 3 | 11 | * Add new class PDFVersion for more convenient comparison of PDF |
| 4 | 12 | version numbers from the %!PDF header. |
| 5 | 13 | |
| 6 | 14 | * Add QPDF::getVersionAsPDFVersion() to return the PDF version and |
| 7 | 15 | extension together as a PDFVersion object instead of a string. |
| 8 | 16 | |
| 17 | + * Add a QPDFWriter::setMinimumPDFVersion() that takes a PDFVersion | |
| 18 | + object. | |
| 19 | + | |
| 9 | 20 | 2022-02-06 Jay Berkenbilt <ejb@ql.org> |
| 10 | 21 | |
| 11 | 22 | * Pl_Buffer and QPDFWriter: add getBufferSharedPointer(), which | ... | ... |
TODO
include/qpdf/QPDFJob.hh
| ... | ... | @@ -26,6 +26,7 @@ |
| 26 | 26 | #include <qpdf/Constants.h> |
| 27 | 27 | #include <qpdf/QPDF.hh> |
| 28 | 28 | #include <qpdf/QPDFPageObjectHelper.hh> |
| 29 | +#include <qpdf/PDFVersion.hh> | |
| 29 | 30 | |
| 30 | 31 | #include <memory> |
| 31 | 32 | #include <string> |
| ... | ... | @@ -587,6 +588,7 @@ class QPDFJob |
| 587 | 588 | int flatten_annotations_required; |
| 588 | 589 | int flatten_annotations_forbidden; |
| 589 | 590 | bool generate_appearances; |
| 591 | + PDFVersion max_input_version; | |
| 590 | 592 | std::string min_version; |
| 591 | 593 | std::string force_version; |
| 592 | 594 | bool show_npages; | ... | ... |
include/qpdf/QPDFWriter.hh
| ... | ... | @@ -42,11 +42,11 @@ |
| 42 | 42 | #include <qpdf/QPDFObjectHandle.hh> |
| 43 | 43 | #include <qpdf/QPDFObjGen.hh> |
| 44 | 44 | #include <qpdf/QPDFXRefEntry.hh> |
| 45 | - | |
| 46 | 45 | #include <qpdf/Pl_Buffer.hh> |
| 47 | 46 | #include <qpdf/PointerHolder.hh> |
| 48 | 47 | #include <qpdf/Pipeline.hh> |
| 49 | 48 | #include <qpdf/Buffer.hh> |
| 49 | +#include <qpdf/PDFVersion.hh> | |
| 50 | 50 | |
| 51 | 51 | class QPDF; |
| 52 | 52 | class Pl_Count; |
| ... | ... | @@ -265,6 +265,8 @@ class QPDFWriter |
| 265 | 265 | // streams are used. |
| 266 | 266 | QPDF_DLL |
| 267 | 267 | void setMinimumPDFVersion(std::string const&, int extension_level = 0); |
| 268 | + QPDF_DLL | |
| 269 | + void setMinimumPDFVersion(PDFVersion const&); | |
| 268 | 270 | |
| 269 | 271 | // Force the PDF version of the output file to be a given version. |
| 270 | 272 | // Use of this function may create PDF files that will not work | ... | ... |
libqpdf/QPDFJob.cc
| ... | ... | @@ -2047,6 +2047,7 @@ QPDFJob::doProcessOnce( |
| 2047 | 2047 | { |
| 2048 | 2048 | fn(pdf.get(), password); |
| 2049 | 2049 | } |
| 2050 | + this->m->max_input_version.updateIfGreater(pdf->getVersionAsPDFVersion()); | |
| 2050 | 2051 | return pdf; |
| 2051 | 2052 | } |
| 2052 | 2053 | |
| ... | ... | @@ -3472,6 +3473,7 @@ QPDFJob::setWriterOptions(QPDF& pdf, QPDFWriter& w) |
| 3472 | 3473 | { |
| 3473 | 3474 | w.setObjectStreamMode(m->object_stream_mode); |
| 3474 | 3475 | } |
| 3476 | + w.setMinimumPDFVersion(this->m->max_input_version); | |
| 3475 | 3477 | if (! m->min_version.empty()) |
| 3476 | 3478 | { |
| 3477 | 3479 | std::string version; | ... | ... |
libqpdf/QPDFWriter.cc
| ... | ... | @@ -297,6 +297,15 @@ QPDFWriter::setMinimumPDFVersion(std::string const& version, |
| 297 | 297 | } |
| 298 | 298 | |
| 299 | 299 | void |
| 300 | +QPDFWriter::setMinimumPDFVersion(PDFVersion const& v) | |
| 301 | +{ | |
| 302 | + std::string version; | |
| 303 | + int extension_level; | |
| 304 | + v.getVersion(version, extension_level); | |
| 305 | + setMinimumPDFVersion(version, extension_level); | |
| 306 | +} | |
| 307 | + | |
| 308 | +void | |
| 300 | 309 | QPDFWriter::forcePDFVersion(std::string const& version, |
| 301 | 310 | int extension_level) |
| 302 | 311 | { | ... | ... |
manual/release-notes.rst
| ... | ... | @@ -148,6 +148,14 @@ For a detailed list of changes, please see the file |
| 148 | 148 | embedded NUL characters. Thanks to M. Holger for the |
| 149 | 149 | contribution. |
| 150 | 150 | |
| 151 | + - New ``PDFVersion`` class for representing a PDF version number | |
| 152 | + with the ability to compare and order PDF versions. Methods | |
| 153 | + ``QPDF::getVersionAsPDFVersion`` and a new version of | |
| 154 | + ``QPDFWriter::setMinimumPDFVersion`` use it. This makes it | |
| 155 | + easier to create an output file whose PDF version is the maximum | |
| 156 | + of the versions across all the input files that contributed to | |
| 157 | + it. | |
| 158 | + | |
| 151 | 159 | - The ``JSON`` object in the qpdf library has been enhanced to |
| 152 | 160 | include a parser and the ability to get values out of the |
| 153 | 161 | ``JSON`` object. Previously it was a write-only interface. Even |
| ... | ... | @@ -181,6 +189,10 @@ For a detailed list of changes, please see the file |
| 181 | 189 | - Some characters were not correctly translated from PDF doc |
| 182 | 190 | encoding to Unicode. |
| 183 | 191 | |
| 192 | + - When splitting or combining pages, ensure that all output files | |
| 193 | + have a PDF version greater than or equal to the maximum version | |
| 194 | + of all the input files. | |
| 195 | + | |
| 184 | 196 | 10.5.0: December 21, 2021 |
| 185 | 197 | - Packaging changes |
| 186 | 198 | ... | ... |
qpdf/qtest/qpdf/01_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/02_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/03_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/04_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/05_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/06_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/07_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/08_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/09_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/10_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/11_split-exp.zdf
No preview for this file type
qpdf/qtest/qpdf/direct-dr-out.pdf
qpdf/qtest/qpdf/dr-with-indirect-item-out.pdf
qpdf/qtest/qpdf/fields-pages-out.pdf
No preview for this file type
qpdf/qtest/qpdf/fields-split-1.pdf
No preview for this file type
qpdf/qtest/qpdf/fields-split-2.pdf
No preview for this file type
qpdf/qtest/qpdf/indirect-r-arg.out
| 1 | -checking indirect-r-arg.pdf | |
| 2 | 1 | WARNING: indirect-r-arg.pdf (object 1 0, offset 76): unknown token while reading object; treating as string |
| 3 | 2 | WARNING: indirect-r-arg.pdf (object 1 0, offset 62): expected dictionary key but found non-name object; inserting key /QPDFFake1 |
| 4 | 3 | WARNING: indirect-r-arg.pdf (object 1 0, offset 62): expected dictionary key but found non-name object; inserting key /QPDFFake2 |
| 4 | +checking indirect-r-arg.pdf | |
| 5 | 5 | PDF Version: 1.3 |
| 6 | 6 | File is not encrypted |
| 7 | 7 | File is not linearized | ... | ... |
qpdf/qtest/qpdf/job-json-copy-attachments.pdf
No preview for this file type
qpdf/qtest/qpdf/job-json-empty-input.pdf
No preview for this file type
qpdf/qtest/qpdf/job-json-underlay-overlay-password.pdf
No preview for this file type
qpdf/qtest/qpdf/labels-split-01-06.pdf
qpdf/qtest/qpdf/labels-split-07-11.pdf
qpdf/qtest/qpdf/merge-implicit-ranges.pdf
No preview for this file type
qpdf/qtest/qpdf/merge-multiple-labels.pdf
No preview for this file type
qpdf/qtest/qpdf/merge-three-files-1.pdf
No preview for this file type
qpdf/qtest/qpdf/merge-three-files-2.pdf
No preview for this file type
qpdf/qtest/qpdf/obj0-check.out
qpdf/qtest/qpdf/overlay-copy-annotations-p1.pdf
qpdf/qtest/qpdf/overlay-copy-annotations-p2.pdf
qpdf/qtest/qpdf/overlay-copy-annotations-p5.pdf
qpdf/qtest/qpdf/overlay-copy-annotations-p6.pdf
qpdf/qtest/qpdf/overlay-copy-annotations.pdf
qpdf/qtest/qpdf/remove-labels.pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-01.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-02.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-03.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-04.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-05.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-06.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-07.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-08.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-09.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-1
No preview for this file type
qpdf/qtest/qpdf/split-exp-1.pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-10.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-11.Pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-2
No preview for this file type
qpdf/qtest/qpdf/split-exp-3
No preview for this file type
qpdf/qtest/qpdf/split-exp-4
No preview for this file type
qpdf/qtest/qpdf/split-exp-group-01-05.pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-group-06-10.pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp-group-11-11.pdf
No preview for this file type
qpdf/qtest/qpdf/split-exp.zdf_01
qpdf/qtest/qpdf/split-exp.zdf_02
qpdf/qtest/qpdf/split-exp.zdf_03
qpdf/qtest/qpdf/split-exp.zdf_04
qpdf/qtest/qpdf/split-exp.zdf_05
qpdf/qtest/qpdf/split-exp.zdf_06
qpdf/qtest/qpdf/split-exp.zdf_07
qpdf/qtest/qpdf/split-exp.zdf_08
qpdf/qtest/qpdf/split-exp.zdf_09
qpdf/qtest/qpdf/split-exp.zdf_10
qpdf/qtest/qpdf/split-exp.zdf_11