アイコン 株式会社トラスト・ソフトウェア・システム
電話:03-5316-3375info@trustss.co.jp
電話:03-5316-3375info@trustss.co.jp

Toolbox Add-on サンプルコード

Toolbox Add-onライブラリを自身のアプリケーションに統合するためのサンプル・コードです。
C/C++、C#、PythonでPDFファイル内容への低レベルアクセス(処理)をアプリケーションに統合できます。
 INFO:
希望言語のコードサンプルを選択してダウンロードしてください。
サンプル・コードは特定の機能のToolbox Add-onライブラリをプロジェクトに統合する方法を示しています。
各サンプル・コードにはそれを実行してひとつまたは複数のファイルを処理する方法について説明したREADMEファイルが付属しています。
 TIP:
ご希望のサンプルが見つからない場合は、お問い合わせページからお知らせください。

アノテーション(注釈)

アノテーションを追加

入力PDFの内容を出力PDFにコピーして、コピーされた出力PDFにアノテーションを追加します。


サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))
{
    // Create output document
    using Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite);
    using Document outDoc = Document.Create(outStream, inDoc.Conformance, null);
// Copy document-wide data
CopyDocumentData(inDoc, outDoc);
// Define page copy options
PageCopyOptions copyOptions = new PageCopyOptions();

// Copy first page and add annotations
Page outPage = CopyAndAddAnnotations(outDoc, inDoc.Pages[0], copyOptions);
// Add the page to the output document's page list
outDoc.Pages.Add(outPage);

