首页 > 解决方案 > 使用显示/隐藏页面上另一个按钮的 PDFBox 2.0.5 创建 PDF 按钮。只有最后创建的集合才能正常工作

问题描述

这段代码的目标是在页面上有一个缩略图,当鼠标悬停在它上面时,它会以全尺寸显示图像。此处的代码适用于主要警告,即只有创建的最终缩略图完整图像组合才能工作,除非在 Adob​​e Acrobat Pro 中,我转到工具 > 交互式对象 > 添加按钮。那么屏幕上可见的所有按钮都将起作用。如果我将鼠标移到任何缩略图上,则与之关联的大按钮将从打开的文档中删除。我已经尝试过 setNeedAppearances(true) 并且这些操作适用于所有组合,但小部件格式已被删除。下面附上我的测试代码。任何帮助将不胜感激。谢谢。

import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;

import java.io.IOException;

public class TestMain {

    public static void main(String[] args) throws IOException {
        PDDocument document = new PDDocument();
        PDPage page = new PDPage();
        document.addPage(page);

        float[] location = new float[]{100 , 600 , 60 , 80};
        TestButton.makeButton(document , page , location , "1.jpg");

        float[] location2 = new float[]{100 , 400 , 60 , 80};
        TestButton.makeButton(document , page , location2 , "2.jpg");

        document.save("mytest.pdf");
        document.close();

    }
}
import org.apache.pdfbox.cos.COSDictionary;
import org.apache.pdfbox.cos.COSName;
import org.apache.pdfbox.cos.COSString;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.PDPageContentStream;
import org.apache.pdfbox.pdmodel.PDResources;
import org.apache.pdfbox.pdmodel.common.PDRectangle;
import org.apache.pdfbox.pdmodel.graphics.color.PDColor;
import org.apache.pdfbox.pdmodel.graphics.color.PDDeviceRGB;
import org.apache.pdfbox.pdmodel.graphics.image.PDImageXObject;
import org.apache.pdfbox.pdmodel.interactive.action.PDActionHide;
import org.apache.pdfbox.pdmodel.interactive.action.PDAnnotationAdditionalActions;
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAnnotationWidget;
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAppearanceCharacteristicsDictionary;
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAppearanceDictionary;
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAppearanceStream;
import org.apache.pdfbox.pdmodel.interactive.form.PDAcroForm;
import org.apache.pdfbox.pdmodel.interactive.form.PDPushButton;

import java.io.IOException;
import java.util.ArrayList;

public class TestButton {

