0

ある PDF ファイルから別の PDF ファイルに注釈をコピーする必要があります。優れた PDFClown ライブラリを使用しましたが、色、回転などを操作できません。これは可能ですか? baseobject 情報を確認できますが、それを直接操作する方法もわかりません。

外観の複製で外観をコピーできますが、「編集」できません。

前もって感謝します。アレックス

PSステファノがリストしている場合、プロジェクトは死んでいますか?

4

2 に答える 2

0

一般的な注釈、特に吹き出し注釈について

私はそれを少し調べましたが、高レベルの方法を使用して任意の入力に対して決定論的に操作できるものはあまりないのではないかと思います. その理由は、Callout 注釈の外観を設定するための代替方法が多数あり、PDF Clown は明示的な高レベル メソッドを使用した優先度の低い方法のみをサポートするためです。優先度の高いものから下へ

  • APストリームでの明示的な出現。指定されている場合は、この外観が Callout 注釈のように見えるかどうか、ましてや他の Callout プロパティで定義されたものと同じように見えるかどうかを無視して使用されます。

    PDF Clown は、特定の属性 (例: Color) の変更に対応するために既存の外観を更新するどころか、他の値から吹き出し注釈の外観をまだ作成していません。ISO 32000-2 のサポートについては、アピアランス ストリームが必須になったため、PDF Clown を改善する必要があります。

    存在する場合は、を使用して外観を取得できますが、取得できるのは低レベルの描画命令getAppearance()のみFormXObjectで、Callout 固有のものはありません。

    ただし、与えられた a を非常に簡単に操作できることの 1 つは、それに応じてMatrixFormXObjectを設定することで、外観を非常に簡単に回転または傾斜させることができます。

    annotation.getAppearance().getNormal().get(null).setMatrix(AffineTransform.getRotateInstance(100, 10));
    
  • RC文字列またはストリーム内のリッチ テキスト文字列。外観が指定されていない限り、吹き出しテキスト ボックス内のテキストは、このリッチ テキスト データムから生成されます (ここでのリッチ テキストは、書式設定に XHTML 1.0 サブセットを使用します)。

    ColorPDF Clown は、吹き出しテキストのリッチ テキスト表現をまだ作成していません。ましてや、特定の属性 (例: ) の変更に対応するために既存のものを更新することはできません。

    存在する場合は、 を使用して低レベル アクセスでリッチ テキストを取得し、getBaseDataObject().get(PdfName.RC)この文字列またはストリームを変更して、 を使用して再度設定できgetBaseDataObject().put(PdfName.RC, ...)ます。PdfName.DS同様に、代わりにその名前を使用して、リッチ テキストの既定のスタイル文字列を取得、操作、および設定できます。

  • アピアランス ストリームと (テキスト コンテンツに関する限り) リッチ テキスト文字列がない場合に、Callout を構築するために使用される個別の側面のさまざまな設定。

    PDF Clown は、これらの属性 (の多く) をサポートします。特に、複製された注釈を にキャストする場合StaticNote、たとえば、不透明度CAを使用してget/set/withAlphaボーダー ボーダー/ BSを使用してget/set/withBorder、背景色Cを使用してget/set/withColor...

    ちなみに、行末スタイルのLEサポートにエラーがあります。どうやら、注釈LEプロパティのコードがチェックせずにコピーされたようです。残念ながら、その属性は別の構文に従います...

あなたのタスク

したがって、変更したいと言った属性については、

  • Rotation : Callout アノテーション自体には回転属性はありません (ページの回転に従うかどうかのフラグ以外)。したがって、回転を単純な注釈属性として設定することはできません。ただし、ソース アノテーションに外観ストリームがある場合は、そのマトリックスを操作して、アノテーションの四角形内で回転させることができます。上記を参照してください。

  • 境界線の色フォント: Callout に外観ストリームがある場合は、 を使用してコンテンツを解析し、ContentScanner色とフォントの設定操作を操作できます。それ以外の場合、リッチ テキスト情報が設定されている場合は、フォントについて、何らかの XML パーサーを使用してリッチ テキストを解析し、フォント スタイル属性を操作することができます。それ以外の場合は、デフォルトの外観DA文字列を解析し、そのフォントと色の設定命令を操作できます。

いくつかのサンプルコード

Adobe Acrobat を使用して Callout 注釈の例を含むファイルを作成しました: Callout-Yellow.pdf。これには外観ストリーム、リッチ テキスト、および単純な属性が含まれているため、このファイルをさまざまなレベルでの操作などに使用できます。

