mirror of
https://github.com/JakubMelka/PDF4QT.git
synced 2025-06-05 21:59:17 +02:00
Issue #118: First part of splitting
This commit is contained in:
160
Pdf4QtLibCore/sources/pdfdocumentmanipulator.h
Normal file
160
Pdf4QtLibCore/sources/pdfdocumentmanipulator.h
Normal file
@ -0,0 +1,160 @@
|
||||
// Copyright (C) 2021 Jakub Melka
|
||||
//
|
||||
// This file is part of PDF4QT.
|
||||
//
|
||||
// PDF4QT is free software: you can redistribute it and/or modify
|
||||
// it under the terms of the GNU Lesser General Public License as published by
|
||||
// the Free Software Foundation, either version 3 of the License, or
|
||||
// with the written consent of the copyright owner, any later version.
|
||||
//
|
||||
// PDF4QT is distributed in the hope that it will be useful,
|
||||
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
// GNU Lesser General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU Lesser General Public License
|
||||
// along with PDF4QT. If not, see <https://www.gnu.org/licenses/>.
|
||||
|
||||
#ifndef PDFDOCUMENTMANIPULATOR_H
|
||||
#define PDFDOCUMENTMANIPULATOR_H
|
||||
|
||||
#include "pdfdocument.h"
|
||||
#include "pdfutils.h"
|
||||
|
||||
#include <QImage>
|
||||
|
||||
namespace pdf
|
||||
{
|
||||
|
||||
/// Document page assembler/manipulator. Can assemble document(s) pages
|
||||
/// to a new document, where pages are inserted/removed/moved, or joined
|
||||
/// from another documents, or blank pages/image pages inserted. Document
|
||||
/// is also optimized.
|
||||
class PDF4QTLIBSHARED_EXPORT PDFDocumentManipulator
|
||||
{
|
||||
Q_DECLARE_TR_FUNCTIONS(pdf::PDFDocumentManipulator)
|
||||
|
||||
public:
|
||||
explicit PDFDocumentManipulator() = default;
|
||||
|
||||
/// Selects outline creation mode, when multiple documents
|
||||
/// are merged into one. For single document manipulation,
|
||||
/// this has no meaning.
|
||||
enum class OutlineMode
|
||||
{
|
||||
NoOutline,
|
||||
Join,
|
||||
DocumentParts
|
||||
};
|
||||
|
||||
struct AssembledPage
|
||||
{
|
||||
PDFInteger documentIndex = -1; ///< Source document index. If page is not from a document, value is -1.
|
||||
PDFInteger imageIndex = -1; ///< Source image index. If page is not from a image, value is -1.
|
||||
PDFInteger pageIndex = -1; ///< Source document page index. If page is not from a document, value is -1.
|
||||
QSizeF pageSize; ///< Unrotated page size
|
||||
PageRotation pageRotation = PageRotation::None; ///< Page rotation
|
||||
|
||||
constexpr bool isDocumentPage() const { return documentIndex != -1; }
|
||||
constexpr bool isImagePage() const { return imageIndex != -1; }
|
||||
constexpr bool isBlankPage() const { return documentIndex == -1 && imageIndex == -1; }
|
||||
};
|
||||
|
||||
using AssembledPages = std::vector<AssembledPage>;
|
||||
|
||||
/// Adds document with given index to available document list
|
||||
/// \param documentIndex Document index
|
||||
/// \param document Document
|
||||
void addDocument(int documentIndex, const PDFDocument* document) { m_documents[documentIndex] = document; }
|
||||
|
||||
/// Adds image with given index to available image list
|
||||
/// \param imageIndex Image index
|
||||
/// \param image Image
|
||||
void addImage(int imageIndex, QImage image) { m_images[imageIndex] = std::move(image); }
|
||||
|
||||
/// Assembles pages into a new document. Returns true, if a new document
|
||||
/// was assembled, otherwise error message is being returned. Assebmled
|
||||
/// document can be accessed trough a given getters.
|
||||
/// \param pages Pages
|
||||
/// \returns True or error message
|
||||
PDFOperationResult assemble(const AssembledPages& pages);
|
||||
|
||||
/// Returns reference to an assembled document. This function should
|
||||
/// be called only, if method \p assemble returns true, otherwise
|
||||
/// undefined document can be returned.
|
||||
/// \returns Assembled document
|
||||
const PDFDocument& getAssembledDocument() const { return m_assembledDocument; }
|
||||
|
||||
/// Returns rvalue reference to an assembled document. This function should
|
||||
/// be called only, if method \p assemble returns true, otherwise
|
||||
/// undefined document can be returned.
|
||||
/// \returns Assembled document
|
||||
PDFDocument&& takeAssembledDocument() { return std::move(m_assembledDocument); }
|
||||
|
||||
static AssembledPages createAllDocumentPages(int documentIndex, const PDFDocument* document);
|
||||
|
||||
static constexpr AssembledPage createDocumentPage(int documentIndex, int pageIndex, QSizeF pageSize, PageRotation pageRotation) { return AssembledPage{ documentIndex, -1, pageIndex, pageSize, pageRotation}; }
|
||||
static constexpr AssembledPage createImagePage(int imageIndex, QSizeF pageSize, PageRotation pageRotation) { return AssembledPage{ -1, imageIndex, -1, pageSize, pageRotation}; }
|
||||
static constexpr AssembledPage createBlankPage(QSizeF pageSize, PageRotation pageRotation) { return AssembledPage{ -1, -1, -1, pageSize, pageRotation}; }
|
||||
|
||||
OutlineMode getOutlineMode() const;
|
||||
void setOutlineMode(OutlineMode outlineMode);
|
||||
|
||||
private:
|
||||
|
||||
struct ProcessedPage
|
||||
{
|
||||
AssembledPage assembledPage;
|
||||
PDFObjectReference targetPageReference;
|
||||
};
|
||||
|
||||
using ProcessedPages = std::vector<ProcessedPage>;
|
||||
|
||||
enum AssembleFlag
|
||||
{
|
||||
None = 0x0000,
|
||||
SingleDocument = 0x0001, ///< We are assembling a single page document (possibly with blank pages / image pages
|
||||
RemovedPages = 0x0002, ///< Document contains removed pages
|
||||
};
|
||||
Q_DECLARE_FLAGS(AssembleFlags, AssembleFlag)
|
||||
|
||||
enum MergedObjectType
|
||||
{
|
||||
MOT_OCProperties,
|
||||
MOT_Form,
|
||||
MOT_Names,
|
||||
MOT_Last
|
||||
};
|
||||
|
||||
/// Processes pages given a page list and a document builder.
|
||||
/// \param documentBuilder Document builder
|
||||
/// \param pages Pages to be processed
|
||||
/// \returns Processed pages
|
||||
ProcessedPages processPages(PDFDocumentBuilder& documentBuilder, const AssembledPages& pages);
|
||||
|
||||
/// Collects objects and copies them into the target document builder.
|
||||
/// \param documentBuilder Document builder
|
||||
/// \param pages Pages to be copied
|
||||
/// \returns Processed pages
|
||||
ProcessedPages collectObjectsAndCopyPages(PDFDocumentBuilder& documentBuilder, const AssembledPages& pages);
|
||||
|
||||
void classify(const AssembledPages& pages);
|
||||
void initializeMergedObjects(PDFDocumentBuilder& documentBuilder);
|
||||
void finalizeMergedObjects(PDFDocumentBuilder& documentBuilder);
|
||||
void finalizeDocument(PDFDocument* document);
|
||||
void addOutlineAndDocumentParts(PDFDocumentBuilder& documentBuilder,
|
||||
const AssembledPages& pages,
|
||||
const std::vector<PDFObjectReference>& adjustedPages);
|
||||
|
||||
std::map<PDFInteger, const PDFDocument*> m_documents;
|
||||
std::map<PDFInteger, QImage> m_images;
|
||||
AssembleFlags m_flags = None;
|
||||
std::array<PDFObjectReference, MOT_Last> m_mergedObjects = { };
|
||||
PDFDocument m_assembledDocument;
|
||||
OutlineMode m_outlineMode = OutlineMode::DocumentParts;
|
||||
std::map<PDFInteger, PDFObjectReference> m_outlines;
|
||||
};
|
||||
|
||||
} // namespace pdf
|
||||
|
||||
#endif // PDFDOCUMENTMANIPULATOR_H
|
Reference in New Issue
Block a user