    public static void makeButton(PDDocument document , PDPage page , float[] thumbLocation, String imageName) throws IOException {
        PDImageXObject image = PDImageXObject.createFromFile("src//main/resources/" + imageName, document);
        // thumbLocation array
        float thumbX = thumbLocation[0];
        float thumbY = thumbLocation[1];
        float thumbWidth = thumbLocation[2];
        float thumbHeight = thumbLocation[3];

        float lowX = page.getMediaBox().getLowerLeftX();
        float lowY = page.getMediaBox().getLowerLeftY();
        float highY = page.getMediaBox().getUpperRightY();

        float fullX = thumbX - image.getWidth() - 10;
        if (fullX < lowX + 10){
            fullX = thumbX + thumbWidth + 10;
        }
        float fullY = (thumbY + thumbHeight / 2) - (image.getHeight() / 2);
        if (fullY < lowY + 10){
            fullY = thumbY + thumbHeight + 10;
        }
        if (fullY + image.getHeight() > highY - 10){
            fullY = thumbY - image.getHeight() - 10;
        }
        float fullWidth = image.getWidth();
        float fullHeight = image.getHeight();

        String thumbImage = imageName + "_Thumb";
        String fullImage = imageName + "_Full";
        PDColor colourBlack = new PDColor(new float[] { 0, 0, 0 }, PDDeviceRGB.INSTANCE);

        // Set up thumbnail
        COSDictionary thumbDict = new COSDictionary();
        PDAcroForm thumbAcro = new PDAcroForm(document , thumbDict);
        document.getDocumentCatalog().setAcroForm(thumbAcro);
        thumbAcro.setFields(new ArrayList<>());

        PDPushButton thumbButton = new PDPushButton(thumbAcro);
        thumbButton.setPartialName(thumbImage);
        // Thumbnail actions
        thumbDict.setItem(COSName.T, new COSString(fullImage));

        PDActionHide actionHide = new PDActionHide();
        actionHide.setT(thumbDict);

        PDActionHide actionShow = new PDActionHide();
        actionShow.setT(thumbDict);
        actionShow.setH(false);

        PDAnnotationAdditionalActions additionalActions = new PDAnnotationAdditionalActions();
        additionalActions.setE(actionShow);
        additionalActions.setX(actionHide);
        // Thumbnail widget
        PDAnnotationWidget thumbWidget = thumbButton.getWidgets().get(0);
        thumbWidget.setActions(additionalActions);
        thumbWidget.setRectangle(new PDRectangle(thumbX, thumbY, thumbWidth, thumbHeight));
        // Thumbnail appearance
        PDAppearanceDictionary thumbAppearanceDict = new PDAppearanceDictionary();
        PDAppearanceStream thumbAppearanceStream = new PDAppearanceStream(document);
        thumbAppearanceStream.setResources(new PDResources());
        PDAppearanceCharacteristicsDictionary thumbFieldAppearance
                = new PDAppearanceCharacteristicsDictionary(new COSDictionary());
        thumbFieldAppearance.setBorderColour(colourBlack);
        thumbWidget.setAppearanceCharacteristics(thumbFieldAppearance);
        try (PDPageContentStream thumbContent = new PDPageContentStream(document, thumbAppearanceStream))
        {
            PDRectangle thumbBox = new PDRectangle(
                    thumbWidget.getRectangle().getWidth(), thumbWidget.getRectangle().getHeight());
            thumbAppearanceStream.setBBox(thumbBox);
            thumbContent.setNonStrokingColor(0, 0, 0);
            thumbContent.setLineWidth(0.5f);
            thumbContent.addRect(thumbBox.getLowerLeftX() + 0.5f, thumbBox.getLowerLeftY() + 0.5f,
                    thumbBox.getWidth() - 1, thumbBox.getHeight() - 1);
            thumbContent.stroke();
            thumbContent.drawImage(image , thumbBox.getLowerLeftX() + 0.5f, thumbBox.getLowerLeftY() + 0.5f,
                    thumbBox.getWidth() - 1, thumbBox.getHeight() - 1);
        }
        thumbAppearanceDict.setNormalAppearance(thumbAppearanceStream);
        thumbWidget.setAppearance(thumbAppearanceDict);
        thumbWidget.setHidden(false);
        thumbWidget.setPrinted(true);

        page.getAnnotations().add(thumbWidget);
        thumbAcro.getFields().add(thumbButton);

        // Set up full
        COSDictionary fullDict = new COSDictionary();
        PDAcroForm fullAcro = new PDAcroForm(document , fullDict);
        document.getDocumentCatalog().setAcroForm(fullAcro);
        fullAcro.setFields(new ArrayList<>());

        PDPushButton fullButton = new PDPushButton(fullAcro);
        fullButton.setPartialName(fullImage);
        // Full widget
        PDAnnotationWidget fullWidget = fullButton.getWidgets().get(0);
        fullWidget.setRectangle(new PDRectangle(fullX - 1 , fullY - 1, fullWidth + 2 , fullHeight + 2));
        // Full appearance
        PDAppearanceDictionary fullAppearanceDict = new PDAppearanceDictionary();
        PDAppearanceStream fullAppearanceStream = new PDAppearanceStream(document);
        fullAppearanceStream.setResources(new PDResources());
        PDAppearanceCharacteristicsDictionary fullFieldAppearance
                = new PDAppearanceCharacteristicsDictionary(new COSDictionary());
        fullFieldAppearance.setBorderColour(colourBlack);
        fullWidget.setAppearanceCharacteristics(fullFieldAppearance);
        try (PDPageContentStream fullContent = new PDPageContentStream(document, fullAppearanceStream))
        {
            PDRectangle fullBox = new PDRectangle(
                    fullWidget.getRectangle().getWidth(), fullWidget.getRectangle().getHeight());
            fullAppearanceStream.setBBox(fullBox);
            fullContent.setNonStrokingColor(0, 0, 0);
            fullContent.setLineWidth(1);
            fullContent.addRect(fullBox.getLowerLeftX() + 1, fullBox.getLowerLeftY() + 1,
                    fullBox.getWidth() - 2, fullBox.getHeight() - 2);
            fullContent.stroke();
            fullContent.drawImage(image, fullBox.getLowerLeftX() + 1, fullBox.getLowerLeftY() + 1,
                    fullBox.getWidth() - 2, fullBox.getHeight() - 2);
        }
        fullAppearanceDict.setNormalAppearance(fullAppearanceStream);
        fullWidget.setAppearance(fullAppearanceDict);
        fullWidget.setHidden(true);
        fullWidget.setPrinted(false);

        page.getAnnotations().add(fullWidget);
        fullAcro.getFields().add(fullButton);
    }
}