// Copy the remaining pages and add to the output document's page list
PageList inPages = inDoc.Pages.GetRange(1, inDoc.Pages.Count - 1);
PageList outPages = PageList.Copy(outDoc, inPages, copyOptions);
outDoc.Pages.AddRange(outPages);
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Metadata
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
private static Page CopyAndAddAnnotations(Document outDoc, Page inPage, PageCopyOptions copyOptions)
{
    // Copy page to output document
    Page outPage = Page.Copy(outDoc, inPage, copyOptions);

    // Make a RGB color space
    ColorSpace rgb = ColorSpace.CreateProcessColorSpace(outDoc, ProcessColorSpaceType.Rgb);

    // Get the page size for positioning annotations
    Size pageSize = outPage.Size;

    // Get the output page's list of annotations for adding annotations
    AnnotationList annotations = outPage.Annotations;

    // Create a sticky note and add to output page's annotations
    Paint green = Paint.Create(outDoc, rgb, new double[] { 0, 1, 0 }, null);
    Point stickyNoteTopLeft = new Point() { X = 10, Y = pageSize.Height - 10 };
    StickyNote stickyNote = StickyNote.Create(outDoc, stickyNoteTopLeft, "Hello world!", green);
    annotations.Add(stickyNote);

    // Create an ellipse and add to output page's annotations
    Paint blue = Paint.Create(outDoc, rgb, new double[] { 0, 0, 1 }, null);
    Paint yellow = Paint.Create(outDoc, rgb, new double[] { 1, 1, 0 }, null);
    Rectangle ellipseBox = new Rectangle() { Left = 10, Bottom = pageSize.Height - 60, Right = 70, Top = pageSize.Height - 20 };
    EllipseAnnotation ellipse = EllipseAnnotation.Create(outDoc, ellipseBox, new Stroke(blue, 1.5), yellow);
    annotations.Add(ellipse);

    // Create a free text and add to output page's annotations
    Paint yellowTransp = Paint.Create(outDoc, rgb, new double[] { 1, 1, 0 }, new Transparency(0.5));
    Rectangle freeTextBox = new Rectangle() { Left = 10, Bottom = pageSize.Height - 170, Right = 120, Top = pageSize.Height - 70 };
    FreeText freeText = FreeText.Create(outDoc, freeTextBox, "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", yellowTransp);
    annotations.Add(freeText);

    // A highlight and a web-link to be fitted on existing page content elements
    Highlight highlight = null;
    WebLink webLink = null;
    // Extract content elements from the input page
    ContentExtractor extractor = new ContentExtractor(inPage.Content);
    foreach (ContentElement element in extractor)
    {
        // Take the first text element
        if (highlight == null && element is TextElement textElement)
        {
            // Get the quadrilaterals of this text element
            QuadrilateralList quadrilaterals = new QuadrilateralList();
            foreach (TextFragment fragment in textElement.Text)
                quadrilaterals.Add(fragment.Transform.TransformRectangle(fragment.BoundingBox));

            // Create a highlight and add to output page's annotations
            highlight = Highlight.CreateFromQuadrilaterals(outDoc, quadrilaterals, yellow);
            annotations.Add(highlight);
        }

        // Take the first image element
        if (webLink == null && element is ImageElement)
        {
            // Get the quadrilateral of this image
            QuadrilateralList quadrilaterals = new QuadrilateralList();
            quadrilaterals.Add(element.Transform.TransformRectangle(element.BoundingBox));

            // Create a web-link and add to the output page's links
            webLink = WebLink.CreateFromQuadrilaterals(outDoc, quadrilaterals, "https://www.pdf-tools.com");
            Paint red = Paint.Create(outDoc, rgb, new double[] { 1, 0, 0 }, null);
            webLink.BorderStyle = new Stroke(red, 1.5);
            outPage.Links.Add(webLink);
        }

        // Exit loop if highlight and webLink have been created
        if (highlight != null && webLink != null)
            break;
    }

    // return the finished page
    return outPage;
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
def copy_and_add_annotations(out_doc: Document, in_page: Page, copy_options: PageCopyOptions):
    # Copy page to output document
    out_page = Page.copy(out_doc, in_page, copy_options)

    # Make a RGB color space
    rgb = ColorSpace.create_process_color_space(out_doc, ProcessColorSpaceType.RGB)

    # Get the page size for positioning annotations
    page_size = out_page.size

    # Get the output page's list of annotations for adding annotations
    annotations = out_page.annotations

    # Create a sticky note and add to output page's annotations
    green = Paint.create(out_doc, rgb, [0.0, 1.0, 0.0], None)
    sticky_note_top_left = Point(x=10.0, y=page_size.height - 10.0)
    sticky_note = StickyNote.create(out_doc, sticky_note_top_left, "Hello world!", green)
    annotations.append(sticky_note)

    # Create an ellipse and add to output page's annotations
    blue = Paint.create(out_doc, rgb, [0.0, 0.0, 1.0], None)
    yellow = Paint.create(out_doc, rgb, [1.0, 1.0, 0.0], None)
    ellipse_box = Rectangle(left=10.0, bottom=page_size.height - 60.0, right=70.0, top=page_size.height - 20.0)
    ellipse = EllipseAnnotation.create(out_doc, ellipse_box, Stroke(blue, 1.5), yellow)
    annotations.append(ellipse)

    # Create a free text and add to output page's annotations
    yellow_transp = Paint.create(out_doc, rgb, [1.0, 1.0, 0.0], Transparency(0.5))
    free_text_box = Rectangle(left=10.0, bottom=page_size.height - 170.0, right=120.0, top=page_size.height - 70.0)
    free_text = FreeText.create(out_doc, free_text_box, "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", yellow_transp)
    annotations.append(free_text)

    # A highlight and a web-link to be fitted on existing page content elements
    highlight = None
    web_link = None
    # Extract content elements from the input page
    extractor = ContentExtractor(in_page.content)
    for element in extractor:
        # Take the first text element
        if highlight is None and isinstance(element, TextElement):
            # Get the quadrilaterals of this text element
            quadrilaterals = QuadrilateralList()
            for fragment in element.text:
                quadrilaterals.append(fragment.transform.transform_rectangle(fragment.bounding_box))

            # Create a highlight and add to output page's annotations
            highlight = Highlight.create_from_quadrilaterals(out_doc, quadrilaterals, yellow)
            annotations.append(highlight)

        # Take the first image element
        if web_link is None and isinstance(element, ImageElement):
            # Get the quadrilateral of this image
            quadrilaterals = QuadrilateralList()
            quadrilaterals.append(element.transform.transform_rectangle(element.bounding_box))

            # Create a web-link and add to the output page's links
            web_link = WebLink.create_from_quadrilaterals(out_doc, quadrilaterals, "https://www.pdf-tools.com")
            red = Paint.create(out_doc, rgb, [1.0, 0.0, 0.0], None)
            web_link.border_style = Stroke(red, 1.5)
            out_page.links.append(web_link)

        # Exit loop if highlight and web-link have been created
        if highlight is not None and web_link is not None:
            break

    return out_page
# Open input document
with io.FileIO(input_file_path, 'rb') as in_stream:
    with Document.open(in_stream, None) as in_doc:
        # Create output document
        with io.FileIO(output_file_path, 'wb+') as output_stream:
            with Document.create(output_stream, in_doc.conformance, None) as out_doc:
                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Define page copy options
                copy_options = PageCopyOptions()

                # Copy first page and add annotations
                out_page = copy_and_add_annotations(out_doc, in_doc.pages[0], copy_options)

                # Add the page to the output document's page list
                out_doc.pages.append(out_page)

                # Copy the remaining pages and add to the output document's page list
                in_pages = in_doc.pages[1:]
                out_pages = PageList.copy(out_doc, in_pages, copy_options)
                out_doc.pages.extend(out_pages)

アノテーションを変更

PDFから"Ellipse"注釈を削除し、新しい注釈リストを新しいFDFファイルにエクスポートします。


サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Stream inFdfStream = new FileStream(inFdfPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.OpenWithFdf(inStream, inFdfStream, null))
{
    // Create output document
    using var outStream = new FileStream(outPath, FileMode.Create, FileAccess.Write);
    using var outFdfStream = new FileStream(outFdfPath, FileMode.Create, FileAccess.Write);
    using var outDoc = Document.CreateWithFdf(outStream, outFdfStream, inDoc.Conformance, null);

    // Copy document-wide data
    CopyDocumentData(inDoc, outDoc);

    FilterAnnotations(inDoc, outDoc);
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Metadata
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
private static void FilterAnnotations(Document inDoc, Document outDoc)
{
    // Define page copy options
    var copyOptions = new PageCopyOptions
    {
        // Remove all annotations: we will add the filtered ones later
        Annotations = CopyStrategy.Remove
    };

    foreach (var inPage in inDoc.Pages)
    {
        // Copy page to output document
        var outPage = Page.Copy(outDoc, inPage, copyOptions);

        // Hold the annotations from the input document
        var inAnnotations = inPage.Annotations;

        // Selectively copy annotations (excluding EllipseAnnotations - like Circle)
        foreach (var inAnnotation in inAnnotations)
        {
            // Skip if the annotation is an EllipseAnnotation
            if (inAnnotation is EllipseAnnotation)
            {
                continue;
            }

            outPage.Annotations.Add(Annotation.Copy(outDoc, inAnnotation));
        }

        // Add the page to the output document
        outDoc.Pages.Add(outPage);
    }
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
def filter_annotations(in_doc: Document, out_doc: Document):
    """Filter annotations and remove 'Ellipse' annotations."""
    # Define page copy options
    copy_options = PageCopyOptions()
    # Remove all annotations: we will add the filtered ones later
    copy_options.annotations = CopyStrategy.REMOVE

    for in_page in in_doc.pages:
        # Copy page to the output document
        out_page = Page.copy(out_doc, in_page, copy_options)

        # Hold the annotations from the input document
        in_annotations = in_page.annotations

        # Selectively copy annotations (excluding EllipseAnnotations - like Circle)
        for in_annotation in in_annotations:
            if not isinstance(in_annotation, EllipseAnnotation):
                out_page.annotations.append(Annotation.copy(out_doc, in_annotation))

        # Add the page to the output document
        out_doc.pages.append(out_page)
# Open input PDF and FDF files
with io.FileIO(input_file_path, "rb") as in_stream:
    with io.FileIO(input_fdf_path, "rb") as in_fdf_stream:
        with Document.open_with_fdf(in_stream, in_fdf_stream, None) as in_doc:
            # Create output PDF and FDF files
            with io.FileIO(output_file_path, "wb+") as out_stream:
                with io.FileIO(output_fdf_path, "wb+") as out_fdf_stream:
                    with Document.create_with_fdf(out_stream, out_fdf_stream, in_doc.conformance, None) as out_doc:
                        # Copy document-wide data
                        copy_document_data(in_doc, out_doc)

                        # Filter and process annotations
                        filter_annotations(in_doc, out_doc)

コンテント(文書内容)を追加

画像をPDFに追加

サイズ指定された画像をページの指定場所に配置します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFを開く
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// 出力PDFを作成
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// ドキュメント全体のデータをコピー
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// コピーオプションを設定
pCopyOptions = PtxPdf_PageCopyOptions_New();

// 入力ページと出力ページのリストを取得
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get the pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get the pages of the output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());

// 先頭ページから選択されたページより前までをコピー
pInPageRange = PtxPdf_PageList_GetRange(pInPageList, 0, iPageNumber - 1);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageRange, _T("Failed to get page range. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageRange = PtxPdf_PageList_Copy(pOutDoc, pInPageRange, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageRange, _T("Failed to copy page range. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_AddRange(pOutPageList, pOutPageRange),
                                  _T("Failed to add page range. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());
Ptx_Release(pInPageRange);
pInPageRange = NULL;
Ptx_Release(pOutPageRange);
pOutPageRange = NULL;

// 選択したページをコピーして画像を追加
pInPage = PtxPdf_PageList_Get(pInPageList, iPageNumber - 1);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPage, _T("Failed to get page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());
pOutPage = PtxPdf_Page_Copy(pOutDoc, pInPage, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPage, _T("Failed to copy page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());
if (addImage(pOutDoc, pOutPage, szImagePath, 150.0, 150.0) != 0)
    goto cleanup;
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_Add(pOutPageList, pOutPage),
                                  _T("Failed to add page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// 残りのページをコピー
pInPageRange = PtxPdf_PageList_GetRange(pInPageList, 1, PtxPdf_PageList_GetCount(pInPageList) - 1);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageRange,
                                 _T("Failed to get page range from input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageRange = PtxPdf_PageList_Copy(pOutDoc, pInPageRange, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageRange,
                                 _T("Failed to copy page range to output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_AddRange(pOutPageList, pOutPageRange),
                                  _T("Failed to add page range to output page list. %s (ErrorCode: 0x%08x).\n"),
                                  szErrorBuff, Ptx_GetLastError());
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // 出力設定
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // メタデータ
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // ビュワー設定
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // 関連ファイル(PDF/A-3およびPDF 2.0のみ)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // プレーンな埋め込みファイル
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
int addImage(TPtxPdf_Document* pOutDoc, TPtxPdf_Page* pOutPage, TCHAR* szImagePath, double x, double y)
{
    TPtxPdfContent_Content*          pContent   = NULL;
    TPtxPdfContent_ContentGenerator* pGenerator = NULL;
    TPtxSys_StreamDescriptor         imageDescriptor;
    FILE*                            pImageStream = NULL;
    TPtxPdfContent_Image*            pImage       = NULL;

    pContent = PtxPdf_Page_GetContent(pOutPage);

    // コンテンツジェネレータを作成
    pGenerator = PtxPdfContent_ContentGenerator_New(pContent, FALSE);

    // 入力パスからの画像読み込み
    pImageStream = _tfopen(szImagePath, _T("rb"));
    PtxSysCreateFILEStreamDescriptor(&imageDescriptor, pImageStream, 0);

    // 画像オブジェクトを作成
    pImage = PtxPdfContent_Image_Create(pOutDoc, &imageDescriptor);

    double dResolution = 150.0;

    TPtxGeomInt_Size size;
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_Image_GetSize(pImage, &size),
                                      _T("Failed to get image size. %s(ErrorCode: 0x%08x).\n"), szErrorBuff,
                                      Ptx_GetLastError());

    // データ行列の矩形を計算
    TPtxGeomReal_Rectangle rect;
    rect.dLeft   = x;
    rect.dBottom = y;
    rect.dRight  = x + (double)size.iWidth * 72.0 / dResolution;
    rect.dTop    = y + (double)size.iHeight * 72.0 / dResolution;

    // 指定されたに矩形画像を描画
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_ContentGenerator_PaintImage(pGenerator, pImage, &rect),
                                      _T("Failed to paint image. %s(ErrorCode: 0x%08x).\n"), szErrorBuff,
                                      Ptx_GetLastError());

cleanup:
    if (pGenerator != NULL)
        PtxPdfContent_ContentGenerator_Close(pGenerator);
    if (pContent != NULL)
        Ptx_Release(pContent);

    return iReturnValue;
}
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFを開く
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// 出力PDFを作成
using (Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // ドキュメント全体のデータをコピー
    CopyDocumentData(inDoc, outDoc);

    // ページコピーオプションを定義
    PageCopyOptions copyOptions = new PageCopyOptions();

    // 先頭ページから選択したページの前までのページをコピーし、出力ドキュメントに追加
    PageList inPageRange = inDoc.Pages.GetRange(0, pageNumber - 1);
    PageList copiedPages = PageList.Copy(outDoc, inPageRange, copyOptions);
    outDoc.Pages.AddRange(copiedPages);

    // 選択したページをコピーし、画像を追加して出力ドキュメントに追加
    Page outPage = Page.Copy(outDoc, inDoc.Pages[pageNumber - 1], copyOptions);
    AddImage(outDoc, outPage, imagePath, 150, 150);
    outDoc.Pages.Add(outPage);

    // 残りのページをコピーして出力ドキュメントに追加
    inPageRange = inDoc.Pages.GetRange(pageNumber, inDoc.Pages.Count - pageNumber);
    copiedPages = PageList.Copy(outDoc, inPageRange, copyOptions);
    outDoc.Pages.AddRange(copiedPages);
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // ドキュメント全体のデータをコピー

    // 出力設定
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // メタデータ
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // ビュワー設定
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // 関連ファイル(PDF/A-3およびPDF 2.0のみ)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // プレーンな埋め込みファイル
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
private static void AddImage(Document document, Page page, string imagePath, double x, double y)
{
    // コンテンツジェネレータを作成
    using ContentGenerator generator = new ContentGenerator(page.Content, false);

    // 入力パスからの画像読み込み
    using Stream inImage = new FileStream(imagePath, FileMode.Open, FileAccess.Read);

    // 画像オブジェクトを作成
    Image image = Image.Create(document, inImage);
    double resolution = 150;

    // 画像の矩形を計算
    PdfTools.Toolbox.Geometry.Integer.Size size = image.Size;
    Rectangle rect = new Rectangle
    {
        Left = x,
        Bottom = y,
        Right = x + size.Width * 72 / resolution,
        Top = y + size.Height * 72 / resolution
    };

    // 指定された矩形に画像を描画
    generator.PaintImage(image, rect);
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))		
def add_image(document: Document, page: Page, image_path: str, x: float, y: float):
    # Create content generator
    with ContentGenerator(page.content, False) as generator:

        # Load image from input path
        with io.FileIO(image_path, 'rb') as in_image_stream:
            # Create image object
            image = Image.create(document, in_image_stream)
            resolution = 150

            # Calculate rectangle for image
            size = image.size
            rect = Rectangle(
                left=x,
                bottom=y,
                right=x + size.width * 72 / resolution,
                top=y + size.height * 72 / resolution
            )

            # Paint image into the specified rectangle
            generator.paint_image(image, rect)		
# Open input document
with io.FileIO(input_file_path, 'rb') as in_stream:
    with Document.open(in_stream, None) as in_doc:

        # Create output document
        with io.FileIO(output_file_path, 'wb+') as output_stream:
            with Document.create(output_stream, in_doc.conformance, None) as out_doc:

                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Define page copy options
                copy_options = PageCopyOptions()

                # Copy pages preceding selected page and append to output document
                if page_number > 1:
                    in_page_range = in_doc.pages[:page_number - 1]
                    copied_pages = PageList.copy(out_doc, in_page_range, copy_options)
                    out_doc.pages.extend(copied_pages)

                # Copy selected page, add image, and append to output document
                out_page = Page.copy(out_doc, in_doc.pages[page_number - 1], copy_options)
                add_image(out_doc, out_page, image_path, 150, 150)
                out_doc.pages.append(out_page)

                # Copy remaining pages and append to output document
                in_page_range = in_doc.pages[page_number:]
                copied_pages = PageList.copy(out_doc, in_page_range, copy_options)
                out_doc.pages.extend(copied_pages)		

マスク画像をPDFに追加

ページ上の指定した位置に長方形のマスク画像を配置します。
マスク画像は、画像をピクセル単位で塗りつぶしたりマスクしたりするステンシルマスクです。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFを開く
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(_T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());

// 出力PDFを作成
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(_T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());

// ドキュメント全体のデータをコピー
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// デバイス色空間を取得
TPtxPdfContent_ColorSpace* pColorSpace =
    PtxPdfContent_ColorSpace_CreateProcessColorSpace(pOutDoc, ePtxPdfContent_ProcessColorSpaceType_Rgb);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pColorSpace, _T("Failed to get the device color space. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());

// RGBカラー値を選択
double color[] = {1.0, 0.0, 0.0};
size_t nColor  = sizeof(color) / sizeof(double);

// 描画オブジェクトを作成
pPaint = PtxPdfContent_Paint_Create(pOutDoc, pColorSpace, color, nColor, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pPaint, _T("Failed to create a transparent paint. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());

// コピーオプションを設定
pCopyOptions = PtxPdf_PageCopyOptions_New();

// 入力ページと出力ページのリストを取得
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get the pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get the pages of the output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());

// 最初のページをコピーして画像マスクを追加
pInPage = PtxPdf_PageList_Get(pInPageList, 0);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPage, _T("Failed to get page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());
pOutPage = PtxPdf_Page_Copy(pOutDoc, pInPage, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPage, _T("Failed to copy page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());
if (addImageMask(pOutDoc, pOutPage, szImageMaskPath, 250, 150) != 0)
    goto cleanup;
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_Add(pOutPageList, pOutPage),
                                  _T("Failed to add page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// 残りのページをコピー
pInPageRange = PtxPdf_PageList_GetRange(pInPageList, 1, PtxPdf_PageList_GetCount(pInPageList) - 1);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageRange,
                                 _T("Failed to get page range from input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageRange = PtxPdf_PageList_Copy(pOutDoc, pInPageRange, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageRange,
                                 _T("Failed to copy page range to output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_AddRange(pOutPageList, pOutPageRange),
                                  _T("Failed to add page range to output page list. %s (ErrorCode: 0x%08x).\n"),
                                  szErrorBuff, Ptx_GetLastError());
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // 出力設定
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // メタデータ
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // ビュワー設定
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // 関連ファイル (PDF/A-3およびPDF2.0のみ)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // プレーンな埋め込みファイル
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
int addImageMask(TPtxPdf_Document* pOutDoc, TPtxPdf_Page* pOutPage, TCHAR* szImageMaskPath, double x, double y)
{
    TPtxPdfContent_Content*          pContent     = NULL;
    TPtxPdfContent_ContentGenerator* pGenerator   = NULL;
    FILE*                            pImageStream = NULL;
    TPtxSys_StreamDescriptor         imageDescriptor;
    TPtxPdfContent_ImageMask*        pImageMask = NULL;

    pContent = PtxPdf_Page_GetContent(pOutPage);

    // コンテンツジェネレータを作成
    pGenerator = PtxPdfContent_ContentGenerator_New(pContent, FALSE);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pGenerator, _T("Failed to create a content generator. %s (ErrorCode: 0x%08x).\n"),
                                     szErrorBuff, Ptx_GetLastError());

    // 入力パスからの画像読み込み
    pImageStream = _tfopen(szImageMaskPath, _T("rb"));
    GOTO_CLEANUP_IF_NULL(pImageStream, _T("Failed to open image mask file \"%s\".\n"), szImageMaskPath);
    PtxSysCreateFILEStreamDescriptor(&imageDescriptor, pImageStream, 0);

    // 画像マスクオブジェクトを作成
    pImageMask = PtxPdfContent_ImageMask_Create(pOutDoc, &imageDescriptor);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pImageMask, _T("Failed to create image mask obejct. %s (ErrorCode: 0x%08x).\n"),
                                     szErrorBuff, Ptx_GetLastError());

    double           dResolution = 150.0;
    TPtxGeomInt_Size size;
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_ImageMask_GetSize(pImageMask, &size),
                                      _T("Failed to get image mask size. %s(ErrorCode: 0x%08x).\n"), szErrorBuff,
                                      Ptx_GetLastError());

    // データ行列の矩形を計算
    TPtxGeomReal_Rectangle rect;
    rect.dLeft   = x;
    rect.dBottom = y;
    rect.dRight  = x + (double)size.iWidth * 72.0 / dResolution;
    rect.dTop    = y + (double)size.iHeight * 72.0 / dResolution;

    // 指定された矩形に画像マスクを描画
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(
        PtxPdfContent_ContentGenerator_PaintImageMask(pGenerator, pImageMask, &rect, pPaint),
        _T("Failed to paint image mask. %s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());

cleanup:
    if (pGenerator != NULL)
        PtxPdfContent_ContentGenerator_Close(pGenerator);
    if (pContent != NULL)
        Ptx_Release(pContent);

    return iReturnValue;
}
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFを開く
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// 出力PDFを作成
using (Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // ドキュメント全体のデータをコピー
    CopyDocumentData(inDoc, outDoc);

    // デバイス色空間を取得
    ColorSpace colorSpace = ColorSpace.CreateProcessColorSpace(outDoc, ProcessColorSpaceType.Rgb);

    // 描画オブジェクトを作成
    paint = Paint.Create(outDoc, colorSpace, new double[] { 1.0, 0.0, 0.0 }, null);

    // ページのコピーオプションを定義
    PageCopyOptions copyOptions = new PageCopyOptions();

    // 最初のページをコピーし、画像マスクを追加して出力ドキュメントに追加
    Page outPage = Page.Copy(outDoc, inDoc.Pages[0], copyOptions);
    AddImageMask(outDoc, outPage, imageMaskPath, 250, 150);
    outDoc.Pages.Add(outPage);

    // 残りのページをコピーして出力ドキュメントに追加
    PageList inPageRange = inDoc.Pages.GetRange(1, inDoc.Pages.Count - 1);
    PageList copiedPages = PageList.Copy(outDoc, inPageRange, copyOptions);
    outDoc.Pages.AddRange(copiedPages);
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // ドキュメント全体のデータをコピー

    // 出力設定
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // メタデータ
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // ビュワー設定
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // 関連ファイル (PDF/A-3およびPDF2.0のみ)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // プレーンな埋め込みファイル
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
    private static void AddImageMask(Document document, Page outPage, string imagePath, 
        double x, double y)
    {
        // コンテンツジェネレータを作成
        using ContentGenerator generator = new ContentGenerator(outPage.Content, false);

        // 入力パスからの画像読み込み
        using Stream inImage = new FileStream(imagePath, FileMode.Open, FileAccess.Read);

        // 画像マスクオブジェクトを作成
        ImageMask imageMask = ImageMask.Create(document, inImage);
        double resolution = 150;

        // 画像の矩形を計算
        PdfTools.Toolbox.Geometry.Integer.Size size = imageMask.Size;
        Rectangle rect = new Rectangle
        {
            Left = x,
            Bottom = y,
            Right = x + size.Width * 72 / resolution,
            Top = y + size.Height * 72 / resolution
        };

        // 指定された四角形に画像マスクを描画
        generator.PaintImageMask(imageMask, rect, paint);
    }

文字列をPDFに追加

PDFドキュメントの先頭ページの指定された位置にテキストを追加します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFをオープン
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// 出力PDFを作成
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// 出力PDFに埋め込みフォントを作成
pFont = PtxPdfContent_Font_CreateFromSystem(pOutDoc, _T("Arial"), _T("Italic"), TRUE);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pFont, _T("Failed to create font. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());

// ドキュメント全体のデータをコピー
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// コピーオプションを設定
pCopyOptions = PtxPdf_PageCopyOptions_New();

// 入力PDFと出力PDFのページリストを取得
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get the pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get the pages of the output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());

// 先頭ページをコピー
pInPage = PtxPdf_PageList_Get(pInPageList, 0);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPage, _T("Failed to get the first page. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPage = PtxPdf_Page_Copy(pOutDoc, pInPage, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPage, _T("Failed to copy page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());

// コピーしたページにテキストを追加
if (addText(pOutDoc, pOutPage, szTextString, pFont, 15) != 0)
    goto cleanup;

// 出力PDFにページを追加
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_Add(pOutPageList, pOutPage),
                                  _T("Failed to add page to output document. %s (ErrorCode: 0x%08x).\n"),
                                  szErrorBuff, Ptx_GetLastError());

// 入力から残りのページを取得
pInPageRange = PtxPdf_PageList_GetRange(pInPageList, 1, PtxPdf_PageList_GetCount(pInPageList) - 1);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageRange,
                                 _T("Failed to get page range from input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());

// 取得した(残りの)ページを出力にコピー
pOutPageRange = PtxPdf_PageList_Copy(pOutDoc, pInPageRange, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageRange,
                                 _T("Failed to copy page range to output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());

// コピーしたページを出力ドキュメントに追加
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_AddRange(pOutPageList, pOutPageRange),
                                  _T("Failed to add page range to output page list. %s (ErrorCode: 0x%08x).\n"),
                                  szErrorBuff, Ptx_GetLastError());
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // 出力設定
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // メタデータ
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // ビュワー設定
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // 関連ファイル(PDF/A-3およびPDF 2.0のみ)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // プレーンな埋め込みファイル
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
int addText(TPtxPdf_Document* pOutDoc, TPtxPdf_Page* pOutPage, TCHAR* szTextString, TPtxPdfContent_Font* pFont,
            double dFontSize)
{
    TPtxPdfContent_Content*          pContent       = NULL;
    TPtxPdfContent_ContentGenerator* pGenerator     = NULL;
    TPtxPdfContent_Text*             pText          = NULL;
    TPtxPdfContent_TextGenerator*    pTextGenerator = NULL;
    TPtxGeomReal_Size                size;
    TPtxGeomReal_Point               position;
    double                           dFontAscent;

    pContent = PtxPdf_Page_GetContent(pOutPage);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pContent, _T("Failed to get content of output file. %s (ErrorCode: 0x%08x).\n"),
                                     szErrorBuff, Ptx_GetLastError());

    // コンテンツジェネレータを作成
    pGenerator = PtxPdfContent_ContentGenerator_New(pContent, FALSE);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pGenerator, _T("Failed to create a content generator. %s (ErrorCode: 0x%08x).\n"),
                                     szErrorBuff, Ptx_GetLastError());

    // テキストオブジェクトを作成
    pText = PtxPdfContent_Text_Create(pOutDoc);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pText, _T("Failed to create text object. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                     Ptx_GetLastError());

    // テキストジェネレータを作成
    pTextGenerator = PtxPdfContent_TextGenerator_New(pText, pFont, dFontSize, NULL);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pTextGenerator, _T("Failed to create a text generator. %s (ErrorCode: 0x%08x).\n"),
                                     szErrorBuff, Ptx_GetLastError());

    // 出力ページサイズを取得
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Page_GetSize(pOutPage, &size),
                                      _T("Failed to read page size. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                      Ptx_GetLastError());

    dFontAscent = PtxPdfContent_Font_GetAscent(pFont);
    GOTO_CLEANUP_IF_ZERO_PRINT_ERROR(dFontAscent, _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());

    // 位置を計算
    position.dX = dBorder;
    position.dY = size.dHeight - dBorder - dFontSize * dFontAscent;

    // 位置に移動
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_TextGenerator_MoveTo(pTextGenerator, &position),
                                      _T("Failed to move to position. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                      Ptx_GetLastError());
    // 指定されたテキスト文字列を追加
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_TextGenerator_ShowLine(pTextGenerator, szTextString),
                                      _T("Failed to add text string. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                      Ptx_GetLastError());
    // テキストジェネレータを閉じる
    PtxPdfContent_TextGenerator_Close(pTextGenerator);
    pTextGenerator = NULL;

    // 配置されたテキストを描画
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_ContentGenerator_PaintText(pGenerator, pText),
                                      _T("Failed to paint the positioned text. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                      Ptx_GetLastError());

cleanup:
    if (pTextGenerator != NULL)
        PtxPdfContent_TextGenerator_Close(pTextGenerator);
    if (pText != NULL)
        Ptx_Release(pText);
    if (pGenerator != NULL)
        PtxPdfContent_ContentGenerator_Close(pGenerator);
    if (pContent != NULL)
        Ptx_Release(pContent);

    return iReturnValue;
}
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFを開く
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// Create output document
using (Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // ドキュメント全体のデータをコピー
    CopyDocumentData(inDoc, outDoc);

    // フォントを作成
    font = Font.CreateFromSystem(outDoc, "Arial", "Italic", true);

    // ページのコピーオプションを定義
    PageCopyOptions copyOptions = new PageCopyOptions();

    // 先頭のページをコピーし、そこにテキストを追加して出力ドキュメントに追加
    Page outPage = Page.Copy(outDoc, inDoc.Pages[0], copyOptions);
    AddText(outDoc, outPage, textString);
    outDoc.Pages.Add(outPage);

    // 残りのページをコピーして出力ドキュメントに追加
    PageList inPageRange = inDoc.Pages.GetRange(1, inDoc.Pages.Count - 1);
    PageList copiedPages = PageList.Copy(outDoc, inPageRange, copyOptions);
    outDoc.Pages.AddRange(copiedPages);
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // ドキュメント全体のデータをコピー

    // 入力設定
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // メタデータ
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // ビュワー設定
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // 関連ファイル(PDF/A-3およびPDF 2.0のみ)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // プレーンな埋め込みファイル
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
private static void AddText(Document outputDoc, Page outPage, string textString)
{
    // コンテンツジェネレータとテキストオブジェクトを作成
    using ContentGenerator gen = new ContentGenerator(outPage.Content, false);
    Text text = Text.Create(outputDoc);

    // テキストジェネレータを作成
    using (TextGenerator textGenerator = new TextGenerator(text, font, fontSize, null))
    {
        // 位置を計算
        Point position = new Point
        {
            X = border,
            Y = outPage.Size.Height - border - fontSize * font.Ascent
        };

        // 位置に移動
        textGenerator.MoveTo(position);
        // 指定されたテキスト文字列を追加
        textGenerator.ShowLine(textString);
    }
    // 配置されたテキストを描画
    gen.PaintText(text);
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))		
def add_text(output_doc: Document, output_page: Page, text_string: str):
    # Create content generator and text object
    with ContentGenerator(output_page.content, False) as gen:
        text = Text.create(output_doc)

        # Create text generator
        with TextGenerator(text, font, font_size, None) as textGenerator:
            # Calculate position
            position = Point(border, output_page.size.height - border - font_size * font.ascent)

            # Move to position
            textGenerator.move_to(position)
            # Add given text string
            textGenerator.show_line(text_string)

        # Paint the positioned text
        gen.paint_text(text)		
# Define global variables
border = 40.0
font_size = 15.0

# Open input document
with io.FileIO(input_file_path, 'rb') as in_stream:
    with Document.open(in_stream, None) as input_document:

        # Create output document
        with io.FileIO(output_file_path, 'wb+') as output_stream:
            with Document.create(output_stream, input_document.conformance, None) as output_document:

                # Copy document-wide data
                copy_document_data(input_document, output_document)

                # Create a font
                font = Font.create_from_system(output_document, "Arial", "Italic", True)

                # Define page copy options
                copy_options = PageCopyOptions()

                # Copy first page, add text, and append to output document
                out_page = Page.copy(output_document, input_document.pages[0], copy_options)
                add_text(output_document, out_page, text_string)
                output_document.pages.append(out_page)

                # Copy remaining pages and append to output document
                inPageRange = input_document.pages[1:]
                copied_pages = PageList.copy(output_document, inPageRange, copy_options)
                output_document.pages.extend(copied_pages)		

Path(パス)をPDFに追加

既存PDFのページに線を描画します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFを開く
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// 出力PDFを作成
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// ドキュメント全体のデータをコピー
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// コピーオプションを設定
pCopyOptions = PtxPdf_PageCopyOptions_New();

// 入力の全ページを繰り返す
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get the pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get the pages of the output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
for (int iPage = 1; iPage <= PtxPdf_PageList_GetCount(pInPageList); iPage++)
{
    pInPage = PtxPdf_PageList_Get(pInPageList, iPage - 1);

    // 入力から出力にページをコピー
    pOutPage = PtxPdf_Page_Copy(pOutDoc, pInPage, pCopyOptions);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPage,
                                     _T("Failed to copy pages from input to output. %s (ErrorCode: 0x%08x).\n"),
                                     szErrorBuff, Ptx_GetLastError());
    PtxPdf_Page_GetSize(pOutPage, &size);

    // 先頭のページにテキストを追加
    if (addLine(pOutDoc, pOutPage) == 1)
    {
        goto cleanup;
    }

    // 出力ドキュメントにページを追加
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_Add(pOutPageList, pOutPage),
                                      _T("Failed to add page to output document. %s (ErrorCode: 0x%08x).\n"),
                                      szErrorBuff, Ptx_GetLastError());

    if (pOutPage != NULL)
    {
        Ptx_Release(pOutPage);
        pOutPage = NULL;
    }

    if (pInPage != NULL)
    {
        Ptx_Release(pInPage);
        pInPage = NULL;
    }
}
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // 出力設定
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // メタデータ
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // ビュワー設定
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // 関連ファイル (PDF/A-3およびPDF 2.0のみ)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // プレーンな埋め込みファイル
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
int addLine(TPtxPdf_Document* pOutDoc, TPtxPdf_Page* pOutPage)
{
    TPtxPdfContent_Content*          pContent             = NULL;
    TPtxPdfContent_ContentGenerator* pGenerator           = NULL;
    TPtxPdfContent_Path*             pPath                = NULL;
    TPtxPdfContent_PathGenerator*    pPathGenerator       = NULL;
    TPtxPdfContent_ColorSpace*       pDeviceRgbColorSpace = NULL;
    double                           aColor[3];
    TPtxPdfContent_Paint*            pPaint = NULL;
    TPtxPdfContent_Stroke*           pStroke;
    TPtxGeomReal_Size                pageSize;
    TPtxGeomReal_Point               point;

    pContent = PtxPdf_Page_GetContent(pOutPage);
    PtxPdf_Page_GetSize(pOutPage, &pageSize);

    // コンテンツジェネレータを作成
    pGenerator = PtxPdfContent_ContentGenerator_New(pContent, FALSE);
    GOTO_CLEANUP_IF_NULL(pGenerator, szErrorBuff, Ptx_GetLastError());

    // パス(ベクターグラフィック)を作成
    pPath = PtxPdfContent_Path_New();
    GOTO_CLEANUP_IF_NULL(pPath, szErrorBuff, Ptx_GetLastError());

    // パスジェネレータを作成
    pPathGenerator = PtxPdfContent_PathGenerator_New(pPath);
    GOTO_CLEANUP_IF_NULL(pPathGenerator, szErrorBuff, Ptx_GetLastError());

    // ページ全体に斜めの線を描画
    point.dX = 10.0;
    point.dY = 10.0;
    GOTO_CLEANUP_IF_FALSE(PtxPdfContent_PathGenerator_MoveTo(pPathGenerator, &point), szErrorBuff, Ptx_GetLastError());
    point.dX = pageSize.dWidth - 10.0;
    point.dY = pageSize.dHeight - 10.0;
    GOTO_CLEANUP_IF_FALSE(PtxPdfContent_PathGenerator_LineTo(pPathGenerator, &point), szErrorBuff, Ptx_GetLastError());

    // パスを終了するためにパスジェネレーターを閉じる
    PtxPdfContent_PathGenerator_Close(pPathGenerator);
    pPathGenerator = NULL;

    // RGBカラースペースを作成
    pDeviceRgbColorSpace =
        PtxPdfContent_ColorSpace_CreateProcessColorSpace(pOutDoc, ePtxPdfContent_ProcessColorSpaceType_Rgb);
    GOTO_CLEANUP_IF_NULL(pDeviceRgbColorSpace, szErrorBuff, Ptx_GetLastError());

    // 赤色で初期化
    aColor[0] = 1.0;
    aColor[1] = 0.0;
    aColor[2] = 0.0;

    // 描画オブジェクトを作成
    pPaint =
        PtxPdfContent_Paint_Create(pOutDoc, pDeviceRgbColorSpace, aColor, sizeof(aColor) / sizeof(aColor[0]), NULL);
    GOTO_CLEANUP_IF_NULL(pPaint, szErrorBuff, Ptx_GetLastError());

    // 指定されたペイントと線幅でストロークパラメータを設定
    pStroke = PtxPdfContent_Stroke_New(pPaint, 10.0);
    GOTO_CLEANUP_IF_NULL(pStroke, szErrorBuff, Ptx_GetLastError());

    // ページにパスを描画
    GOTO_CLEANUP_IF_FALSE(PtxPdfContent_ContentGenerator_PaintPath(pGenerator, pPath, NULL, pStroke), szErrorBuff,
                          Ptx_GetLastError());

cleanup:
    if (pPathGenerator != NULL)
        PtxPdfContent_PathGenerator_Close(pPathGenerator);
    if (pGenerator != NULL)
        PtxPdfContent_ContentGenerator_Close(pGenerator);
    if (pContent != NULL)
        Ptx_Release(pContent);

    return iReturnValue;
}
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFを開く
using (System.IO.Stream inStream = new System.IO.FileStream(inPath, System.IO.FileMode.Open, System.IO.FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// 出力PDFを作成
using (System.IO.Stream outStream = new System.IO.FileStream(outPath, System.IO.FileMode.Create, System.IO.FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // ドキュメント全体のデータをコピー
    CopyDocumentData(inDoc, outDoc);

    // ページコピーオプションを定義
    PageCopyOptions copyOptions = new PageCopyOptions();

    // 入力PDFからすべてのページをコピー
    foreach (Page inPage in inDoc.Pages)
    {
        Page outPage = Page.Copy(outDoc, inPage, copyOptions);

        // 線分をページに描画
        AddLine(outDoc, outPage);

        // ページを出力PDFに追加
        outDoc.Pages.Add(outPage);
    }
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // ドキュメント全体のデータをコピー

    // 出力設定
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // メタデータ
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // ビュワー設定
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // 関連ファイル (PDF/A-3およびPDF2.0のみ)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // プレーンな埋め込みファイル
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
private static void AddLine(Document document, Page page)
{
    // コンテンツジェネレータを作成
    using ContentGenerator generator = new ContentGenerator(page.Content, false);

    // パス(ベクターグラフィック)を作成
    Path path = new Path();
    using (PathGenerator pathGenerator = new PathGenerator(path))
    {
        // ページ全体に斜めの線を描画
        Size pageSize = page.Size;
        pathGenerator.MoveTo(new Point() { X = 10.0, Y = 10.0 });
        pathGenerator.LineTo(new Point() { X = pageSize.Width - 10.0, Y = pageSize.Height - 10.0 });
    }

    // RGBカラースペースを作成
    ColorSpace deviceRgbColorSpace = ColorSpace.CreateProcessColorSpace(document, ProcessColorSpaceType.Rgb);

    // 赤色を作成
    double[] color = new double[] { 1.0, 0.0, 0.0 };

    // ペイントオブジェクトを作成
    Paint paint = Paint.Create(document, deviceRgbColorSpace, color, null);

    // 指定されたペイントと線幅でストロークパラメータを作成
    Stroke stroke = new Stroke(paint, 10.0);

    // ページにパスを描画
    generator.PaintPath(path, null, stroke);
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
def add_line(out_doc: Document, page: Page):
    # Extract content generator
    with ContentGenerator(page.content, False) as generator:

        # Create a path
        path = Path()
        with PathGenerator(path) as path_generator:
            # Draw a line diagonally across the page
            page_size = page.size
            path_generator.move_to(Point(x = 10.0, y = 10.0))
            path_generator.line_to(Point(x = page_size.width - 10.0, y=page_size.height - 10.0))

        # Create a RGB color space
        device_rgb_color_space = ColorSpace.create_process_color_space(out_doc, ProcessColorSpaceType.RGB)

        # Create a red color
        red = [1.0, 0.0, 0.0]

        #  Create a paint
        paint = Paint.create(out_doc, device_rgb_color_space, red, None)

        # Create stroking parameters with given paint and line width
        stroke = Stroke(paint, 10.0)

        # Draw the path onto the page
        generator.paint_path(path, None, stroke)
# Open input document
with io.FileIO(input_file_path, 'rb') as in_stream:
    with Document.open(in_stream, None) as in_doc:

        # Create output document
        with io.FileIO(output_file_path, 'wb+') as output_stream:
            with Document.create(output_stream, in_doc.conformance, None) as out_doc:

                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Define page copy options
                copy_options = PageCopyOptions()

                # Copy all pages from input document
                for in_page in in_doc.pages:
                    out_page = Page.copy(out_doc, in_page, copy_options)

                    # Add a line
                    add_line(out_doc, out_page)

                    # Add page to output document
                    out_doc.pages.append(out_page)

コンテント(文書内容)を変更

グリフ(文字)をPDFから削除

入力PDFの文字列を出力PDFにコピーする際に、先頭2文字を削除してから出力PDFに格納します。


サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Pyhon)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// 入力PDFを開く
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// 出力PDFを生成
using (Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // ドキュメント全体のデータをコピー
    CopyDocumentData(inDoc, outDoc);

    // 各ページを処理
    foreach (var inPage in inDoc.Pages)
    {
        // 空の出力ページを作成
        Page outPage = Page.Create(outDoc, inPage.Size);
        // 入力から出力にページコンテンツをコピーし、グリフを削除
        CopyContentAndRemoveGlyphs(inPage.Content, outPage.Content, outDoc);
        // 新しいページを出力ドキュメントのページリストに追加
        outDoc.Pages.Add(outPage);
    }
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // ドキュメント全体のデータをコピー

    // 出力設定
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // メタデータ
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // ビュワー設定
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // 関連ファイル(PDF/A-3およびPDF 2.0のみ)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // プレーンな埋め込みファイル
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
private static void CopyContentAndRemoveGlyphs(Content inContent, Content outContent, Document outDoc)
{
    // コンテンツ抽出ツールとコンテンツジェネレータを使用してコンテンツをコピー
    ContentExtractor extractor = new ContentExtractor(inContent);
    using ContentGenerator generator = new ContentGenerator(outContent, false);

    // すべてのコンテンツ要素を反復処理
    foreach (ContentElement inElement in extractor)
    {
        ContentElement outElement;
        // グループ要素の特別な処理
        if (inElement is GroupElement inGroupElement)
        {
            // 空の出力グループ要素を作成
            GroupElement outGroupElement = GroupElement.CopyWithoutContent(outDoc, inGroupElement);
            outElement = outGroupElement;
            // グループ要素のコンテンツに対してCopyContentAndRemoveGlyphs()を再帰的にコール
            CopyContentAndRemoveGlyphs(inGroupElement.Group.Content, outGroupElement.Group.Content, outDoc);
        }
        else
        {
            // コンテンツ要素を出力ドキュメントにコピー
            outElement = ContentElement.Copy(outDoc, inElement);
            if (outElement is TextElement outTextElement)
            {
                // テキスト要素の特別な処理
                Text text = outTextElement.Text;
                // 各テキストフラグメントから最初の2つのグリフを削除
                foreach (var fragment in text)
                {
                    // フラグメントに2つ以上のグリフがあることを確認
                    if (fragment.Count > 2)
                    {
                        // RemoveAtを2回コール
                        fragment.RemoveAt(0);
                        fragment.RemoveAt(0);
                    }
                }
            }
        }
        // 完成した出力要素をコンテンツジェネレーターに追加
        generator.AppendContentElement(outElement);
    }
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))		
def copy_content_and_remove_glyphs(in_content: Content, out_content: Content, out_doc: Document):
    """Process content to remove the first two glyphs from text fragments."""
    # Use a content extractor and a content generator to copy content
    extractor = ContentExtractor(in_content)
    with ContentGenerator(out_content, False) as generator:

        # Iterate over all content elements
        for in_element in extractor:
            # Special treatment for group elements
            if isinstance(in_element, GroupElement):
                # Create empty output group element
                out_group_element = GroupElement.copy_without_content(out_doc, in_element)
                out_element = out_group_element
                copy_content_and_remove_glyphs(in_element.group.content, out_group_element.group.content, out_doc)
            else:
                # Copy the content element to the output document
                out_element = ContentElement.copy(out_doc, in_element)
                if isinstance(out_element, TextElement):
                    # Special treatment for text element
                    text = out_element.text
                    # Remove the first two glyphs from each text fragment
                    for fragment in text:
                        # Ensure that the fragment has more than two glyphs
                        if len(fragment) > 2:
                            # Call RemoveAt twice
                            fragment.remove(0)
                            fragment.remove(0)

            # Append the finished output element to the content generator
            generator.append_content_element(out_element)		
# Open input and create output documents
with io.FileIO(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, None) as in_doc:

        # Create output document
        with io.FileIO(output_file_path, "wb+") as out_stream:
            with Document.create(out_stream, in_doc.conformance, None) as out_doc:

                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Process each page
                for in_page in in_doc.pages:
                    # Create empty output page
                    out_page = Page.create(out_doc, in_page.size)
                    # Copy page content from input to output and remove glyphs
                    copy_content_and_remove_glyphs(in_page.content, out_page.content, out_doc)
                    # Add the new page to the output document's page list
                    out_doc.pages.append(out_page)		

PDFからホワイトテキストを削除

PDFの全ページからホワイトテキストを削除します。
リンク、注釈、フォームフィールド、アウトライン、論理構造、埋め込みファイルは破棄されます。


サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// Create output document
using (Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // Copy document-wide data
    CopyDocumentData(inDoc, outDoc);

    // Process each page
    foreach (var inPage in inDoc.Pages)
    {
        // Create empty output page
        Page outPage = Page.Create(outDoc, inPage.Size);
        // Copy page content from input to output
        CopyContent(inPage.Content, outPage.Content, outDoc);
        // Add the new page to the output document's page list
        outDoc.Pages.Add(outPage);
    }
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Metadata
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
private static void CopyContent(Content inContent, Content outContent, Document outDoc)
{
    // Use a content extractor and a content generator to copy content
    ContentExtractor extractor = new ContentExtractor(inContent);
    using ContentGenerator generator = new ContentGenerator(outContent, false);

    // Iterate over all content elements
    foreach (ContentElement inElement in extractor)
    {
        ContentElement outElement;
        // Special treatment for group elements
        if (inElement is GroupElement inGroupElement)
        {
            // Create empty output group element
            GroupElement outGroupElement = GroupElement.CopyWithoutContent(outDoc, inGroupElement);
            outElement = outGroupElement;
            // Call CopyContent() recursively for the group element's content
            CopyContent(inGroupElement.Group.Content, outGroupElement.Group.Content, outDoc);
        }
        else
        {
            // Copy the content element to the output document
            outElement = ContentElement.Copy(outDoc, inElement);
            if (outElement is TextElement outTextElement)
            {
                // Special treatment for text element
                Text text = outTextElement.Text;
                // Remove all those text fragments whose fill and stroke paint is white
                for (int iFragment = text.Count - 1; iFragment >= 0; iFragment--)
                {
                    TextFragment fragment = text[iFragment];
                    if ((fragment.Fill == null || IsWhite(fragment.Fill.Paint)) &&
                        (fragment.Stroke == null || IsWhite(fragment.Stroke.Paint)))
                        text.RemoveAt(iFragment);
                }
                // Prevent appending an empty text element
                if (text.Count == 0)
                    outElement = null;
            }
        }
        // Append the finished output element to the content generator
        if (outElement != null)
            generator.AppendContentElement(outElement);
    }
}
private static bool IsWhite(Paint paint)
{
    ColorSpace colorSpace = paint.ColorSpace;
    if (colorSpace is DeviceGrayColorSpace || colorSpace is CalibratedGrayColorSpace ||
        colorSpace is DeviceRgbColorSpace || colorSpace is CalibratedRgbColorSpace)
    {
        // These color spaces are additive: white is 1.0
        return paint.Color.Min() == 1.0;
    }
    if (colorSpace is DeviceCmykColorSpace)
    {
        // This color space is subtractive: white is 0.0
        return paint.Color.Max() == 0.0;
    }
    return false;
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
def is_white(paint: Paint) -> bool:
    """Determine if a paint is white based on its color space."""
    color_space = paint.color_space
    color = paint.color

    if isinstance(color_space, (DeviceGrayColorSpace, CalibratedGrayColorSpace, DeviceRgbColorSpace, CalibratedRgbColorSpace)):
        # These color spaces are additive: white is 1.0
        return min(color) == 1.0
    if isinstance(color_space, DeviceCmykColorSpace):
        # This color space is subtractive: white is 0.0
        return max(color) == 0.0

    return False
def copy_content_and_remove_white_text(in_content: Content, out_content: Content, out_doc: Document):
    """Process content to remove white text fragments."""
    # Use a content extractor and a content generator to copy content
    extractor = ContentExtractor(in_content)
    with ContentGenerator(out_content, False) as generator:

        # Iterate over all content elements
        for in_element in extractor:
            # Special treatment for group elements
            if isinstance(in_element, GroupElement):
                # Create empty output group element
                out_group_element = GroupElement.copy_without_content(out_doc, in_element)
                out_element = out_group_element
                copy_content_and_remove_white_text(in_element.group.content, out_group_element.group.content, out_doc)
            else:
                # Copy the content element to the output document
                out_element = ContentElement.copy(out_doc, in_element)
                if isinstance(out_element, TextElement):
                    text = out_element.text
                    # Remove all those text fragments whose fill and stroke paint is white
                    for i_fragment in range(len(text) - 1, -1, -1):
                        fragment = text[i_fragment]
                        if ((fragment.fill is None or is_white(fragment.fill.paint)) and
                            (fragment.stroke is None or is_white(fragment.stroke.paint))):
                            text.remove(i_fragment)
                    # Prevent appending an empty text element
                    if len(text) == 0:
                        out_element = None

            # Append the finished output element to the content generator
            if out_element:
                generator.append_content_element(out_element)
# Open input and create output documents
with io.FileIO(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, None) as in_doc:

        # Create output document
        with io.FileIO(output_file_path, "wb+") as out_stream:
            with Document.create(out_stream, in_doc.conformance, None) as out_doc:

                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Process each page
                for in_page in in_doc.pages:
                    # Create empty output page
                    out_page = Page.create(out_doc, in_page.size)
                    # Copy page content from input to output and remove white text
                    copy_content_and_remove_white_text(in_page.content, out_page.content, out_doc)
                    # Add the new page to the output document's page list
                    out_doc.pages.append(out_page)

文書設定

メタデータをPDFに追加

PDFの作成者、タイトル、作成者などのメタデータを設定します。
他の手順として、別のPDFドキュメントのメタデータやXMPファイルのコンテンツを使用することもできます。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document 
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// Create output document
using (Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // Copy document-wide data
    CopyDocumentData(inDoc, outDoc);

    // Set Metadata
    if (args.Length == 3)
    {
        Metadata mdata;

        // Add metadata from a input file 
        using FileStream metaStream = File.OpenRead(mdatafile);
        if (mdatafile.EndsWith(".pdf"))
        {
            // Use the metadata of another PDF file
            using Document metaDoc = Document.Open(metaStream, "");
            mdata = Metadata.Copy(outDoc, metaDoc.Metadata);
        }
        else
        {
            // Use the content of an XMP metadata file 
            mdata = Metadata.Create(outDoc, metaStream);
        }
        outDoc.Metadata = mdata;
    }
    else
    {
        // Set some metadata properties 
        Metadata metadata = outDoc.Metadata;
        metadata.Author = "Your Author";
        metadata.Title = "Your Title";
        metadata.Subject = "Your Subject";
        metadata.Creator = "Your Creator";
    }

    // Define page copy options
    PageCopyOptions copyOptions = new PageCopyOptions();

    // Copy all pages and append to output document
    PageList copiedPages = PageList.Copy(outDoc, inDoc.Pages, copyOptions);
    outDoc.Pages.AddRange(copiedPages);
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data (except metadata)

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
サンプル・プロジェクトの実行手順を参照してください
// Open input document
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// Create output document
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// Copy document-wide data
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// Configure copy options
pCopyOptions = PtxPdf_PageCopyOptions_New();

// Copy all pages
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pCopiedPages = PtxPdf_PageList_Copy(pOutDoc, pInPageList, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pCopiedPages, _T("Failed to copy pages. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());

// Add copied pages to output
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get pages of the output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_AddRange(pOutPageList, pCopiedPages),
                                  _T("Failed to add copied pages to output. %s (ErrorCode: 0x%08x).\n"),
                                  szErrorBuff, Ptx_GetLastError());

if (argc == 4)
{
    // Add metadata from a input file
    pMdataStream = _tfopen(szMdatafile, _T("rb"));
    GOTO_CLEANUP_IF_NULL(pMdataStream, _T("Failed to open metadata file \"%s\".\n"), szMdatafile);
    PtxSysCreateFILEStreamDescriptor(&mdataDescriptor, pMdataStream, 0);

    // Get file extension
    TCHAR* szExt = _tcsrchr(szMdatafile, '.');
    _tcscpy(szExtension, szExt);

    if (_tcscmp(szExtension, _T(".pdf")) == 0)
    {
        // Use the metadata of another PDF file
        TPtxPdf_Document* pMetaDoc = PtxPdf_Document_Open(&mdataDescriptor, _T(""));
        GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pMetaDoc, _T("Failed to open metadata file. %s (ErrorCode: 0x%08x).\n"),
                                         szErrorBuff, Ptx_GetLastError());
        TPtxPdf_Metadata* pMetadata = PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pMetaDoc));
        GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pMetadata, _T("Failed to copy metadata. %s (ErrorCode: 0x%08x)."),
                                         szErrorBuff, Ptx_GetLastError());
        GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Document_SetMetadata(pOutDoc, pMetadata),
                                          _T("Failed to set metadata. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                          Ptx_GetLastError());
    }
    else
    {
        // Use the content of an XMP metadata file
        GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(
            PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Create(pOutDoc, &mdataDescriptor)),
            _T("Failed to set metadata. %s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
    }
}
else
{
    // Set some metadata properties
    TPtxPdf_Metadata* pMetadata = PtxPdf_Document_GetMetadata(pOutDoc);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pMetadata, _T("Failed to get metadata. %s (ErrorCode: 0x%08x).\n"),
                                     szErrorBuff, Ptx_GetLastError());
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Metadata_SetAuthor(pMetadata, _T("Your Author")),
                                      _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Metadata_SetTitle(pMetadata, _T("Your Title")),
                                      _T("%s(ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Metadata_SetSubject(pMetadata, _T("Your Subject")),
                                      _T("%s(ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Metadata_SetCreator(pMetadata, _T("Your Creator")),
                                      _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
}
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    // Copy document-wide data (excluding metadata)

    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // Output intent
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // Viewer settings
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // Plain embedded files
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data (excluding metadata)

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
# Open input document
with io.FileIO(input_file_path, 'rb') as content_pdf_stream:
    with Document.open(content_pdf_stream, None) as content_pdf_document:

        # Create output document
        with io.FileIO(output_file_path, 'wb+') as output_stream:
            with Document.create(output_stream, content_pdf_document.conformance, None) as output_document:
                # Copy document-wide data
                copy_document_data(content_pdf_document, output_document)

                # Set Metadata
                if metadata_file_path is not None:
                    with io.FileIO(metadata_file_path, 'rb') as metadata_stream:
                        if metadata_file_path.endswith(".pdf"):
                            # Use the metadata of another PDF file
                            with Document.open(metadata_stream, "") as meta_doc:
                                mdata = Metadata.copy(output_document, meta_doc.metadata)
                        else:
                            # Use the content of an XMP metadata file
                            mdata = Metadata.create(output_document, metadata_stream)
                else:
                    mdata = output_document.metadata
                    mdata.author = "Your Author"
                    mdata.title = "Your Title"
                    mdata.subject = "Your Subject"
                    mdata.creator = "Your Creator"

                output_document.metadata = mdata

                # Define page copy options
                copy_options = PageCopyOptions()

                # Copy all pages and append to output document
                copied_pages = PageList.copy(output_document, content_pdf_document.pages, copy_options)
                output_document.pages.extend(copied_pages)

フォームフィールドをフラット化

フォーム フィールドの外観をフラット化し、すべてのインタラクティブな要素を破棄します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// Create output document
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// Copy document-wide data
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// Configure copy options: enable form field flattening
pCopyOptions = PtxPdf_PageCopyOptions_New();
PtxPdf_PageCopyOptions_SetFormFields(pCopyOptions, ePtxPdfForms_FormFieldCopyStrategy_Flatten);

// Copy all pages
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pCopiedPages = PtxPdf_PageList_Copy(pOutDoc, pInPageList, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pCopiedPages, _T("Failed to copy pages. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());

// Add copied pages to output
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get pages of the output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_AddRange(pOutPageList, pCopiedPages),
                                  _T("Failed to add copied pages to output. %s (ErrorCode: 0x%08x).\n"),
                                  szErrorBuff, Ptx_GetLastError());
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // Output intent
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // Metadata
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // Viewer settings
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // Plain embedded files
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// Create output document
using (Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // Copy document-wide data
    CopyDocumentData(inDoc, outDoc);

    // Define copy options including form field flattening
    PageCopyOptions copyOptions = new PageCopyOptions();
    copyOptions.FormFields = FormFieldCopyStrategy.Flatten;

    // Copy all pages and append to output document
    PageList copiedPages = PageList.Copy(outDoc, inDoc.Pages, copyOptions);
    outDoc.Pages.AddRange(copiedPages);
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Metadata
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
# Open input document
with io.FileIO(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, None) as in_doc:

        # Create output document
        with io.FileIO(output_file_path, "wb+") as out_stream:
            with Document.create(out_stream, in_doc.conformance, None) as out_doc:

                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Set form field flattening options
                copy_options = PageCopyOptions()
                copy_options.form_fields = FormFieldCopyStrategy.FLATTEN

                # Copy all pages with flattening options
                copied_pages = PageList.copy(out_doc, in_doc.pages, copy_options)
                out_doc.pages.extend(copied_pages)

PDFからページを削除

PDFからページを選択的に削除します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get the pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
int nInPages = PtxPdf_PageList_GetCount(pInPageList);
iStartIndex  = MAX(MIN(nInPages - 1, iStartIndex), 0);
nCount       = MIN(nInPages - iStartIndex, nCount);
GOTO_CLEANUP_IF_FALSE(nCount > 0, _T("lastPage must be greater or equal to firstPage.\n"));

// Create output document
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// Copy document-wide data
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// Configure copy options
pCopyOptions = PtxPdf_PageCopyOptions_New();

// Get page range from input pages
pInPageRange = PtxPdf_PageList_GetRange(pInPageList, iStartIndex, nCount);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageRange,
                                 _T("Failed to get page range from input document. %s (ErrorCode: 0x%08x)\n"),
                                 szErrorBuff, Ptx_GetLastError());

// Copy page range to toutput document
pOutPageRange = PtxPdf_PageList_Copy(pOutDoc, pInPageRange, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageRange, _T("Failed to copy page range. %s (ErrorCode: 0x%08x)\n"),
                                 szErrorBuff, Ptx_GetLastError());

// Get output pages
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get the pages of the output document. %s (ErrorCode: 0x%08x)\n"),
                                 szErrorBuff, Ptx_GetLastError());

// Appende page range to output pages
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_AddRange(pOutPageList, pOutPageRange),
                                  _T("Failed to append page range. %s (ErrorCode: 0x%08x)\n"), szErrorBuff,
                                  Ptx_GetLastError());
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // Output intent
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // Metadata
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // Viewer settings
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // Plain embedded files
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))
{
    startIndex = Math.Max(Math.Min(inDoc.Pages.Count - 1, startIndex), 0);
    count = Math.Min(inDoc.Pages.Count - startIndex, count);
    if (count <= 0)
    {
        Console.WriteLine("lastPage must be greater or equal to firstPage");
        return;
    }

    // Create output document
    using Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite);
    using Document outDoc = Document.Create(outStream, inDoc.Conformance, null);

    // Copy document-wide data
    CopyDocumentData(inDoc, outDoc);

    // Define page copy options
    PageCopyOptions copyOptions = new PageCopyOptions();

    // Get page range from input pages
    PageList inPageRange = inDoc.Pages.GetRange(startIndex, count);

    // Copy page range and append to output document
    PageList outPageRange = PageList.Copy(outDoc, inPageRange, copyOptions);
    outDoc.Pages.AddRange(outPageRange);
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Metadata
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
start_index = int(first_page) - 1
last_page = int(last_page)
count = last_page - start_index

# Open input document
with io.FileIO(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, None) as in_doc:

        # Validate page range
        start_index = max(min(len(in_doc.pages) - 1, start_index), 0)
        count = min(len(in_doc.pages) - start_index, count)
        if count <= 0:
            raise ValueError("lastPage must be greater or equal to firstPage")

        # Create output document
        with io.FileIO(output_file_path, "wb+") as out_stream:
            with Document.create(out_stream, in_doc.conformance, None) as out_doc:

                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Define page copy options
                page_copy_options = PageCopyOptions()

                # Get page range from input pages
                in_page_range = in_doc.pages[start_index:last_page]

                # Copy page range and append to output document
                out_page_range = PageList.copy(out_doc, in_page_range, page_copy_options)
                out_doc.pages.extend(out_page_range)

インポジション

ページを特定のページ形式に合わせる

PDFの各ページを指定されたのページ形式に適合させます。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// Create output document
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// Copy document-wide data
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// Configure copy options
pCopyOptions = PtxPdf_PageCopyOptions_New();

// Copy all pages
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get pages of the output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
for (int iPage = 0; iPage < PtxPdf_PageList_GetCount(pInPageList); iPage++)
{
    TPtxGeomReal_Size pageSize;
    TPtxGeomReal_Size rotatedSize;
    BOOL              bRotate;

    pInPage = PtxPdf_PageList_Get(pInPageList, iPage);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPage, _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());

    pOutPage = NULL;
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Page_GetSize(pInPage, &pageSize), _T("%s (ErrorCode: 0x%08x).\n"),
                                      szErrorBuff, Ptx_GetLastError());

    bRotate = bAllowRotate && (pageSize.dHeight >= pageSize.dWidth) != (targetSize.dHeight >= targetSize.dWidth);
    if (bRotate)
    {
        rotatedSize.dWidth  = pageSize.dHeight;
        rotatedSize.dHeight = pageSize.dHeight;
    }
    else
    {
        rotatedSize = pageSize;
    }

    if (rotatedSize.dWidth == targetSize.dWidth && rotatedSize.dHeight == targetSize.dWidth)
    {
        // If size is correct, copy page only
        pOutPage = PtxPdf_Page_Copy(pOutDoc, pInPage, pCopyOptions);
        GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPage,
                                         _T("Failed to copy pages from input to output. %s (ErrorCode: 0x%08x).\n"),
                                         szErrorBuff, Ptx_GetLastError());

        if (bRotate)
        {
            GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Page_Rotate(pOutPage, ePtxGeom_Rotation_Clockwise),
                                              _T("Failed to rotate page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                              Ptx_GetLastError());
        }
    }
    else
    {
        TPtxPdfContent_Group*        pGroup   = NULL;
        TPtxPdfContent_Content*      pContent = NULL;
        TPtxGeomReal_AffineTransform transform;
        TPtxGeomReal_Point           position;
        TPtxGeomReal_Point           point;

        // Create a new page of correct size and fit existing page onto it
        pOutPage = PtxPdf_Page_Create(pOutDoc, &targetSize);
        GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPage, _T("Failed to create a new page. %s (ErrorCode: 0x%08x).\n"),
                                         szErrorBuff, Ptx_GetLastError());

        // Copy page as group
        pGroup = PtxPdfContent_Group_CopyFromPage(pOutDoc, pInPage, pCopyOptions);
        GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pGroup, _T("Failed to copy page as group. %s (ErrorCode: 0x%08x).\n"),
                                         szErrorBuff, Ptx_GetLastError());

        // Calculate scaling and position of group
        double scale = MIN(targetSize.dWidth / rotatedSize.dWidth, targetSize.dHeight / rotatedSize.dHeight);

        // Calculate position
        position.dX = (targetSize.dWidth - pageSize.dWidth * scale) / 2;
        position.dY = (targetSize.dHeight - pageSize.dHeight * scale) / 2;

        pContent = PtxPdf_Page_GetContent(pOutPage);

        // Create content generator
        pGenerator = PtxPdfContent_ContentGenerator_New(pContent, FALSE);
        GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pGenerator,
                                         _T("Failed to create a content generator. %s (ErrorCode: 0x%08x).\n"),
                                         szErrorBuff, Ptx_GetLastError());

        // Calculate and apply transformation
        GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxGeomReal_AffineTransform_GetIdentity(&transform),
                                          _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
        GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(
            PtxGeomReal_AffineTransform_Translate(&transform, position.dX, position.dY),
            _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
        GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxGeomReal_AffineTransform_Scale(&transform, scale, scale),
                                          _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());

        point.dX = pageSize.dWidth / 2.0;
        point.dY = pageSize.dHeight / 2.0;

        // Rotate input file
        if (bRotate)
        {
            GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxGeomReal_AffineTransform_Rotate(&transform, 90, &point),
                                              _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
        }
        GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_ContentGenerator_Transform(pGenerator, &transform),
                                          _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());

        // Paint form
        GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_ContentGenerator_PaintGroup(pGenerator, pGroup, NULL, NULL),
                                          _T("Failed to paint the group. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                          Ptx_GetLastError());

        PtxPdfContent_ContentGenerator_Close(pGenerator);
        pGenerator = NULL;

        if (pGenerator != NULL)
            Ptx_Release(pGenerator);
        if (pGroup != NULL)
            Ptx_Release(pGroup);
    }

    // Add page to output document
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_Add(pOutPageList, pOutPage),
                                      _T("Failed to add page to output document. %s (ErrorCode: 0x%08x).\n"),
                                      szErrorBuff, Ptx_GetLastError());

    if (pOutPage != NULL)
    {
        Ptx_Release(pOutPage);
        pOutPage = NULL;
    }

    if (pInPage != NULL)
    {
        Ptx_Release(pInPage);
        pInPage = NULL;
    }
}
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // Output intent
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // Metadata
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // Viewer settings
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // Plain embedded files
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// Create output document 
using (Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outStream, inDoc.Conformance, null))
{
    // Copy document-wide data
    CopyDocumentData(inDoc, outDoc);

    // Define page copy options
    PageCopyOptions copyOptions = new PageCopyOptions();

    // Copy pages
    foreach (Page inPage in inDoc.Pages)
    {
        Page outPage = null;
        Size pageSize = inPage.Size;

        bool rotate = AllowRotate &&
            (pageSize.Height >= pageSize.Width) != (TargetSize.Height >= TargetSize.Width);
        Size rotatedSize = pageSize;

        if (rotate)
            rotatedSize = new Size { Width = pageSize.Height, Height = pageSize.Width };

        if (rotatedSize.Width == TargetSize.Width && rotatedSize.Height == TargetSize.Width)
        {
            // If size is correct, copy page only
            outPage = Page.Copy(outDoc, inPage, copyOptions);

            if (rotate)
                outPage.Rotate(Rotation.Clockwise);
        }
        else
        {
            // Create new page of correct size and fit existing page onto it
            outPage = Page.Create(outDoc, TargetSize);

            // Copy page as group
            Group group = Group.CopyFromPage(outDoc, inPage, copyOptions);
            // Calculate scaling and position of group
            double scale = Math.Min(TargetSize.Width / rotatedSize.Width,
                TargetSize.Height / rotatedSize.Height);

            // Calculate position
            Point position = new Point
            {
                X = (TargetSize.Width - pageSize.Width * scale) / 2,
                Y = (TargetSize.Height - pageSize.Height * scale) / 2
            };

            // Create content generator
            using ContentGenerator generator = new ContentGenerator(outPage.Content, false);

            // Calculate and apply transformation
            AffineTransform transform = AffineTransform.Identity;
            transform.Translate(position.X, position.Y);
            transform.Scale(scale, scale);

            Point point = new Point()
            {
                X = pageSize.Width / 2.0,
                Y = pageSize.Height / 2.0
            };

            // Rotate input file 
            if (rotate)
                transform.Rotate(90, point);
            generator.Transform(transform);

            // Paint group
            generator.PaintGroup(group, null, null);
        }
        // Add page to output document 
        outDoc.Pages.Add(outPage);
    }
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Metadata
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
def scale_pages_to_fit(in_doc: Document, out_doc: Document):
    copy_options = PageCopyOptions()

    # Copy pages
    for in_page in in_doc.pages:
        page_size = in_page.size
        rotate = (
            ALLOW_ROTATE
            and (page_size.height >= page_size.width) != (TARGET_SIZE.height >= TARGET_SIZE.width)
        )

        rotated_size = Size(
            width=page_size.height, height=page_size.width
        ) if rotate else page_size

        if rotated_size.width == TARGET_SIZE.width and rotated_size.height == TARGET_SIZE.height:
            # If size is correct, copy page only
            out_page = Page.copy(out_doc, in_page, copy_options)

            if rotate:
                out_page.rotate(90)  # Clockwise rotation
        else:
            # Create new page of correct size and fit existing page onto it
            out_page = Page.create(out_doc, TARGET_SIZE)

            # Copy page as group
            group = Group.copy_from_page(out_doc, in_page, copy_options)
            # Calculate scaling and position of group
            scale = min(TARGET_SIZE.width / rotated_size.width, TARGET_SIZE.height / rotated_size.height)

            # Calculate position
            position = Point(
                x=(TARGET_SIZE.width - page_size.width * scale) / 2,
                y=(TARGET_SIZE.height - page_size.height * scale) / 2,
            )

            # Create content generator
            with ContentGenerator(out_page.content, False) as generator:

                # Calculate and apply transformation
                transform = AffineTransform.get_identity()
                transform.translate(position.x, position.y)
                transform.scale(scale, scale)

                # Rotate input file 
                if rotate:
                    center_point = Point(x=page_size.width / 2, y=page_size.height / 2)
                    transform.rotate(90, center_point)

                # Paint group
                generator.transform(transform)
                generator.paint_group(group, None, None)

        # Add the page to the output document
        out_doc.pages.append(out_page)
# Define global variables
TARGET_SIZE = Size(width=595, height=842)  # A4 portrait
ALLOW_ROTATE = True

# Open input document
with io.FileIO(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, None) as in_doc:

        # Create output document
        with io.FileIO(output_file_path, "wb+") as out_stream:
            with Document.create(out_stream, in_doc.conformance, None) as out_doc:

                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Process and resize pages
                scale_pages_to_fit(in_doc, out_doc)

複数のページを1ページに配置する

PDF4ページを単一ページに配置します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// Create output document
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// Copy document-wide data
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// Configure copy options
pCopyOptions = PtxPdf_PageCopyOptions_New();

// Copy all pages
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get the pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPageList,
                                 _T("Failed to get pages of the output document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
int nPageCount = 0;
for (int iPage = 0; iPage < PtxPdf_PageList_GetCount(pInPageList); iPage++)
{
    pInPage = PtxPdf_PageList_Get(pInPageList, iPage);

    if (nPageCount == nNx * nNy)
    {
        // Add to output document
        PtxPdfContent_ContentGenerator_Close(pGenerator);
        GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_Add(pOutPageList, pOutPage),
                                          _T("Failed to add page to output document. %s (ErrorCode: 0x%08x).\n"),
                                          szErrorBuff, Ptx_GetLastError());
        Ptx_Release(pOutPage);
        pOutPage   = NULL;
        nPageCount = 0;
    }
    if (pOutPage == NULL)
    {
        // Create a new output page
        pOutPage = PtxPdf_Page_Create(pOutDoc, &PageSize);
        GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPage,
                                         _T("Failed to create a new output page. %s (ErrorCode: 0x%08x).\n"),
                                         szErrorBuff, Ptx_GetLastError());
        TPtxPdfContent_Content* pContent = PtxPdf_Page_GetContent(pOutPage);
        pGenerator                       = PtxPdfContent_ContentGenerator_New(pContent, FALSE);
        GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pGenerator,
                                         _T("Failed to create content generator. %s (ErrorCode: 0x%08x).\n"),
                                         szErrorBuff, Ptx_GetLastError());
    }

    // Get area where group has to be
    int x = nPageCount % nNx;
    int y = nNy - (nPageCount / nNx) - 1;

    // Calculate cell size
    TPtxGeomReal_Size cellSize;
    cellSize.dWidth  = (PageSize.dWidth - ((nNx + 1) * dBorder)) / nNx;
    cellSize.dHeight = (PageSize.dHeight - ((nNy + 1) * dBorder)) / nNy;

    // Calculate cell position
    TPtxGeomReal_Point cellPosition;
    cellPosition.dX = dBorder + x * (cellSize.dWidth + dBorder);
    cellPosition.dY = dBorder + y * (cellSize.dHeight + dBorder);

    // Copy page group from input to output
    pGroup = PtxPdfContent_Group_CopyFromPage(pOutDoc, pInPage, pCopyOptions);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(
        pGroup, _T("Failed to copy page group from input to output. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
        Ptx_GetLastError());

    // Calculate group position
    TPtxGeomReal_Size groupSize;
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdfContent_Group_GetSize(pGroup, &groupSize),
                                      _T("%s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());
    double dScale = MIN(cellSize.dWidth / groupSize.dWidth, cellSize.dHeight / groupSize.dHeight);

    // Calculate target size
    TPtxGeomReal_Size targetSize;
    targetSize.dWidth  = groupSize.dWidth * dScale;
    targetSize.dHeight = groupSize.dHeight * dScale;

    // Calculate position
    TPtxGeomReal_Point targetPos;
    targetPos.dX = cellPosition.dX + ((cellSize.dWidth - targetSize.dWidth) / 2);
    targetPos.dY = cellPosition.dY + ((cellSize.dHeight - targetSize.dHeight) / 2);

    // Calculate rectangle
    TPtxGeomReal_Rectangle targetRect;
    targetRect.dLeft   = targetPos.dX;
    targetRect.dBottom = targetPos.dY;
    targetRect.dRight  = targetPos.dX + targetSize.dWidth;
    targetRect.dTop    = targetPos.dY + targetSize.dHeight;

    // Add group to page
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(
        PtxPdfContent_ContentGenerator_PaintGroup(pGenerator, pGroup, &targetRect, NULL),
        _T("Failed to paint the group. %s (ErrorCode: 0x%08x).\n"), szErrorBuff, Ptx_GetLastError());

    if (pGroup != NULL)
    {
        Ptx_Release(pGroup);
        pGroup = NULL;
    }
    if (pInPage != NULL)
    {
        Ptx_Release(pInPage);
        pInPage = NULL;
    }

    nPageCount++;
}

// Add partially filled page
if (pOutPage != NULL)
{
    PtxPdfContent_ContentGenerator_Close(pGenerator);
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_Add(pOutPageList, pOutPage),
                                      _T("Failed to add page to output document. %s (ErrorCode: 0x%08x).\n"),
                                      szErrorBuff, Ptx_GetLastError());
    Ptx_Release(pOutPage);
    pOutPage = NULL;
}
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // Output intent
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // Metadata
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // Viewer settings
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // Plain embedded files
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))
{
    // Create output document 
    using Stream outStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite);
    using Document outDoc = Document.Create(outStream, inDoc.Conformance, null);
    PageList outPages = outDoc.Pages;
    int pageCount = 0;
    ContentGenerator generator = null;
    Page outPage = null;

    // Copy document-wide data
    CopyDocumentData(inDoc, outDoc);

    // Copy all pages from input document
    foreach (Page inPage in inDoc.Pages)
    {
        if (pageCount == Nx * Ny)
        {
            // Add to output document
            generator.Dispose();
            outPages.Add(outPage);
            outPage = null;
            pageCount = 0;
        }
        if (outPage == null)
        {
            // Create a new output page
            outPage = Page.Create(outDoc, PageSize);
            generator = new ContentGenerator(outPage.Content, false);
        }

        // Get area where group has to be
        int x = pageCount % Nx;
        int y = Ny - (pageCount / Nx) - 1;

        // Compute cell size
        Size cellSize = new Size
        {
            Width = (PageSize.Width - ((Nx + 1) * Border)) / Nx,
            Height = (PageSize.Height - ((Ny + 1) * Border)) / Ny
        };

        // Compute cell position
        Point cellPosition = new Point
        {
            X = Border + x * (cellSize.Width + Border),
            Y = Border + y * (cellSize.Height + Border)
        };

        // Define page copy options
        PageCopyOptions copyOptions = new PageCopyOptions();

        // Copy page as group from input to output
        Group group = Group.CopyFromPage(outDoc, inPage, copyOptions);

        // Compute group position 
        Size groupSize = group.Size;
        double scale = Math.Min(cellSize.Width / groupSize.Width,
            cellSize.Height / groupSize.Height);

        // Compute target size
        Size targetSize = new Size
        {
            Width = groupSize.Width * scale,
            Height = groupSize.Height * scale
        };

        // Compute position
        Point targetPos = new Point
        {
            X = cellPosition.X + ((cellSize.Width - targetSize.Width) / 2),
            Y = cellPosition.Y + ((cellSize.Height - targetSize.Height) / 2)
        };

        // Compute rectangle
        Rectangle targetRect = new Rectangle
        {
            Left = targetPos.X,
            Bottom = targetPos.Y,
            Right = targetPos.X + targetSize.Width,
            Top = targetPos.Y + targetSize.Height
        };

        // Add group to page
        generator.PaintGroup(group, targetRect, null);
        pageCount++;
    }
    // Add page
    if (outPage != null)
    {
        generator.Dispose();
        outPages.Add(outPage);
    }
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Metadata
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
# Define global variables
nx = 2
ny = 2
page_size = Size(595.0, 842.0)  # A4 portrait
border = 10.0

# Open input document
with io.FileIO(input_file_path, 'rb') as in_stream:
    with Document.open(in_stream, None) as input_document:

        # Create output document
        with io.FileIO(output_file_path, 'wb+') as output_stream:
            with Document.create(output_stream, input_document.conformance, None) as output_document:
                out_pages = output_document.pages
                page_count = 0
                generator = None
                out_page = None

                # Copy document-wide data
                copy_document_data(input_document, output_document)

                # Copy all pages from input document
                for in_page in input_document.pages:
                    if page_count == nx * ny:
                        # Add to output document
                        generator.__exit__(None, None, None)
                        out_pages.append(out_page)
                        out_page = None
                        page_count = 0
                    if out_page is None:
                        # Create a new output page
                        out_page = Page.create(output_document, page_size)
                        generator = ContentGenerator(out_page.content, False)

                    # Get area where group has to be (// calculates the floor of the division)
                    x = int(page_count % nx)
                    y = int(ny - (page_count // nx) - 1)

                    # Compute cell size
                    cell_width = (page_size.width - ((nx + 1) * border)) / nx
                    cell_height = (page_size.height - ((ny + 1) * border)) / ny

                    # Compute cell position
                    cell_x = border + x * (cell_width + border)
                    cell_y = border + y * (cell_height + border)

                    # Define page copy options
                    copy_options = PageCopyOptions()

                    # Copy page as group from input to output
                    group = Group.copy_from_page(output_document, in_page, copy_options)

                    # Compute group position
                    group_size = group.size
                    scale = min(cell_width / group_size.width, cell_height / group_size.height)

                    # Compute target size
                    target_width = group_size.width * scale
                    target_height = group_size.height * scale

                    # Compute position
                    target_x = cell_x + ((cell_width - target_width) / 2)
                    target_y = cell_y + ((cell_height - target_height) / 2)

                    # Compute rectangle
                    target_rect = Rectangle()
                    target_rect.left = target_x
                    target_rect.bottom = target_y
                    target_rect.right = target_x + target_width
                    target_rect.top = target_y + target_height

                    # Add group to page
                    generator.paint_group(group, target_rect, None)
                    page_count += 1

                # Add page
                if out_page:
                    generator.__exit__(None, None, None)
                    out_pages.append(out_page)

ページの向きを設定する

PDFの指定されたページを90度回転します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// Create output document
pOutStream = _tfopen(szOutPath, _T("wb+"));
GOTO_CLEANUP_IF_NULL(pOutStream, _T("Failed to open output file \"%s\".\n"), szOutPath);
PtxSysCreateFILEStreamDescriptor(&outDescriptor, pOutStream, 0);
iConformance = PtxPdf_Document_GetConformance(pInDoc);
pOutDoc      = PtxPdf_Document_Create(&outDescriptor, &iConformance, NULL);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutDoc, _T("Output file \"%s\" cannot be created. %s (ErrorCode: 0x%08x).\n"),
                                 szOutPath, szErrorBuff, Ptx_GetLastError());

// Copy document-wide data
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(copyDocumentData(pInDoc, pOutDoc),
                                  _T("Failed to copy document-wide data. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());

// Configure copy options
pCopyOptions = PtxPdf_PageCopyOptions_New();

// Copy all pages
pInPageList = PtxPdf_Document_GetPages(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInPageList,
                                 _T("Failed to get the pages of the input document. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
pCopiedPages = PtxPdf_PageList_Copy(pOutDoc, pInPageList, pCopyOptions);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pCopiedPages, _T("Failed to copy pages. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());

// Rotate given pages by 90 degrees
for (int i = 0; i < ARRAY_SIZE(aPageNumbers); i++)
{
    pOutPage = PtxPdf_PageList_Get(pCopiedPages, aPageNumbers[i] - 1);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pOutPage, _T("Failed to get copied page. %s (ErrorCode: 0x%08x).\n"),
                                     szErrorBuff, Ptx_GetLastError());
    GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_Page_Rotate(pOutPage, ePtxGeom_Rotation_Clockwise),
                                      _T("Failed to rotate page. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                      Ptx_GetLastError());
}

// Add pages to output document
pOutPageList = PtxPdf_Document_GetPages(pOutDoc);
GOTO_CLEANUP_IF_FALSE_PRINT_ERROR(PtxPdf_PageList_AddRange(pOutPageList, pCopiedPages),
                                  _T("Failed to add copied pages. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                  Ptx_GetLastError());
int copyDocumentData(TPtxPdf_Document* pInDoc, TPtxPdf_Document* pOutDoc)
{
    TPtxPdf_FileReferenceList* pInFileRefList;
    TPtxPdf_FileReferenceList* pOutFileRefList;

    // Output intent
    if (PtxPdf_Document_GetOutputIntent(pInDoc) != NULL)
        if (PtxPdf_Document_SetOutputIntent(pOutDoc, PtxPdfContent_IccBasedColorSpace_Copy(
                                                         pOutDoc, PtxPdf_Document_GetOutputIntent(pInDoc))) == FALSE)
            return FALSE;

    // Metadata
    if (PtxPdf_Document_SetMetadata(pOutDoc, PtxPdf_Metadata_Copy(pOutDoc, PtxPdf_Document_GetMetadata(pInDoc))) ==
        FALSE)
        return FALSE;

    // Viewer settings
    if (PtxPdf_Document_SetViewerSettings(
            pOutDoc, PtxPdfNav_ViewerSettings_Copy(pOutDoc, PtxPdf_Document_GetViewerSettings(pInDoc))) == FALSE)
        return FALSE;

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    pInFileRefList  = PtxPdf_Document_GetAssociatedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetAssociatedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    // Plain embedded files
    pInFileRefList  = PtxPdf_Document_GetPlainEmbeddedFiles(pInDoc);
    pOutFileRefList = PtxPdf_Document_GetPlainEmbeddedFiles(pOutDoc);
    if (pInFileRefList == NULL || pOutFileRefList == NULL)
        return FALSE;
    for (int iFileRef = 0; iFileRef < PtxPdf_FileReferenceList_GetCount(pInFileRefList); iFileRef++)
        if (PtxPdf_FileReferenceList_Add(
                pOutFileRefList,
                PtxPdf_FileReference_Copy(pOutDoc, PtxPdf_FileReferenceList_Get(pInFileRefList, iFileRef))) == FALSE)
            return FALSE;

    return TRUE;
}
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))

// Create output document
using (Stream outFs = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
using (Document outDoc = Document.Create(outFs, inDoc.Conformance, null))
{
    // Copy document-wide data
    CopyDocumentData(inDoc, outDoc);

    // Define page copy options
    PageCopyOptions copyOptions = new PageCopyOptions();

    // Copy all pages
    PageList copiedPages = PageList.Copy(outDoc, inDoc.Pages, copyOptions);

    // Rotate selected pages by 90 degrees
    foreach (var pageNumber in pageNumbers)
    {
        copiedPages[pageNumber - 1].Rotate(Rotation.Clockwise);
    }

    // Add pages to output document
    outDoc.Pages.AddRange(copiedPages);
}
private static void CopyDocumentData(Document inDoc, Document outDoc)
{
    // Copy document-wide data

    // Output intent
    if (inDoc.OutputIntent != null)
        outDoc.OutputIntent = IccBasedColorSpace.Copy(outDoc, inDoc.OutputIntent);

    // Metadata
    outDoc.Metadata = Metadata.Copy(outDoc, inDoc.Metadata);

    // Viewer settings
    outDoc.ViewerSettings = ViewerSettings.Copy(outDoc, inDoc.ViewerSettings);

    // Associated files (for PDF/A-3 and PDF 2.0 only)
    FileReferenceList outAssociatedFiles = outDoc.AssociatedFiles;
    foreach (FileReference inFileRef in inDoc.AssociatedFiles)
        outAssociatedFiles.Add(FileReference.Copy(outDoc, inFileRef));

    // Plain embedded files
    FileReferenceList outEmbeddedFiles = outDoc.PlainEmbeddedFiles;
    foreach (FileReference inFileRef in inDoc.PlainEmbeddedFiles)
        outEmbeddedFiles.Add(FileReference.Copy(outDoc, inFileRef));
}
サンプル・プロジェクトの実行手順を参照してください
def copy_document_data(in_doc: Document, out_doc: Document):
    # Copy document-wide data

    # Output intent
    if in_doc.output_intent is not None:
        in_doc.output_intent = IccBasedColorSpace.copy(out_doc, in_doc.output_intent)

    # Metadata
    out_doc.metadata = Metadata.copy(out_doc, in_doc.metadata)

    # Viewer settings
    out_doc.viewer_settings = ViewerSettings.copy(out_doc, in_doc.viewer_settings)

    # Associated files (for PDF/A-3 and PDF 2.0 only)
    outAssociatedFiles = out_doc.associated_files
    for in_file_ref in in_doc.associated_files:
        outAssociatedFiles.append(FileReference.copy(out_doc, in_file_ref))

    # Plain embedded files
    out_embedded_files = out_doc.plain_embedded_files
    for in_file_ref in in_doc.plain_embedded_files:
        out_embedded_files.append(FileReference.copy(out_doc, in_file_ref))
# Open input document
with io.FileIO(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, None) as in_doc:

        # Create output document
        with io.FileIO(output_file_path, "wb+") as out_stream:
            with Document.create(out_stream, in_doc.conformance, None) as out_doc:

                # Copy document-wide data
                copy_document_data(in_doc, out_doc)

                # Define page copy options
                page_copy_options = PageCopyOptions()

                # Copy all pages
                copied_pages = PageList.copy(out_doc, in_doc.pages, page_copy_options)

                # Rotate selected pages by 90 degrees
                for page_number in page_numbers:
                    copied_pages[int(page_number) - 1].rotate(Rotation.CLOCKWISE)

                # Add pages to output document
                out_doc.pages.extend(copied_pages)

情報抽出

PDFからドキュメントの属性とメタデータを抽出

PDFの属性(PF準拠性や暗号化情報)とメタデータ(作成者、タイトル、作成日など)を一覧表示します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, szPassword);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// Conformance
TPtxPdf_Conformance conformance = PtxPdf_Document_GetConformance(pInDoc);
if (conformance == 0)
{
    GOTO_CLEANUP(szErrorBuff, Ptx_GetLastError());
}
_tprintf(_T("Conformance: "));
switch (conformance)
{
case ePtxPdf_Conformance_Pdf10:
    _tprintf(_T("PDF 1.0\n"));
    break;
case ePtxPdf_Conformance_Pdf11:
    _tprintf(_T("PDF 1.1\n"));
    break;
case ePtxPdf_Conformance_Pdf12:
    _tprintf(_T("PDF 1.2\n"));
    break;
case ePtxPdf_Conformance_Pdf13:
    _tprintf(_T("PDF 1.3\n"));
    break;
case ePtxPdf_Conformance_Pdf14:
    _tprintf(_T("PDF 1.4\n"));
    break;
case ePtxPdf_Conformance_Pdf15:
    _tprintf(_T("PDF 1.5\n"));
    break;
case ePtxPdf_Conformance_Pdf16:
    _tprintf(_T("PDF 1.6\n"));
    break;
case ePtxPdf_Conformance_Pdf17:
    _tprintf(_T("PDF 1.7\n"));
    break;
case ePtxPdf_Conformance_Pdf20:
    _tprintf(_T("PDF 2.0\n"));
    break;
case ePtxPdf_Conformance_PdfA1B:
    _tprintf(_T("PDF/A1-b\n"));
    break;
case ePtxPdf_Conformance_PdfA1A:
    _tprintf(_T("PDF/A1-a\n"));
    break;
case ePtxPdf_Conformance_PdfA2B:
    _tprintf(_T("PDF/A2-b\n"));
    break;
case ePtxPdf_Conformance_PdfA2U:
    _tprintf(_T("PDF/A2-u\n"));
    break;
case ePtxPdf_Conformance_PdfA2A:
    _tprintf(_T("PDF/A2-a\n"));
    break;
case ePtxPdf_Conformance_PdfA3B:
    _tprintf(_T("PDF/A3-b\n"));
    break;
case ePtxPdf_Conformance_PdfA3U:
    _tprintf(_T("PDF/A3-u\n"));
    break;
case ePtxPdf_Conformance_PdfA3A:
    _tprintf(_T("PDF/A3-a\n"));
    break;
}

// Encryption information
TPtxPdf_Permission permissions;
BOOL               iRet = PtxPdf_Document_GetPermissions(pInDoc, &permissions);
if (iRet == FALSE)
{
    if (Ptx_GetLastError() != ePtx_Error_Success)
        GOTO_CLEANUP(szErrorBuff, Ptx_GetLastError());
    _tprintf(_T("Not encrypted\n"));
}
else
{
    _tprintf(_T("Encryption:\n"));
    _tprintf(_T("  - Permissions: "));
    if (permissions & ePtxPdf_Permission_Print)
        _tprintf(_T("Print, "));
    if (permissions & ePtxPdf_Permission_Modify)
        _tprintf(_T("Modify, "));
    if (permissions & ePtxPdf_Permission_Copy)
        _tprintf(_T("Copy, "));
    if (permissions & ePtxPdf_Permission_Annotate)
        _tprintf(_T("Annotate, "));
    if (permissions & ePtxPdf_Permission_FillForms)
        _tprintf(_T("FillForms, "));
    if (permissions & ePtxPdf_Permission_SupportDisabilities)
        _tprintf(_T("SupportDisabilities, "));
    if (permissions & ePtxPdf_Permission_Assemble)
        _tprintf(_T("Assemble, "));
    if (permissions & ePtxPdf_Permission_DigitalPrint)
        _tprintf(_T("DigitalPrint, "));
    _tprintf(_T("\n"));
}

// Get metadata of input PDF
pMetadata = PtxPdf_Document_GetMetadata(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pMetadata, _T("Failed to get metadata. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                 Ptx_GetLastError());
_tprintf(_T("Document information:\n"));

// Get title
size_t nTitle = PtxPdf_Metadata_GetTitle(pMetadata, NULL, 0);
if (nTitle != 0)
{
    TCHAR* szTitle = (TCHAR*)malloc(nTitle * sizeof(TCHAR));
    if (szTitle != NULL)
    {
        PtxPdf_Metadata_GetTitle(pMetadata, szTitle, nTitle);
        _tprintf(_T("  - Title: %s\n"), szTitle);
        free(szTitle);
    }
}

// Get author
size_t nAuthor = PtxPdf_Metadata_GetAuthor(pMetadata, NULL, 0);
if (nAuthor != 0)
{
    TCHAR* szAuthor = (TCHAR*)malloc(nAuthor * sizeof(TCHAR));
    if (szAuthor != NULL)
    {
        PtxPdf_Metadata_GetAuthor(pMetadata, szAuthor, nAuthor);
        _tprintf(_T("  - Author: %s\n"), szAuthor);
        free(szAuthor);
    }
}

// Get creator
size_t nCreator = PtxPdf_Metadata_GetCreator(pMetadata, NULL, 0);
if (nCreator != 0)
{
    TCHAR* szCreator = (TCHAR*)malloc(nCreator * sizeof(TCHAR));
    if (szCreator != NULL)
    {
        PtxPdf_Metadata_GetCreator(pMetadata, szCreator, nCreator);
        _tprintf(_T("  - Creator: %s\n"), szCreator);
        free(szCreator);
    }
}

// Get producer
size_t nProducer = PtxPdf_Metadata_GetProducer(pMetadata, NULL, 0);
if (nProducer != 0)
{
    TCHAR* szProducer = (TCHAR*)malloc(nProducer * sizeof(TCHAR));
    if (szProducer != NULL)
    {
        PtxPdf_Metadata_GetProducer(pMetadata, szProducer, nProducer);
        _tprintf(_T("  - Producer: %s\n"), szProducer);
        free(szProducer);
    }
}

// Get subject
size_t nSubject = PtxPdf_Metadata_GetSubject(pMetadata, NULL, 0);
if (nSubject != 0)
{
    TCHAR* szSubject = (TCHAR*)malloc(nSubject * sizeof(TCHAR));
    if (szSubject != NULL)
    {
        PtxPdf_Metadata_GetSubject(pMetadata, szSubject, nSubject);
        _tprintf(_T("  - Subject: %s\n"), szSubject);
        free(szSubject);
    }
}

// Get keywords
size_t nKeywords = PtxPdf_Metadata_GetKeywords(pMetadata, NULL, 0);
if (nKeywords != 0)
{
    TCHAR* szKeywords = (TCHAR*)malloc(nKeywords * sizeof(TCHAR));
    if (szKeywords != NULL)
    {
        PtxPdf_Metadata_GetKeywords(pMetadata, szKeywords, nKeywords);
        _tprintf(_T("  - Keywords: %s\n"), szKeywords);
        free(szKeywords);
    }
}

// Get creation date
if (PtxPdf_Metadata_GetCreationDate(pMetadata, &date) == TRUE)
{
    _tprintf(_T("  - Creation Date: %02d-%02d-%d %02d:%02d:%02d%c%02d:%02d\n"), date.iYear, date.iMonth, date.iDay,
             date.iHour, date.iMinute, date.iSecond, date.iTZSign >= 0 ? '+' : '-', date.iTZHour, date.iTZMinute);
}

// Get modification date
if (PtxPdf_Metadata_GetModificationDate(pMetadata, &date) == TRUE)
{
    _tprintf(_T("  - Modification Date: %02d-%02d-%d %02d:%02d:%02d%c%02d:%02d\n"), date.iYear, date.iMonth,
             date.iDay, date.iHour, date.iMinute, date.iSecond, date.iTZSign >= 0 ? '+' : '-', date.iTZHour,
             date.iTZMinute);
}

// Get custom entries
_tprintf(_T("Custom entries:\n"));
TPtx_StringMap* pCustomEntries = PtxPdf_Metadata_GetCustomEntries(pMetadata);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pCustomEntries, _T("Failed to get custom entries. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
for (int i = Ptx_StringMap_GetBegin(pCustomEntries), iEnd = Ptx_StringMap_GetEnd(pCustomEntries); i != iEnd;
     i = Ptx_StringMap_GetNext(pCustomEntries, i))
{
    size_t nKeySize = Ptx_StringMap_GetKey(pCustomEntries, i, NULL, 0);
    TCHAR* szKey    = (TCHAR*)malloc(nKeySize * sizeof(TCHAR));
    nKeySize        = Ptx_StringMap_GetKey(pCustomEntries, i, szKey, nKeySize);

    size_t nValueSize = Ptx_StringMap_GetValue(pCustomEntries, i, NULL, 0);
    TCHAR* szValue    = (TCHAR*)malloc(nValueSize * sizeof(TCHAR));
    nValueSize        = Ptx_StringMap_GetValue(pCustomEntries, i, szValue, nValueSize);

    if (szKey && nKeySize && szValue && nValueSize)
        _tprintf(_T("  - %s: %s\n"), szKey, szValue);

    free(szKey);
    free(szValue);
}
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, password))
{
    // Conformance
    Console.WriteLine("Conformance: {0}", inDoc.Conformance.ToString());

    // Encryption information
    Permission? permissions = inDoc.Permissions;
    if (!permissions.HasValue)
    {
        Console.WriteLine("Not encrypted");
    }
    else
    {
        Console.WriteLine("Encryption:");
        Console.Write("  - Permissions: ");
        foreach (Enum flag in Enum.GetValues(typeof(Permission)))
            if (permissions.Value.HasFlag(flag))
                Console.Write("{0}, ", flag.ToString());
        Console.WriteLine();
    }

    // Get metadata
    Metadata metadata = inDoc.Metadata;
    Console.WriteLine("Document information:");

    // Get title
    string title = metadata.Title;
    if (title != null)
        Console.WriteLine("  - Title: {0}", title);

    // Get author
    string author = metadata.Author;
    if (author != null)
        Console.WriteLine("  - Author: {0}", author);

    // Get subject
    string subject = metadata.Subject;
    if (subject != null)
        Console.WriteLine("  - Subject: {0}", subject);

    // Get keywords
    string keywords = metadata.Keywords;
    if (keywords != null)
        Console.WriteLine("  - Keywords: {0}", keywords);

    // Get creation date
    DateTimeOffset? creationDate = metadata.CreationDate;
    if (creationDate != null)
        Console.WriteLine("  - Creation Date: {0}", creationDate);

    // Get modification date
    DateTimeOffset? modificationDate = metadata.ModificationDate;
    if (modificationDate != null)
        Console.WriteLine("  - Modification Date: {0}", modificationDate);

    // Get creator
    string creator = metadata.Creator;
    if (creator != null)
        Console.WriteLine("  - Creator: {0}", creator);

    // Get producer
    string producer = metadata.Producer;
    if (producer != null)
        Console.WriteLine("  - Producer: {0}", producer);

    // Custom entries
    Console.WriteLine("Custom entries:");
    foreach (var entry in metadata.CustomEntries)
        Console.WriteLine("  - {0}: {1}", entry.Key, entry.Value);
}
サンプル・プロジェクトの実行手順を参照してください
def display_permissions(permissions: int):
    """Display encryption permissions in a readable format."""
    # Display active permission names
    active_permissions = [perm.name for perm in Permission if permissions & perm]
    for perm in active_permissions:
        print(f"  - {perm}")
def list_pdf_info(input_doc: Document):
    """
    List document information and metadata of the given PDF.
    """
    # Conformance
    print(f"Conformance: {input_doc.conformance.name}")

    # Encryption information
    permissions = input_doc.permissions
    if permissions is None:
        print("Not encrypted")
    else:
        display_permissions(permissions)

    # Get metadata
    metadata = input_doc.metadata
    print("Document information:")

    # Display standard metadata
    if metadata.title:
        print(f"  - Title: {metadata.title}")
    if metadata.author:
        print(f"  - Author: {metadata.author}")
    if metadata.subject:
        print(f"  - Subject: {metadata.subject}")
    if metadata.keywords:
        print(f"  - Keywords: {metadata.keywords}")
    if metadata.creation_date:
        print(f"  - Creation Date: {metadata.creation_date}")
    if metadata.modification_date:
        print(f"  - Modification Date: {metadata.modification_date}")
    if metadata.creator:
        print(f"  - Creator: {metadata.creator}")
    if metadata.producer:
        print(f"  - Producer: {metadata.producer}")

    # Display custom entries
    print("Custom entries:")
    for key, value in metadata.custom_entries.items():
        print(f"  - {key}: {value}")
# Open input document
with io.FileIO(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, pdf_password) as in_doc:
        # Process the PDF
        list_pdf_info(in_doc)

PDFからすべての電子署名情報を抽出

PDF内のすべての署名フィールドとそのプロパティを一覧表示します。


サンプル・プロジェクト(C)をダウンロード
サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
pInStream = _tfopen(szInPath, _T("rb"));
GOTO_CLEANUP_IF_NULL(pInStream, _T("Failed to open input file \"%s\".\n"), szInPath);
PtxSysCreateFILEStreamDescriptor(&descriptor, pInStream, 0);
pInDoc = PtxPdf_Document_Open(&descriptor, _T(""));
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pInDoc, _T("Input file \"%s\" cannot be opened. %s (ErrorCode: 0x%08x).\n"),
                                 szInPath, szErrorBuff, Ptx_GetLastError());

// Get signatures of input PDF
pSignatureFields = PtxPdf_Document_GetSignatureFields(pInDoc);
GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pSignatureFields,
                                 _T("Failed to get signatures of input PDF. %s (ErrorCode: 0x%08x).\n"),
                                 szErrorBuff, Ptx_GetLastError());
_tprintf(_T("Number of signature fields: %d\n"), PtxPdfForms_SignatureFieldList_GetCount(pSignatureFields));

for (int i = 0; i < PtxPdfForms_SignatureFieldList_GetCount(pSignatureFields); i++)
{
    pSig = PtxPdfForms_SignatureFieldList_Get(pSignatureFields, i);
    GOTO_CLEANUP_IF_NULL_PRINT_ERROR(pSig, _T("Failed to get signature. %s (ErrorCode: 0x%08x).\n"), szErrorBuff,
                                     Ptx_GetLastError());

    TPtxPdfForms_SignatureFieldType iFieldType = PtxPdfForms_SignatureField_GetType(pSig);
    if (iFieldType == ePtxPdfForms_SignatureFieldType_Signature ||
        iFieldType == ePtxPdfForms_SignatureFieldType_DocMdpSignature ||
        iFieldType == ePtxPdfForms_SignatureFieldType_DocumentSignature)
    {
        // List name
        size_t nName = PtxPdfForms_SignedSignatureField_GetName(pSig, NULL, 0);
        _tprintf(_T("- %s fields"), PtxPdfForms_SignatureField_IsVisible(pSig) ? _T("Visible") : _T("Invisible"));
        if (nName != 0)
        {
            TCHAR* szName = (TCHAR*)malloc(nName * sizeof(TCHAR));
            if (szName != NULL)
            {
                PtxPdfForms_SignedSignatureField_GetName(pSig, szName, nName);
                _tprintf(_T(", signed by: %s"), szName);
                free(szName);
            }
        }
        _tprintf(_T("\n"));

        // List location
        size_t nLocation = PtxPdfForms_Signature_GetLocation(pSig, NULL, 0);
        if (nLocation != 0)
        {
            TCHAR* szLocation = (TCHAR*)malloc(nLocation * sizeof(TCHAR));
            if (szLocation != NULL)
            {
                PtxPdfForms_Signature_GetLocation(pSig, szLocation, nLocation);
                _tprintf(_T("  - Location: %s\n"), szLocation);
                free(szLocation);
            }
        }

        // List reason
        size_t nReason = PtxPdfForms_Signature_GetReason(pSig, NULL, 0);
        if (nReason != 0)
        {
            TCHAR* szReason = (TCHAR*)malloc(nReason * sizeof(TCHAR));
            if (szReason != NULL)
            {
                PtxPdfForms_Signature_GetReason(pSig, szReason, nReason);
                _tprintf(_T("  - Reason: %s\n"), szReason);
                free(szReason);
            }
        }

        // List contact info
        size_t nContactInfo = PtxPdfForms_Signature_GetContactInfo(pSig, NULL, 0);
        if (nContactInfo != 0)
        {
            TCHAR* szContactInfo = (TCHAR*)malloc(nContactInfo * sizeof(TCHAR));
            if (szContactInfo != NULL)
            {
                PtxPdfForms_Signature_GetContactInfo(pSig, szContactInfo, nContactInfo);
                _tprintf(_T("  - Contact info: %s\n"), szContactInfo);
                free(szContactInfo);
            }
        }

        // List date
        if (PtxPdfForms_SignedSignatureField_GetDate(pSig, &date) == TRUE)
        {
            _tprintf(_T("  - Date: %02d-%02d-%d %02d:%02d:%02d%c%02d:%02d\n"), date.iYear, date.iMonth, date.iDay,
                     date.iHour, date.iMinute, date.iSecond, date.iTZSign >= 0 ? '+' : '-', date.iTZHour,
                     date.iTZMinute);
        }
    }
    else
    {
        _tprintf(_T("- %s field, not signed\n"),
                 PtxPdfForms_SignatureField_IsVisible(pSig) ? _T("Visible") : _T("Invisible"));
    }
}
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))
{
    SignatureFieldList signatureFields = inDoc.SignatureFields;
    Console.WriteLine("Number of signature fields: {0}", signatureFields.Count);
    foreach (SignatureField field in signatureFields)
    {
        if (field is Signature sig)
        {
            // List name
            string name = sig.Name;
            Console.WriteLine("- {0} fields, signed by: {1}",
                sig.IsVisible ? "Visible" : "Invisible", name ?? "(Unknown name)");

            // List location
            string location = sig.Location;
            if (location != null)
                Console.WriteLine("  - Location: {0}", location);

            // List reason 
            string reason = sig.Reason;
            if (reason != null)
                Console.WriteLine("  - Reason: {0}", reason);

            // List contact info
            string contactInfo = sig.ContactInfo;
            if (contactInfo != null)
                Console.WriteLine("  - Contact info: {0}", contactInfo);

            // List date
            DateTimeOffset? date = sig.Date;
            if (date != null)
                Console.WriteLine("  - Date: {0}", date.Value);
        }
        else
            Console.WriteLine("- {0} field, not signed", field.IsVisible ? "Visible" : "Invisible");
    }
}
サンプル・プロジェクトの実行手順を参照してください
def list_signatures(in_doc: Document):
    # Retrieve the list of signature fields
    signature_fields = in_doc.signature_fields
    print(f"Number of signature fields: {len(signature_fields)}")

    for field in signature_fields:
        if isinstance(field, Signature):
            # List name
            name = field.name or "(Unknown name)"
            print(f"- {'Visible' if field.is_visible else 'Invisible'} field, signed by: {name}")

            # List location
            if field.location:
                print(f"  - Location: {field.location}")

            # List reason
            if field.reason:
                print(f"  - Reason: {field.reason}")

            # List contact info
            if field.contact_info:
                print(f"  - Contact info: {field.contact_info}")

            # List date
            if field.date:
                print(f"  - Date: {field.date}")
        else:
            print(f"- {'Visible' if field.is_visible else 'Invisible'} field, not signed")
# Open input document
with io.FileIO(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, None) as in_doc:
        # List all signatures of the PDF document
        list_signatures(in_doc)

PDFからすべてのテキストを抽出

PDFからページごとに抽出したテキストをコンソールに書き込みます。
2つのテキストが同じ単語に属しているかどうかをヒューリスティックに判断します。


サンプル・プロジェクト(C#)をダウンロード
サンプル・プロジェクト(Python)をダウンロード
サンプル・プロジェクトをダウンロード
サンプル・プロジェクトの実行手順を参照してください
// Open input document
using (Stream inStream = new FileStream(inPath, FileMode.Open, FileAccess.Read))
using (Document inDoc = Document.Open(inStream, null))
{
    int pageNumber = 1;

    // Process each page
    foreach (var inPage in inDoc.Pages)
    {
        Console.WriteLine("==========");
        Console.WriteLine($"Page: {pageNumber++}");
        Console.WriteLine("==========");

        ContentExtractor extractor = new ContentExtractor(inPage.Content);
        extractor.Ungrouping = UngroupingSelection.All;

        // Iterate over all content elements and only process text elements
        foreach (ContentElement element in extractor)
            if (element is TextElement textElement)
                WriteText(textElement.Text);
    }
}
private static void WriteText(Text text)
{
    string textPart = "";

    // Write all text fragments
    // Determine heuristically if there is a space between two text fragments
    for (int iFragment = 0; iFragment < text.Count; iFragment++)
    {

        TextFragment currFragment = text[iFragment];
        if (iFragment == 0)
            textPart += currFragment.Text;
        else
        {
            TextFragment lastFragment = text[iFragment - 1];
            if (currFragment.CharacterSpacing != lastFragment.CharacterSpacing ||
                currFragment.FontSize != lastFragment.FontSize ||
                currFragment.HorizontalScaling != lastFragment.HorizontalScaling ||
                currFragment.Rise != lastFragment.Rise ||
                currFragment.WordSpacing != lastFragment.WordSpacing)
                textPart += $" {currFragment.Text}";
            else
            {
                Point currentBotLeft = currFragment.Transform.TransformRectangle(currFragment.BoundingBox).BottomLeft;
                Point beforeBotRight = lastFragment.Transform.TransformRectangle(lastFragment.BoundingBox).BottomRight;

                if (beforeBotRight.X < currentBotLeft.X - 0.7 * currFragment.FontSize ||
                    beforeBotRight.Y < currentBotLeft.Y - 0.1 * currFragment.FontSize ||
                    currentBotLeft.Y < beforeBotRight.Y - 0.1 * currFragment.FontSize)
                    textPart += $" {currFragment.Text}";
                else
                    textPart += currFragment.Text;
            }
        }
    }
    Console.WriteLine(textPart);
}
サンプル・プロジェクトの実行手順を参照してください
def write_text(text: Text):
    """Reconstruct text heuristically from text fragments."""
    text_part = []

    # Write all text fragments
    # Determine heuristically if there is a space between two text fragments
    for i_fragment, curr_fragment in enumerate(text):
        if i_fragment == 0:
            text_part.append(curr_fragment.text)
        else:
            last_fragment = text[i_fragment - 1]

            # Determine if there's a space between fragments
            if (curr_fragment.character_spacing != last_fragment.character_spacing or
                curr_fragment.font_size != last_fragment.font_size or
                curr_fragment.horizontal_scaling != last_fragment.horizontal_scaling or
                curr_fragment.rise != last_fragment.rise or
                curr_fragment.word_spacing != last_fragment.word_spacing):
                text_part.append(f" {curr_fragment.text}")
            else:
                current_bot_left = curr_fragment.transform.transform_rectangle(curr_fragment.bounding_box).bottom_left
                before_bot_right = last_fragment.transform.transform_rectangle(last_fragment.bounding_box).bottom_right

                if (before_bot_right.x < current_bot_left.x - 0.7 * curr_fragment.font_size or
                    before_bot_right.y < current_bot_left.y - 0.1 * curr_fragment.font_size or
                    current_bot_left.y < before_bot_right.y - 0.1 * curr_fragment.font_size):
                    text_part.append(f" {curr_fragment.text}")
                else:
                    text_part.append(curr_fragment.text)

    print("".join(text_part))
# Open input document
with open(input_file_path, "rb") as in_stream:
    with Document.open(in_stream, None) as in_doc:
        page_number = 1

        # Process each page
        for in_page in in_doc.pages:
            print(f"==========\nPage: {page_number}\n==========")

            extractor = ContentExtractor(in_page.content)
            extractor.ungrouping = UngroupingSelection.ALL

            # Iterate over all content elements and only process text elements
            for element in extractor:
                if isinstance(element, TextElement):
                    write_text(element.text)
            page_number += 1

> PDF Structure (PDF構成)

> PDF Imager-LP (画像化)

> PDF Stamper (電子印鑑)

> Pdftools SDK

- サンプル・コード
- Pdftools SDKサンプルの利用手順
- Toolbox Add-on
- Toolbox Add-onサンプルの利用手順
> Pdftools SDK APIリファレンス
- その他のAPI及びコマンドラインツール
> PDF SDK オープンソースと有償ライブラリ