Commit 2e7ee23bf63da6de221737907bcc6fa8526c3fda
1 parent
4cded108
Add QPDFPageDocumentHelper and QPDFPageObjectHelper
This is the beginning of higher-level API support using helper classes. The goal is to be able to add more helpers without continuing to pollute QPDF's and QPDFObjectHandle's public interfaces.
Showing
10 changed files
with
546 additions
and
107 deletions
ChangeLog
| 1 | +2018-06-20 Jay Berkenbilt <ejb@ql.org> | |
| 2 | + | |
| 3 | + * Added new classes QPDFPageDocumentHelper and QPDFPageObjctHelper | |
| 4 | + for page-level API functions. These classes introduce a new API | |
| 5 | + pattern of document helpers and object helpers in qpdf. The helper | |
| 6 | + classes provide a higher level API for working with certain types | |
| 7 | + of structural features of PDF while still staying true to qpdf's | |
| 8 | + philosophy of not isolating the user from the underlying | |
| 9 | + structure. Please see the chapter in the documentation entitled | |
| 10 | + "Design and Library Notes" for additional discussion. | |
| 11 | + | |
| 1 | 12 | 2018-06-19 Jay Berkenbilt <ejb@ql.org> |
| 2 | 13 | |
| 3 | 14 | * New QPDFObject::Rectangle class will convert to and from arrays | ... | ... |
include/qpdf/QPDF.hh
| ... | ... | @@ -452,15 +452,17 @@ class QPDF |
| 452 | 452 | void optimize(std::map<int, int> const& object_stream_data, |
| 453 | 453 | bool allow_changes = true); |
| 454 | 454 | |
| 455 | - // Convenience routines for common functions. See also | |
| 456 | - // QPDFObjectHandle.hh for additional convenience routines. | |
| 457 | - | |
| 458 | - // Page handling API | |
| 459 | - | |
| 460 | - // Traverse page tree return all /Page objects. Note that calls | |
| 461 | - // to page manipulation APIs will change the internal vector that | |
| 462 | - // this routine returns a pointer to. If you don't want that, | |
| 463 | - // assign this to a regular vector rather than a const reference. | |
| 455 | + // Traverse page tree return all /Page objects. For efficiency, | |
| 456 | + // this method returns a const reference to an internal vector of | |
| 457 | + // pages. Calls to addPage, addPageAt, and removePage safely | |
| 458 | + // update this, but directly manipulation of the pages three or | |
| 459 | + // pushing inheritable objects to the page level may invalidate | |
| 460 | + // it. See comments for updateAllPagesCache() for additional | |
| 461 | + // notes. Newer code should use | |
| 462 | + // QPDFPageDocumentHelper::getAllPages instead. The decision to | |
| 463 | + // expose this internal cache was arguably incorrect, but it is | |
| 464 | + // being left here for compatibility. It is, however, completely | |
| 465 | + // safe to use this for files that you are not modifying. | |
| 464 | 466 | QPDF_DLL |
| 465 | 467 | std::vector<QPDFObjectHandle> const& getAllPages(); |
| 466 | 468 | |
| ... | ... | @@ -479,32 +481,25 @@ class QPDF |
| 479 | 481 | QPDF_DLL |
| 480 | 482 | void updateAllPagesCache(); |
| 481 | 483 | |
| 482 | - // The PDF /Pages tree allows inherited values. Working with | |
| 483 | - // the pages of a pdf is much easier when the inheritance is | |
| 484 | - // resolved by explicitly setting the values in each /Page. | |
| 484 | + // Legacy handling API. These methods are not going anywhere, and | |
| 485 | + // you should feel free to continue using them if it simplifies | |
| 486 | + // your code. Newer code should make use of QPDFPageDocumentHelper | |
| 487 | + // instead as future page handling methods will be added there. | |
| 488 | + // The functionality and specification of these legacy methods is | |
| 489 | + // identical to the identically named methods there, except that | |
| 490 | + // these versions use QPDFObjectHandle instead of | |
| 491 | + // QPDFPageObjectHelper, so please see comments in that file for | |
| 492 | + // descriptions. | |
| 485 | 493 | QPDF_DLL |
| 486 | 494 | void pushInheritedAttributesToPage(); |
| 487 | - | |
| 488 | - // Add new page at the beginning or the end of the current pdf. | |
| 489 | - // The newpage parameter may be either a direct object, an | |
| 490 | - // indirect object from this QPDF, or an indirect object from | |
| 491 | - // another QPDF. If it is a direct object, it will be made | |
| 492 | - // indirect. If it is an indirect object from another QPDF, this | |
| 493 | - // method will call pushInheritedAttributesToPage on the other | |
| 494 | - // file and then copy the page to this QPDF using the same | |
| 495 | - // underlying code as copyForeignObject. | |
| 496 | 495 | QPDF_DLL |
| 497 | 496 | void addPage(QPDFObjectHandle newpage, bool first); |
| 498 | - | |
| 499 | - // Add new page before or after refpage. See comments for addPage | |
| 500 | - // for details about what newpage should be. | |
| 501 | 497 | QPDF_DLL |
| 502 | 498 | void addPageAt(QPDFObjectHandle newpage, bool before, |
| 503 | 499 | QPDFObjectHandle refpage); |
| 504 | - | |
| 505 | - // Remove page from the pdf. | |
| 506 | 500 | QPDF_DLL |
| 507 | 501 | void removePage(QPDFObjectHandle page); |
| 502 | + // End legacy page helpers | |
| 508 | 503 | |
| 509 | 504 | // Writer class is restricted to QPDFWriter so that only it can |
| 510 | 505 | // call certain methods. | ... | ... |
include/qpdf/QPDFDocumentHelper.hh
0 → 100644
| 1 | +// Copyright (c) 2005-2018 Jay Berkenbilt | |
| 2 | +// | |
| 3 | +// This file is part of qpdf. | |
| 4 | +// | |
| 5 | +// Licensed under the Apache License, Version 2.0 (the "License"); | |
| 6 | +// you may not use this file except in compliance with the License. | |
| 7 | +// You may obtain a copy of the License at | |
| 8 | +// | |
| 9 | +// http://www.apache.org/licenses/LICENSE-2.0 | |
| 10 | +// | |
| 11 | +// Unless required by applicable law or agreed to in writing, software | |
| 12 | +// distributed under the License is distributed on an "AS IS" BASIS, | |
| 13 | +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
| 14 | +// See the License for the specific language governing permissions and | |
| 15 | +// limitations under the License. | |
| 16 | +// | |
| 17 | +// Versions of qpdf prior to version 7 were released under the terms | |
| 18 | +// of version 2.0 of the Artistic License. At your option, you may | |
| 19 | +// continue to consider qpdf to be licensed under those terms. Please | |
| 20 | +// see the manual for additional information. | |
| 21 | + | |
| 22 | +#ifndef __QPDFDOCUMENTHELPER_HH__ | |
| 23 | +#define __QPDFDOCUMENTHELPER_HH__ | |
| 24 | + | |
| 25 | +#include <qpdf/DLL.h> | |
| 26 | +#include <qpdf/QPDF.hh> | |
| 27 | + | |
| 28 | +// This is a base class for QPDF Document Helper classes. Document | |
| 29 | +// helpers are classes that provide a convenient, higher-level API for | |
| 30 | +// accessing document-level structures with a PDF file. Document | |
| 31 | +// helpers are always initialized with a reference to a QPDF object, | |
| 32 | +// and the object can always be retrieved. The intention is that you | |
| 33 | +// may freely intermix use of document helpers with the underlying | |
| 34 | +// QPDF object unless there is a specific comment in a specific helper | |
| 35 | +// method that says otherwise. The pattern of using helper objects was | |
| 36 | +// introduced to allow creation of higher level helper functions | |
| 37 | +// without polluting the public interface of QPDF. | |
| 38 | + | |
| 39 | +class QPDFDocumentHelper | |
| 40 | +{ | |
| 41 | + public: | |
| 42 | + QPDF_DLL | |
| 43 | + QPDFDocumentHelper(QPDF& qpdf) : | |
| 44 | + qpdf(qpdf) | |
| 45 | + { | |
| 46 | + } | |
| 47 | + QPDF_DLL | |
| 48 | + QPDF& getQPDF() | |
| 49 | + { | |
| 50 | + return this->qpdf; | |
| 51 | + } | |
| 52 | + QPDF_DLL | |
| 53 | + QPDF const& getQPDF() const | |
| 54 | + { | |
| 55 | + return this->qpdf; | |
| 56 | + } | |
| 57 | + | |
| 58 | + protected: | |
| 59 | + QPDF& qpdf; | |
| 60 | +}; | |
| 61 | + | |
| 62 | +#endif // __QPDFDOCUMENTHELPER_HH__ | ... | ... |
include/qpdf/QPDFObjectHandle.hh
| ... | ... | @@ -278,37 +278,21 @@ class QPDFObjectHandle |
| 278 | 278 | StringDecrypter* decrypter, |
| 279 | 279 | QPDF* context); |
| 280 | 280 | |
| 281 | - // Helpers for parsing content streams | |
| 282 | - | |
| 283 | - // Parse a page's contents through ParserCallbacks, described | |
| 284 | - // above. This method works whether the contents are a single | |
| 285 | - // stream or an array of streams. Call on a page object. | |
| 286 | - QPDF_DLL | |
| 287 | - void parsePageContents(ParserCallbacks* callbacks); | |
| 288 | - | |
| 289 | - // Pass a page's contents through the given TokenFilter. If a | |
| 290 | - // pipeline is also provided, it will be the target of the write | |
| 291 | - // methods from the token filter. If a pipeline is not specified, | |
| 292 | - // any output generated by the token filter will be discarded. Use | |
| 293 | - // this interface if you need to pass a page's contents through | |
| 294 | - // filter for work purposes without having that filter | |
| 295 | - // automatically applied to the page's contents, as happens with | |
| 296 | - // addContentTokenFilter. See examples/pdf-count-strings.cc for an | |
| 297 | - // example. | |
| 298 | - QPDF_DLL | |
| 299 | - void filterPageContents(TokenFilter* filter, Pipeline* next = 0); | |
| 300 | - | |
| 301 | - // Pipe a page's contents through the given pipeline. This method | |
| 302 | - // works whether the contents are a single stream or an array of | |
| 303 | - // streams. Call on a page object. | |
| 281 | + // Older method: stream_or_array should be the value of /Contents | |
| 282 | + // from a page object. It's more convenient to just call | |
| 283 | + // QPDFPageObjectHelper::parsePageContents on the page object, and | |
| 284 | + // error messages will also be more useful because the page object | |
| 285 | + // information will be known. | |
| 304 | 286 | QPDF_DLL |
| 305 | - void pipePageContents(Pipeline* p); | |
| 287 | + static void parseContentStream(QPDFObjectHandle stream_or_array, | |
| 288 | + ParserCallbacks* callbacks); | |
| 306 | 289 | |
| 307 | 290 | // When called on a stream or stream array that is some page's |
| 308 | 291 | // content streams, do the same as pipePageContents. This method |
| 309 | - // is a lower level way to do what pipePageContents does, but it | |
| 310 | - // allows you to perform this operation on a contents object that | |
| 311 | - // is disconnected from a page object. The description argument | |
| 292 | + // is a lower level way to do what | |
| 293 | + // QPDFPageObjectHelper::pipePageContents does, but it allows you | |
| 294 | + // to perform this operation on a contents object that is | |
| 295 | + // disconnected from a page object. The description argument | |
| 312 | 296 | // should describe the containing page and is used in error |
| 313 | 297 | // messages. The all_description argument is initialized to |
| 314 | 298 | // something that could be used to describe the result of the |
| ... | ... | @@ -318,32 +302,33 @@ class QPDFObjectHandle |
| 318 | 302 | void pipeContentStreams(Pipeline* p, std::string const& description, |
| 319 | 303 | std::string& all_description); |
| 320 | 304 | |
| 321 | - // Older method: stream_or_array should be the value of /Contents | |
| 322 | - // from a page object. It's more convenient to just call | |
| 323 | - // parsePageContents on the page object, and error messages will | |
| 324 | - // also be more useful because the page object information will be | |
| 325 | - // known. | |
| 326 | - QPDF_DLL | |
| 327 | - static void parseContentStream(QPDFObjectHandle stream_or_array, | |
| 328 | - ParserCallbacks* callbacks); | |
| 329 | - | |
| 330 | - // Attach a token filter to a page's contents. If the page's | |
| 331 | - // contents is an array of streams, it is automatically coalesced. | |
| 332 | - // The token filter is applied to the page's contents as a single | |
| 333 | - // stream. | |
| 334 | - QPDF_DLL | |
| 335 | - void addContentTokenFilter(PointerHolder<TokenFilter> token_filter); | |
| 336 | - | |
| 337 | 305 | // As of qpdf 8, it is possible to add custom token filters to a |
| 338 | 306 | // stream. The tokenized stream data is passed through the token |
| 339 | 307 | // filter after all original filters but before content stream |
| 340 | 308 | // normalization if requested. This is a low-level interface to |
| 341 | 309 | // add it to a stream. You will usually want to call |
| 342 | - // addContentTokenFilter instead, which can be applied to a page | |
| 343 | - // object, and which will automatically handle the case of pages | |
| 344 | - // whose contents are split across multiple streams. | |
| 310 | + // QPDFPageObjectHelper::addContentTokenFilter instead, which can | |
| 311 | + // be applied to a page object, and which will automatically | |
| 312 | + // handle the case of pages whose contents are split across | |
| 313 | + // multiple streams. | |
| 345 | 314 | void addTokenFilter(PointerHolder<TokenFilter> token_filter); |
| 346 | 315 | |
| 316 | + // Legacy helpers for parsing content streams. These methods are | |
| 317 | + // not going away, but newer code should call the correspond | |
| 318 | + // methods in QPDFPageObjectHelper instead. The specification and | |
| 319 | + // behavior of these methods are the same as the identically named | |
| 320 | + // methods in that class, but newer functionality will be added | |
| 321 | + // there. | |
| 322 | + QPDF_DLL | |
| 323 | + void parsePageContents(ParserCallbacks* callbacks); | |
| 324 | + QPDF_DLL | |
| 325 | + void filterPageContents(TokenFilter* filter, Pipeline* next = 0); | |
| 326 | + QPDF_DLL | |
| 327 | + void pipePageContents(Pipeline* p); | |
| 328 | + QPDF_DLL | |
| 329 | + void addContentTokenFilter(PointerHolder<TokenFilter> token_filter); | |
| 330 | + // End legacy content stream helpers | |
| 331 | + | |
| 347 | 332 | // Type-specific factories |
| 348 | 333 | QPDF_DLL |
| 349 | 334 | static QPDFObjectHandle newNull(); |
| ... | ... | @@ -731,51 +716,22 @@ class QPDFObjectHandle |
| 731 | 716 | QPDF_DLL |
| 732 | 717 | std::string unparseResolved(); |
| 733 | 718 | |
| 734 | - // Convenience routines for commonly performed functions | |
| 735 | - | |
| 736 | - // Returns an empty map if there are no images or no resources. | |
| 737 | - // This function does not presently support inherited resources. | |
| 738 | - // If this is a significant concern, call | |
| 739 | - // pushInheritedAttributesToPage() on the QPDF object that owns | |
| 740 | - // this page. See comment in the source for details. Return value | |
| 741 | - // is a map from XObject name to the image object, which is always | |
| 742 | - // a stream. | |
| 719 | + // Legacy helper methods for commonly performed operations on | |
| 720 | + // pages. Newer code should use QPDFPageObjectHelper instead. The | |
| 721 | + // specification and behavior of these methods are the same as the | |
| 722 | + // identically named methods in that class, but newer | |
| 723 | + // functionality will be added there. | |
| 743 | 724 | QPDF_DLL |
| 744 | 725 | std::map<std::string, QPDFObjectHandle> getPageImages(); |
| 745 | - | |
| 746 | - // Returns a vector of stream objects representing the content | |
| 747 | - // streams for the given page. This routine allows the caller to | |
| 748 | - // not care whether there are one or more than one content streams | |
| 749 | - // for a page. | |
| 750 | 726 | QPDF_DLL |
| 751 | 727 | std::vector<QPDFObjectHandle> getPageContents(); |
| 752 | - | |
| 753 | - // Add the given object as a new content stream for this page. If | |
| 754 | - // parameter 'first' is true, add to the beginning. Otherwise, add | |
| 755 | - // to the end. This routine automatically converts the page | |
| 756 | - // contents to an array if it is a scalar, allowing the caller not | |
| 757 | - // to care what the initial structure is. You can call | |
| 758 | - // coalesceContentStreams() afterwards if you want to force it to | |
| 759 | - // be a single stream. | |
| 760 | 728 | QPDF_DLL |
| 761 | 729 | void addPageContents(QPDFObjectHandle contents, bool first); |
| 762 | - | |
| 763 | - // Rotate a page. If relative is false, set the rotation of the | |
| 764 | - // page to angle. Otherwise, add angle to the rotation of the | |
| 765 | - // page. Angle must be a multiple of 90. Adding 90 to the rotation | |
| 766 | - // rotates clockwise by 90 degrees. | |
| 767 | 730 | QPDF_DLL |
| 768 | 731 | void rotatePage(int angle, bool relative); |
| 769 | - | |
| 770 | - // Coalesce a page's content streams. A page's content may be a | |
| 771 | - // stream or an array of streams. If this page's content is an | |
| 772 | - // array, concatenate the streams into a single stream. This can | |
| 773 | - // be useful when working with files that split content streams in | |
| 774 | - // arbitrary spots, such as in the middle of a token, as that can | |
| 775 | - // confuse some software. You could also call this after calling | |
| 776 | - // addPageContents. | |
| 777 | 732 | QPDF_DLL |
| 778 | 733 | void coalesceContentStreams(); |
| 734 | + // End legacy page helpers | |
| 779 | 735 | |
| 780 | 736 | // Issue a warning about this object if possible. If the object |
| 781 | 737 | // has a description, a warning will be issued. Otherwise, if | ... | ... |
include/qpdf/QPDFObjectHelper.hh
0 → 100644
| 1 | +// Copyright (c) 2005-2018 Jay Berkenbilt | |
| 2 | +// | |
| 3 | +// This file is part of qpdf. | |
| 4 | +// | |
| 5 | +// Licensed under the Apache License, Version 2.0 (the "License"); | |
| 6 | +// you may not use this file except in compliance with the License. | |
| 7 | +// You may obtain a copy of the License at | |
| 8 | +// | |
| 9 | +// http://www.apache.org/licenses/LICENSE-2.0 | |
| 10 | +// | |
| 11 | +// Unless required by applicable law or agreed to in writing, software | |
| 12 | +// distributed under the License is distributed on an "AS IS" BASIS, | |
| 13 | +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
| 14 | +// See the License for the specific language governing permissions and | |
| 15 | +// limitations under the License. | |
| 16 | +// | |
| 17 | +// Versions of qpdf prior to version 7 were released under the terms | |
| 18 | +// of version 2.0 of the Artistic License. At your option, you may | |
| 19 | +// continue to consider qpdf to be licensed under those terms. Please | |
| 20 | +// see the manual for additional information. | |
| 21 | + | |
| 22 | +#ifndef __QPDFOBJECTHELPER_HH__ | |
| 23 | +#define __QPDFOBJECTHELPER_HH__ | |
| 24 | + | |
| 25 | +#include <qpdf/DLL.h> | |
| 26 | + | |
| 27 | +#include <qpdf/QPDFObjectHandle.hh> | |
| 28 | + | |
| 29 | +// This is a base class for QPDF Object Helper classes. Object helpers | |
| 30 | +// are classes that provide a convenient, higher-level API for working | |
| 31 | +// with specific types of QPDF objects. Object helpers are always | |
| 32 | +// initialized with a QPDFObjectHandle, and the underlying object | |
| 33 | +// handle can always be retrieved. The intention is that you may | |
| 34 | +// freely intermix use of document helpers with the underlying QPDF | |
| 35 | +// objects unless there is a specific comment in a specific helper | |
| 36 | +// method that says otherwise. The pattern of using helper objects was | |
| 37 | +// introduced to allow creation of higher level helper functions | |
| 38 | +// without polluting the public interface of QPDFObjectHandle. | |
| 39 | + | |
| 40 | +class QPDFObjectHelper | |
| 41 | +{ | |
| 42 | + public: | |
| 43 | + QPDF_DLL | |
| 44 | + QPDFObjectHelper(QPDFObjectHandle oh) : | |
| 45 | + oh(oh) | |
| 46 | + { | |
| 47 | + } | |
| 48 | + QPDF_DLL | |
| 49 | + QPDFObjectHandle getObjectHandle() | |
| 50 | + { | |
| 51 | + return this->oh; | |
| 52 | + } | |
| 53 | + QPDF_DLL | |
| 54 | + QPDFObjectHandle const getObjectHandle() const | |
| 55 | + { | |
| 56 | + return this->oh; | |
| 57 | + } | |
| 58 | + | |
| 59 | + protected: | |
| 60 | + QPDFObjectHandle oh; | |
| 61 | +}; | |
| 62 | + | |
| 63 | +#endif // __QPDFOBJECTHELPER_HH__ | ... | ... |
include/qpdf/QPDFPageDocumentHelper.hh
0 → 100644
| 1 | +// Copyright (c) 2005-2018 Jay Berkenbilt | |
| 2 | +// | |
| 3 | +// This file is part of qpdf. | |
| 4 | +// | |
| 5 | +// Licensed under the Apache License, Version 2.0 (the "License"); | |
| 6 | +// you may not use this file except in compliance with the License. | |
| 7 | +// You may obtain a copy of the License at | |
| 8 | +// | |
| 9 | +// http://www.apache.org/licenses/LICENSE-2.0 | |
| 10 | +// | |
| 11 | +// Unless required by applicable law or agreed to in writing, software | |
| 12 | +// distributed under the License is distributed on an "AS IS" BASIS, | |
| 13 | +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
| 14 | +// See the License for the specific language governing permissions and | |
| 15 | +// limitations under the License. | |
| 16 | +// | |
| 17 | +// Versions of qpdf prior to version 7 were released under the terms | |
| 18 | +// of version 2.0 of the Artistic License. At your option, you may | |
| 19 | +// continue to consider qpdf to be licensed under those terms. Please | |
| 20 | +// see the manual for additional information. | |
| 21 | + | |
| 22 | +#ifndef __QPDFPAGEDOCUMENTHELPER_HH__ | |
| 23 | +#define __QPDFPAGEDOCUMENTHELPER_HH__ | |
| 24 | + | |
| 25 | +#include <qpdf/QPDFDocumentHelper.hh> | |
| 26 | +#include <qpdf/QPDFPageObjectHelper.hh> | |
| 27 | + | |
| 28 | +#include <qpdf/DLL.h> | |
| 29 | + | |
| 30 | +#include <vector> | |
| 31 | + | |
| 32 | +#include <qpdf/QPDF.hh> | |
| 33 | + | |
| 34 | +class QPDFPageDocumentHelper: public QPDFDocumentHelper | |
| 35 | +{ | |
| 36 | + public: | |
| 37 | + QPDFPageDocumentHelper(QPDF&); | |
| 38 | + | |
| 39 | + // Traverse page tree, and return all /Page objects wrapped in | |
| 40 | + // QPDFPageObjectHelper objects. Unlike with | |
| 41 | + // QPDFObjectHandle::getAllPages, the vector of pages returned by | |
| 42 | + // this call is not affected by additions or removals of pages. If | |
| 43 | + // you manipulate pages, you will have to call this again to get a | |
| 44 | + // new copy. Please comments in QPDFObjectHandle.hh for | |
| 45 | + // getAllPages() for additional details. | |
| 46 | + QPDF_DLL | |
| 47 | + std::vector<QPDFPageObjectHelper> getAllPages(); | |
| 48 | + | |
| 49 | + // The PDF /Pages tree allows inherited values. Working with the | |
| 50 | + // pages of a pdf is much easier when the inheritance is resolved | |
| 51 | + // by explicitly setting the values in each /Page. | |
| 52 | + QPDF_DLL | |
| 53 | + void pushInheritedAttributesToPage(); | |
| 54 | + | |
| 55 | + // Add new page at the beginning or the end of the current pdf. | |
| 56 | + // The newpage parameter may be either a direct object, an | |
| 57 | + // indirect object from this QPDF, or an indirect object from | |
| 58 | + // another QPDF. If it is a direct object, it will be made | |
| 59 | + // indirect. If it is an indirect object from another QPDF, this | |
| 60 | + // method will call pushInheritedAttributesToPage on the other | |
| 61 | + // file and then copy the page to this QPDF using the same | |
| 62 | + // underlying code as copyForeignObject. | |
| 63 | + QPDF_DLL | |
| 64 | + void addPage(QPDFPageObjectHelper newpage, bool first); | |
| 65 | + | |
| 66 | + // Add new page before or after refpage. See comments for addPage | |
| 67 | + // for details about what newpage should be. | |
| 68 | + QPDF_DLL | |
| 69 | + void addPageAt(QPDFPageObjectHelper newpage, bool before, | |
| 70 | + QPDFPageObjectHelper refpage); | |
| 71 | + | |
| 72 | + // Remove page from the pdf. | |
| 73 | + QPDF_DLL | |
| 74 | + void removePage(QPDFPageObjectHelper page); | |
| 75 | + | |
| 76 | + private: | |
| 77 | + class Members | |
| 78 | + { | |
| 79 | + friend class QPDFPageDocumentHelper; | |
| 80 | + | |
| 81 | + public: | |
| 82 | + ~Members(); | |
| 83 | + | |
| 84 | + private: | |
| 85 | + Members(); | |
| 86 | + Members(Members const&); | |
| 87 | + }; | |
| 88 | + | |
| 89 | + PointerHolder<Members> m; | |
| 90 | +}; | |
| 91 | + | |
| 92 | +#endif // __QPDFPAGEDOCUMENTHELPER_HH__ | ... | ... |
include/qpdf/QPDFPageObjectHelper.hh
0 → 100644
| 1 | +// Copyright (c) 2005-2018 Jay Berkenbilt | |
| 2 | +// | |
| 3 | +// This file is part of qpdf. | |
| 4 | +// | |
| 5 | +// Licensed under the Apache License, Version 2.0 (the "License"); | |
| 6 | +// you may not use this file except in compliance with the License. | |
| 7 | +// You may obtain a copy of the License at | |
| 8 | +// | |
| 9 | +// http://www.apache.org/licenses/LICENSE-2.0 | |
| 10 | +// | |
| 11 | +// Unless required by applicable law or agreed to in writing, software | |
| 12 | +// distributed under the License is distributed on an "AS IS" BASIS, | |
| 13 | +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |
| 14 | +// See the License for the specific language governing permissions and | |
| 15 | +// limitations under the License. | |
| 16 | +// | |
| 17 | +// Versions of qpdf prior to version 7 were released under the terms | |
| 18 | +// of version 2.0 of the Artistic License. At your option, you may | |
| 19 | +// continue to consider qpdf to be licensed under those terms. Please | |
| 20 | +// see the manual for additional information. | |
| 21 | + | |
| 22 | +#ifndef __QPDFPAGEOBJECTHELPER_HH__ | |
| 23 | +#define __QPDFPAGEOBJECTHELPER_HH__ | |
| 24 | + | |
| 25 | +#include <qpdf/QPDFObjectHelper.hh> | |
| 26 | + | |
| 27 | +#include <qpdf/DLL.h> | |
| 28 | + | |
| 29 | +#include <qpdf/QPDFObjectHandle.hh> | |
| 30 | + | |
| 31 | +class QPDFPageObjectHelper: public QPDFObjectHelper | |
| 32 | +{ | |
| 33 | + public: | |
| 34 | + QPDFPageObjectHelper(QPDFObjectHandle); | |
| 35 | + | |
| 36 | + // Returns an empty map if there are no images or no resources. | |
| 37 | + // This function does not presently support inherited resources. | |
| 38 | + // If this is a significant concern, call | |
| 39 | + // pushInheritedAttributesToPage() on the QPDF object that owns | |
| 40 | + // this page. See comment in the source for details. Return value | |
| 41 | + // is a map from XObject name to the image object, which is always | |
| 42 | + // a stream. | |
| 43 | + QPDF_DLL | |
| 44 | + std::map<std::string, QPDFObjectHandle> getPageImages(); | |
| 45 | + | |
| 46 | + // Returns a vector of stream objects representing the content | |
| 47 | + // streams for the given page. This routine allows the caller to | |
| 48 | + // not care whether there are one or more than one content streams | |
| 49 | + // for a page. | |
| 50 | + QPDF_DLL | |
| 51 | + std::vector<QPDFObjectHandle> getPageContents(); | |
| 52 | + | |
| 53 | + // Add the given object as a new content stream for this page. If | |
| 54 | + // parameter 'first' is true, add to the beginning. Otherwise, add | |
| 55 | + // to the end. This routine automatically converts the page | |
| 56 | + // contents to an array if it is a scalar, allowing the caller not | |
| 57 | + // to care what the initial structure is. You can call | |
| 58 | + // coalesceContentStreams() afterwards if you want to force it to | |
| 59 | + // be a single stream. | |
| 60 | + QPDF_DLL | |
| 61 | + void addPageContents(QPDFObjectHandle contents, bool first); | |
| 62 | + | |
| 63 | + // Rotate a page. If relative is false, set the rotation of the | |
| 64 | + // page to angle. Otherwise, add angle to the rotation of the | |
| 65 | + // page. Angle must be a multiple of 90. Adding 90 to the rotation | |
| 66 | + // rotates clockwise by 90 degrees. | |
| 67 | + QPDF_DLL | |
| 68 | + void rotatePage(int angle, bool relative); | |
| 69 | + | |
| 70 | + // Coalesce a page's content streams. A page's content may be a | |
| 71 | + // stream or an array of streams. If this page's content is an | |
| 72 | + // array, concatenate the streams into a single stream. This can | |
| 73 | + // be useful when working with files that split content streams in | |
| 74 | + // arbitrary spots, such as in the middle of a token, as that can | |
| 75 | + // confuse some software. You could also call this after calling | |
| 76 | + // addPageContents. | |
| 77 | + QPDF_DLL | |
| 78 | + void coalesceContentStreams(); | |
| 79 | + | |
| 80 | + // | |
| 81 | + // Content stream handling | |
| 82 | + // | |
| 83 | + | |
| 84 | + // Parse a page's contents through ParserCallbacks, described | |
| 85 | + // above. This method works whether the contents are a single | |
| 86 | + // stream or an array of streams. Call on a page object. | |
| 87 | + QPDF_DLL | |
| 88 | + void parsePageContents(QPDFObjectHandle::ParserCallbacks* callbacks); | |
| 89 | + | |
| 90 | + // Pass a page's contents through the given TokenFilter. If a | |
| 91 | + // pipeline is also provided, it will be the target of the write | |
| 92 | + // methods from the token filter. If a pipeline is not specified, | |
| 93 | + // any output generated by the token filter will be discarded. Use | |
| 94 | + // this interface if you need to pass a page's contents through | |
| 95 | + // filter for work purposes without having that filter | |
| 96 | + // automatically applied to the page's contents, as happens with | |
| 97 | + // addContentTokenFilter. See examples/pdf-count-strings.cc for an | |
| 98 | + // example. | |
| 99 | + QPDF_DLL | |
| 100 | + void filterPageContents(QPDFObjectHandle::TokenFilter* filter, | |
| 101 | + Pipeline* next = 0); | |
| 102 | + | |
| 103 | + // Pipe a page's contents through the given pipeline. This method | |
| 104 | + // works whether the contents are a single stream or an array of | |
| 105 | + // streams. Call on a page object. | |
| 106 | + QPDF_DLL | |
| 107 | + void pipePageContents(Pipeline* p); | |
| 108 | + | |
| 109 | + // Attach a token filter to a page's contents. If the page's | |
| 110 | + // contents is an array of streams, it is automatically coalesced. | |
| 111 | + // The token filter is applied to the page's contents as a single | |
| 112 | + // stream. | |
| 113 | + QPDF_DLL | |
| 114 | + void addContentTokenFilter( | |
| 115 | + PointerHolder<QPDFObjectHandle::TokenFilter> token_filter); | |
| 116 | + | |
| 117 | + private: | |
| 118 | + class Members | |
| 119 | + { | |
| 120 | + friend class QPDFPageObjectHelper; | |
| 121 | + | |
| 122 | + public: | |
| 123 | + ~Members(); | |
| 124 | + | |
| 125 | + private: | |
| 126 | + Members(); | |
| 127 | + Members(Members const&); | |
| 128 | + }; | |
| 129 | + | |
| 130 | + PointerHolder<Members> m; | |
| 131 | +}; | |
| 132 | + | |
| 133 | +#endif // __QPDFPAGEOBJECTHELPER_HH__ | ... | ... |
libqpdf/QPDFPageDocumentHelper.cc
0 → 100644
| 1 | +#include <qpdf/QPDFPageDocumentHelper.hh> | |
| 2 | + | |
| 3 | +QPDFPageDocumentHelper::Members::~Members() | |
| 4 | +{ | |
| 5 | +} | |
| 6 | + | |
| 7 | +QPDFPageDocumentHelper::Members::Members() | |
| 8 | +{ | |
| 9 | +} | |
| 10 | + | |
| 11 | +QPDFPageDocumentHelper::QPDFPageDocumentHelper(QPDF& qpdf) : | |
| 12 | + QPDFDocumentHelper(qpdf) | |
| 13 | +{ | |
| 14 | +} | |
| 15 | + | |
| 16 | +std::vector<QPDFPageObjectHelper> | |
| 17 | +QPDFPageDocumentHelper::getAllPages() | |
| 18 | +{ | |
| 19 | + std::vector<QPDFObjectHandle> const& pages_v = this->qpdf.getAllPages(); | |
| 20 | + std::vector<QPDFPageObjectHelper> pages; | |
| 21 | + for (std::vector<QPDFObjectHandle>::const_iterator iter = pages_v.begin(); | |
| 22 | + iter != pages_v.end(); ++iter) | |
| 23 | + { | |
| 24 | + pages.push_back(QPDFPageObjectHelper(*iter)); | |
| 25 | + } | |
| 26 | + return pages; | |
| 27 | +} | |
| 28 | + | |
| 29 | +void | |
| 30 | +QPDFPageDocumentHelper::pushInheritedAttributesToPage() | |
| 31 | +{ | |
| 32 | + this->qpdf.pushInheritedAttributesToPage(); | |
| 33 | +} | |
| 34 | + | |
| 35 | +void | |
| 36 | +QPDFPageDocumentHelper::addPage(QPDFPageObjectHelper newpage, bool first) | |
| 37 | +{ | |
| 38 | + this->qpdf.addPage(newpage.getObjectHandle(), first); | |
| 39 | +} | |
| 40 | + | |
| 41 | +void | |
| 42 | +QPDFPageDocumentHelper::addPageAt(QPDFPageObjectHelper newpage, bool before, | |
| 43 | + QPDFPageObjectHelper refpage) | |
| 44 | +{ | |
| 45 | + this->qpdf.addPageAt(newpage.getObjectHandle(), before, | |
| 46 | + refpage.getObjectHandle()); | |
| 47 | +} | |
| 48 | + | |
| 49 | +void | |
| 50 | +QPDFPageDocumentHelper::removePage(QPDFPageObjectHelper page) | |
| 51 | +{ | |
| 52 | + this->qpdf.removePage(page.getObjectHandle()); | |
| 53 | +} | ... | ... |
libqpdf/QPDFPageObjectHelper.cc
0 → 100644
| 1 | +#include <qpdf/QPDFPageObjectHelper.hh> | |
| 2 | + | |
| 3 | +QPDFPageObjectHelper::Members::~Members() | |
| 4 | +{ | |
| 5 | +} | |
| 6 | + | |
| 7 | +QPDFPageObjectHelper::Members::Members() | |
| 8 | +{ | |
| 9 | +} | |
| 10 | + | |
| 11 | +QPDFPageObjectHelper::QPDFPageObjectHelper(QPDFObjectHandle oh) : | |
| 12 | + QPDFObjectHelper(oh) | |
| 13 | +{ | |
| 14 | +} | |
| 15 | + | |
| 16 | +std::map<std::string, QPDFObjectHandle> | |
| 17 | +QPDFPageObjectHelper::getPageImages() | |
| 18 | +{ | |
| 19 | + return this->oh.getPageImages(); | |
| 20 | +} | |
| 21 | + | |
| 22 | +std::vector<QPDFObjectHandle> | |
| 23 | +QPDFPageObjectHelper::getPageContents() | |
| 24 | +{ | |
| 25 | + return this->oh.getPageContents(); | |
| 26 | +} | |
| 27 | + | |
| 28 | +void | |
| 29 | +QPDFPageObjectHelper::addPageContents(QPDFObjectHandle contents, bool first) | |
| 30 | +{ | |
| 31 | + this->oh.addPageContents(contents, first); | |
| 32 | +} | |
| 33 | + | |
| 34 | +void | |
| 35 | +QPDFPageObjectHelper::rotatePage(int angle, bool relative) | |
| 36 | +{ | |
| 37 | + this->oh.rotatePage(angle, relative); | |
| 38 | +} | |
| 39 | + | |
| 40 | +void | |
| 41 | +QPDFPageObjectHelper::coalesceContentStreams() | |
| 42 | +{ | |
| 43 | + this->oh.coalesceContentStreams(); | |
| 44 | +} | |
| 45 | + | |
| 46 | +void | |
| 47 | +QPDFPageObjectHelper::parsePageContents( | |
| 48 | + QPDFObjectHandle::ParserCallbacks* callbacks) | |
| 49 | +{ | |
| 50 | + this->oh.parsePageContents(callbacks); | |
| 51 | +} | |
| 52 | + | |
| 53 | +void | |
| 54 | +QPDFPageObjectHelper::filterPageContents( | |
| 55 | + QPDFObjectHandle::TokenFilter* filter, | |
| 56 | + Pipeline* next) | |
| 57 | +{ | |
| 58 | + this->oh.filterPageContents(filter, next); | |
| 59 | +} | |
| 60 | + | |
| 61 | +void | |
| 62 | +QPDFPageObjectHelper::pipePageContents(Pipeline* p) | |
| 63 | +{ | |
| 64 | + this->oh.pipePageContents(p); | |
| 65 | +} | |
| 66 | + | |
| 67 | +void | |
| 68 | +QPDFPageObjectHelper::addContentTokenFilter( | |
| 69 | + PointerHolder<QPDFObjectHandle::TokenFilter> token_filter) | |
| 70 | +{ | |
| 71 | + this->oh.addContentTokenFilter(token_filter); | |
| 72 | +} | ... | ... |
libqpdf/build.mk
| ... | ... | @@ -39,6 +39,8 @@ SRCS_libqpdf = \ |
| 39 | 39 | libqpdf/QPDFObjGen.cc \ |
| 40 | 40 | libqpdf/QPDFObject.cc \ |
| 41 | 41 | libqpdf/QPDFObjectHandle.cc \ |
| 42 | + libqpdf/QPDFPageDocumentHelper.cc \ | |
| 43 | + libqpdf/QPDFPageObjectHelper.cc \ | |
| 42 | 44 | libqpdf/QPDFTokenizer.cc \ |
| 43 | 45 | libqpdf/QPDFWriter.cc \ |
| 44 | 46 | libqpdf/QPDFXRefEntry.cc \ | ... | ... |