标签: javapdfbox

解决方案


谢谢 mkl,你把我送到了正确的方向。我最终使 TestButton 类成为非静态类,并将 Acroform 定义移至主类。我正在制作没有字典的 AcroForm,因为它是在 TestButton 类中设置的。这是代码:

import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.interactive.form.PDAcroForm;

import java.io.IOException;
import java.util.ArrayList;

public class TestMain {

    public static void main(String[] args) throws IOException {
        PDDocument document = new PDDocument();
        PDPage page = new PDPage();
        document.addPage(page);

        PDAcroForm buttonAcro = new PDAcroForm(document);
        document.getDocumentCatalog().setAcroForm(buttonAcro);
        buttonAcro.setFields(new ArrayList<>());

        TestButton button = new TestButton();

        float[] location = new float[]{100 , 600 , 60 , 80};
        button.makeButton(document , page , location , "1.jpg" , buttonAcro);

        float[] location2 = new float[]{100 , 400 , 60 , 80};
        button.makeButton(document , page , location2 , "2.jpg", buttonAcro);

        document.save("mytest.pdf");
        document.close();

    }
}
import org.apache.pdfbox.cos.COSDictionary;
import org.apache.pdfbox.cos.COSName;
import org.apache.pdfbox.cos.COSString;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.PDPage;
import org.apache.pdfbox.pdmodel.PDPageContentStream;
import org.apache.pdfbox.pdmodel.PDResources;
import org.apache.pdfbox.pdmodel.common.PDRectangle;
import org.apache.pdfbox.pdmodel.graphics.color.PDColor;
import org.apache.pdfbox.pdmodel.graphics.color.PDDeviceRGB;
import org.apache.pdfbox.pdmodel.graphics.image.PDImageXObject;
import org.apache.pdfbox.pdmodel.interactive.action.PDActionHide;
import org.apache.pdfbox.pdmodel.interactive.action.PDAnnotationAdditionalActions;
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAnnotationWidget;
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAppearanceCharacteristicsDictionary;
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAppearanceDictionary;
import org.apache.pdfbox.pdmodel.interactive.annotation.PDAppearanceStream;
import org.apache.pdfbox.pdmodel.interactive.form.PDAcroForm;
import org.apache.pdfbox.pdmodel.interactive.form.PDPushButton;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

public class TestButton {