このコードをkeepAppearanceStreamandに異なる値を付けて適用しましたkeepRichText(Java と .Net のどちらに PDF Clown を使用したかは言及されていませんでした。そのため、Java を選択しました。.Net へのポートは簡単なはずですが...):

boolean keepAppearanceStream = ...;
boolean keepRichText = ...;

try (   InputStream sourceResource = GET_STREAM_FOR("Callout-Yellow.pdf");
        InputStream targetResource = GET_STREAM_FOR("test123.pdf");
        org.pdfclown.files.File sourceFile = new org.pdfclown.files.File(sourceResource);
        org.pdfclown.files.File targetFile = new org.pdfclown.files.File(targetResource); ) {
    Document sourceDoc = sourceFile.getDocument();
    Page sourcePage = sourceDoc.getPages().get(0);
    Annotation<?> sourceAnnotation = sourcePage.getAnnotations().get(0);

    Document targetDoc = targetFile.getDocument();
    Page targetPage = targetDoc.getPages().get(0);

    StaticNote targetAnnotation = (StaticNote) sourceAnnotation.clone(targetDoc);

    if (keepAppearanceStream) {
        // changing properties of an appearance
        // rotating the appearance in the appearance rectangle
        targetAnnotation.getAppearance().getNormal().get(null).setMatrix(AffineTransform.getRotateInstance(100, 10));
    } else {
        // removing the appearance to allow lower level properties changes
        targetAnnotation.setAppearance(null);
    }

    // changing text background color
    targetAnnotation.setColor(new DeviceRGBColor(0, 0, 1));

    if (keepRichText) {
        // changing rich text properties
        PdfString richText = (PdfString) targetAnnotation.getBaseDataObject().get(PdfName.RC);
        String richTextString = richText.getStringValue();
        // replacing the font family
        richTextString = richTextString.replaceAll("font-family:Helvetica", "font-family:Courier");
        richText = new PdfString(richTextString);
        targetAnnotation.getBaseDataObject().put(PdfName.RC, richText);
    } else {
        targetAnnotation.getBaseDataObject().remove(PdfName.RC);
        targetAnnotation.getBaseDataObject().remove(PdfName.DS);
    }

    // changing default appearance properties
    PdfString defaultAppearance = (PdfString) targetAnnotation.getBaseDataObject().get(PdfName.DA);
    String defaultAppearanceString = defaultAppearance.getStringValue();
    // replacing the font
    defaultAppearanceString = defaultAppearanceString.replaceFirst("Helv", "HeBo");
    // replacing the text and line color
    defaultAppearanceString = defaultAppearanceString.replaceFirst(". . . rg", ".5 g");
    defaultAppearance = new PdfString(defaultAppearanceString);
    targetAnnotation.getBaseDataObject().put(PdfName.DA, defaultAppearance);

    // changing the text value
    PdfString contents = (PdfString) targetAnnotation.getBaseDataObject().get(PdfName.Contents);
    String contentsString = contents.getStringValue();
    contentsString = contentsString.replaceFirst("text", "text line");
    contents = new PdfString(contentsString);
    targetAnnotation.getBaseDataObject().put(PdfName.Contents, contents);

    // change the line width and style
    targetAnnotation.setBorder(new Border(0, new LineDash(new double[] {3, 2})));

    targetPage.getAnnotations().add(targetAnnotation);

    targetFile.save(new File(RESULT_FOLDER, "test123-withCalloutCopy.pdf"),  SerializationModeEnum.Standard);
}

( CopyCallOutテストtestCopyCallout)

コードには概念実証の品質しかないことに注意してください: 任意の PDF の場合、単に "font-family:Helvetica" を "font-family:Courier" に、または "Helv" を "HeBo" または ". ..rg" ごとに ".5 g" を実行してください: フォントは、さまざまなスタイル属性または名前を使用して指定でき、さまざまな色指定を使用できます。

Adobe のスクリーンショット

  • 元のファイル:

    元の注釈

  • keepAppearanceStream = true:

    アピアランス ストリームは保持されますが、回転されます

  • keepAppearanceStream = falsekeepRichText = true:

    外観ストリームが削除され、リッチ テキストは保持されますが操作されます

  • keepAppearanceStream = falsekeepRichText = false:

    外観ストリームとリッチ テキストを削除し、単純な属性を操作

于 2018-05-14T14:22:46.047 に答える