    public void makeButton(PDDocument document, PDPage page, float[] thumbLocation, String imageName,
                           PDAcroForm buttonAcro) throws IOException {
        PDImageXObject image = PDImageXObject.createFromFile("src//main/resources/" + imageName, document);
        float thumbX = thumbLocation[0];
        float thumbY = thumbLocation[1];
        float thumbWidth = thumbLocation[2];
        float thumbHeight = thumbLocation[3];

        float lowX = page.getMediaBox().getLowerLeftX();
        float lowY = page.getMediaBox().getLowerLeftY();
        float highY = page.getMediaBox().getUpperRightY();

        float fullX = thumbX - image.getWidth() - 10;
        if (fullX < lowX + 10){
            fullX = thumbX + thumbWidth + 10;
        }
        float fullY = (thumbY + thumbHeight / 2) - (image.getHeight() / 2);
        if (fullY < lowY + 10){
            fullY = thumbY + thumbHeight + 10;
        }
        if (fullY + image.getHeight() > highY - 10){
            fullY = thumbY - image.getHeight() - 10;
        }
        float fullWidth = image.getWidth();
        float fullHeight = image.getHeight();

        String thumbImage = imageName + "_Thumb";
        String fullImage = imageName + "_Full";
        PDColor colourBlack = new PDColor(new float[] { 0, 0, 0 }, PDDeviceRGB.INSTANCE);

        // Set up thumbnail
        COSDictionary thumbDict = new COSDictionary();

        PDPushButton thumbButton = new PDPushButton(buttonAcro);
        thumbButton.setPartialName(thumbImage);
        // Thumbnail actions
        thumbDict.setItem(COSName.T, new COSString(fullImage));

        PDActionHide actionHide = new PDActionHide();
        actionHide.setT(thumbDict);

        PDActionHide actionShow = new PDActionHide();
        actionShow.setT(thumbDict);
        actionShow.setH(false);

        PDAnnotationAdditionalActions additionalActions = new PDAnnotationAdditionalActions();
        additionalActions.setE(actionShow);
        additionalActions.setX(actionHide);
        // Thumbnail widget
        PDAnnotationWidget thumbWidget = thumbButton.getWidgets().get(0);
        thumbWidget.setActions(additionalActions);
        thumbWidget.setRectangle(new PDRectangle(thumbX, thumbY, thumbWidth, thumbHeight));
        // Thumbnail appearance
        PDAppearanceDictionary thumbAppearanceDict = new PDAppearanceDictionary();
        PDAppearanceStream thumbAppearanceStream = new PDAppearanceStream(document);
        thumbAppearanceStream.setResources(new PDResources());
        PDAppearanceCharacteristicsDictionary thumbFieldAppearance
                = new PDAppearanceCharacteristicsDictionary(new COSDictionary());
        thumbFieldAppearance.setBorderColour(colourBlack);
        thumbWidget.setAppearanceCharacteristics(thumbFieldAppearance);
        try (PDPageContentStream thumbContent = new PDPageContentStream(document, thumbAppearanceStream))
        {
            PDRectangle thumbBox = new PDRectangle(
                    thumbWidget.getRectangle().getWidth(), thumbWidget.getRectangle().getHeight());
            thumbAppearanceStream.setBBox(thumbBox);
            thumbContent.setNonStrokingColor(0, 0, 0);
            thumbContent.setLineWidth(0.5f);
            thumbContent.addRect(thumbBox.getLowerLeftX() + 0.5f, thumbBox.getLowerLeftY() + 0.5f,
                    thumbBox.getWidth() - 1, thumbBox.getHeight() - 1);
            thumbContent.stroke();
            thumbContent.drawImage(image , thumbBox.getLowerLeftX() + 0.5f, thumbBox.getLowerLeftY() + 0.5f,
                    thumbBox.getWidth() - 1, thumbBox.getHeight() - 1);
        }
        thumbAppearanceDict.setNormalAppearance(thumbAppearanceStream);
        thumbWidget.setAppearance(thumbAppearanceDict);
        thumbWidget.setHidden(false);
        thumbWidget.setPrinted(true);


        page.getAnnotations().add(thumbWidget);
        buttonAcro.getFields().add(thumbButton);


        // Set up full
        PDPushButton fullButton = new PDPushButton(buttonAcro);
        fullButton.setPartialName(fullImage);
        // Full widget
        PDAnnotationWidget fullWidget = fullButton.getWidgets().get(0);
        fullWidget.setRectangle(new PDRectangle(fullX - 1 , fullY - 1, fullWidth + 2 , fullHeight + 2));
        // Full appearance
        PDAppearanceDictionary fullAppearanceDict = new PDAppearanceDictionary();
        PDAppearanceStream fullAppearanceStream = new PDAppearanceStream(document);
        fullAppearanceStream.setResources(new PDResources());
        PDAppearanceCharacteristicsDictionary fullFieldAppearance
                = new PDAppearanceCharacteristicsDictionary(new COSDictionary());
        fullFieldAppearance.setBorderColour(colourBlack);
        fullWidget.setAppearanceCharacteristics(fullFieldAppearance);
        try (PDPageContentStream fullContent = new PDPageContentStream(document, fullAppearanceStream))
        {
            PDRectangle fullBox = new PDRectangle(
                    fullWidget.getRectangle().getWidth(), fullWidget.getRectangle().getHeight());
            fullAppearanceStream.setBBox(fullBox);
            fullContent.setNonStrokingColor(0, 0, 0);
            fullContent.setLineWidth(1);
            fullContent.addRect(fullBox.getLowerLeftX() + 1, fullBox.getLowerLeftY() + 1,
                    fullBox.getWidth() - 2, fullBox.getHeight() - 2);
            fullContent.stroke();
            fullContent.drawImage(image, fullBox.getLowerLeftX() + 1, fullBox.getLowerLeftY() + 1,
                    fullBox.getWidth() - 2, fullBox.getHeight() - 2);
        }
        fullAppearanceDict.setNormalAppearance(fullAppearanceStream);
        fullWidget.setAppearance(fullAppearanceDict);
        fullWidget.setHidden(true);
        fullWidget.setPrinted(false);

        page.getAnnotations().add(fullWidget);
        buttonAcro.getFields().add(fullButton);
    }
}

推荐阅读