将 PDF 页面导出为 Java 中的一系列图像

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/550129/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 16:07:26  来源:igfitidea点击:

Export PDF pages to a series of images in Java

javaimagepdfexport

提问by dasp

I need to export the pages of an arbitrary PDF document into a series of individual images in jpeg/png/etc format. I need to do this in in Java.

我需要将任意 PDF 文档的页面导出为一系列 jpeg/png/etc 格式的单个图像。我需要在 Java 中执行此操作。

Although I do know about iText, PDFBox and various other java pdf libraries, I am hoping for a pointer to some working example, or some how-to.

尽管我确实了解 iText、PDFBox 和各种其他 java pdf 库,但我希望有一个指向一些工作示例或一些操作方法的指针。

Thanks.

谢谢。

采纳答案by jedierikb

Here is one way to do it, combining some code fragments from around the web.

这是一种方法,结合来自网络的一些代码片段。

How do I draw a PDF into an Image?

如何将 PDF 绘制成图像?

https://pdf-renderer.dev.java.net/examples.html

https://pdf-renderer.dev.java.net/examples.html

Creating a Buffered Image from an Image

从图像创建缓冲图像

ORIGINAL: http://www.exampledepot.com/egs/java.awt.image/Image2Buf.html

原文:http: //www.exampledepot.com/egs/java.awt.image/Image2Buf.html

UPDATED: How to convert buffered image to image and vice-versa?

更新:如何将缓冲图像转换为图像,反之亦然?

Saving a Generated Graphic to a PNG or JPEG File

将生成的图形保存为 PNG 或 JPEG 文件

ORIGINAL: http://www.exampledepot.com/egs/javax.imageio/Graphic2File.html

原文:http: //www.exampledepot.com/egs/javax.imageio/Graphic2File.html

UPDATED: http://docs.oracle.com/javase/tutorial/2d/images/saveimage.html

更新:http: //docs.oracle.com/javase/tutorial/2d/images/saveimage.html

Combined together into something that works like this to turn all the pages into images:

组合在一起,像这样将所有页面变成图像:

import com.sun.pdfview.PDFFile;
import com.sun.pdfview.PDFPage;

import java.awt.Graphics;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.HeadlessException;
import java.awt.Image;
import java.awt.Rectangle;
import java.awt.Transparency;
import java.io.*;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import javax.swing.*;
import javax.imageio.*;
import java.awt.image.*;

public class ImageMain {
    public static void setup() throws IOException {
        // load a pdf from a byte buffer
        File file = new File("test.pdf");
        RandomAccessFile raf = new RandomAccessFile(file, "r");
        FileChannel channel = raf.getChannel();
        ByteBuffer buf = channel.map(FileChannel.MapMode.READ_ONLY, 0, channel.size());
        PDFFile pdffile = new PDFFile(buf);
        int numPgs = pdffile.getNumPages();
        for (int i = 0; i < numPgs; i++) {
            // draw the first page to an image
            PDFPage page = pdffile.getPage(i);
            // get the width and height for the doc at the default zoom
            Rectangle rect = new Rectangle(0, 0, (int) page.getBBox().getWidth(), (int) page.getBBox().getHeight());
            // generate the image
            Image img = page.getImage(rect.width, rect.height, // width & height
                    rect, // clip rect
                    null, // null for the ImageObserver
                    true, // fill background with white
                    true // block until drawing is done
                    );
            // save it as a file
            BufferedImage bImg = toBufferedImage(img);
            File yourImageFile = new File("page_" + i + ".png");
            ImageIO.write(bImg, "png", yourImageFile);
        }
    }

    // This method returns a buffered image with the contents of an image
    public static BufferedImage toBufferedImage(Image image) {
        if (image instanceof BufferedImage) {
            return (BufferedImage) image;
        }
        // This code ensures that all the pixels in the image are loaded
        image = new ImageIcon(image).getImage();
        // Determine if the image has transparent pixels; for this method's
        // implementation, see e661 Determining If an Image Has Transparent
        // Pixels
        boolean hasAlpha = hasAlpha(image);
        // Create a buffered image with a format that's compatible with the
        // screen
        BufferedImage bimage = null;
        GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
        try {
            // Determine the type of transparency of the new buffered image
            int transparency = Transparency.OPAQUE;
            if (hasAlpha) {
                transparency = Transparency.BITMASK;
            }
            // Create the buffered image
            GraphicsDevice gs = ge.getDefaultScreenDevice();
            GraphicsConfiguration gc = gs.getDefaultConfiguration();
            bimage = gc.createCompatibleImage(image.getWidth(null), image.getHeight(null), transparency);
        } catch (HeadlessException e) {
            // The system does not have a screen
        }
        if (bimage == null) {
            // Create a buffered image using the default color model
            int type = BufferedImage.TYPE_INT_RGB;
            if (hasAlpha) {
                type = BufferedImage.TYPE_INT_ARGB;
            }
            bimage = new BufferedImage(image.getWidth(null), image.getHeight(null), type);
        }
        // Copy image to buffered image
        Graphics g = bimage.createGraphics();
        // Paint the image onto the buffered image
        g.drawImage(image, 0, 0, null);
        g.dispose();
        return bimage;
    }

    public static boolean hasAlpha(Image image) {
        // If buffered image, the color model is readily available
        if (image instanceof BufferedImage) {
            BufferedImage bimage = (BufferedImage) image;
            return bimage.getColorModel().hasAlpha();
        }
        // Use a pixel grabber to retrieve the image's color model;
        // grabbing a single pixel is usually sufficient
        PixelGrabber pg = new PixelGrabber(image, 0, 0, 1, 1, false);
        try {
            pg.grabPixels();
        } catch (InterruptedException e) {
        }
        // Get the image's color model
        ColorModel cm = pg.getColorModel();
        return cm.hasAlpha();
    }

    public static void main(final String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                try {
                    ImageMain.setup();
                } catch (IOException ex) {
                    ex.printStackTrace();
                }
            }
        });
    }
}

回答by jedierikb

If you consider the JPedal PDF library, its built in and documented with eample source at https://support.idrsolutions.com/hc/en-us/articles/115001978091-Convert-PDF-Files-to-Image

如果您考虑 JPedal PDF 库,其内置并在https://support.idrsolutions.com/hc/en-us/articles/115001978091-Convert-PDF-Files-to-Image

回答by Ravi Amlani

Just start your for loop from 1 instead of 0. Your problem will be solved.

只需从 1 而不是 0 开始您的 for 循环。您的问题将得到解决。

回答by alaris

If you find out that the sun renderer is not working for all your PDF documents, you may look into using jPDFImages.

如果您发现 sun 渲染器不适用于您的所有 PDF 文档,您可以考虑使用 jPDFImages。

To be more efficient, you should convert each PDF page to a buffered image and from there convert to the various image formats you need. This would avoid having to convert from PDF to images for each format.

为了提高效率,您应该将每个 PDF 页面转换为缓冲图像,然后从那里转换为您需要的各种图像格式。这将避免必须为每种格式从 PDF 转换为图像。

Here is the link to convert from PDF to buffered images using jPDFImages: http://kbdeveloper.qoppa.com/jpdfimages/codesampleconvertpdfpageintobufferedimageinjava

这是使用 jPDFImages 从 PDF 转换为缓冲图像的链接:http://kbdeveloper.qoppa.com/jpdfimages/codesampleconvertpdfpageintobufferedimageinjava

For each page image you can simply export to different image formats: ImageIO.write(pageBufferedImage, "JPEG", outputFile); ImageIO.write(pageBufferedImage, "PNG", outputFile); etc...

对于每个页面图像,您可以简单地导出为不同的图像格式: ImageIO.write(pageBufferedImage, "JPEG", outputFile); ImageIO.write(pageBufferedImage, "PNG", outputFile); 等等...

回答by Neeraj

There are different libraries to do it. I have achieved this with PDFBox. But in my opinion the most efficient solution is to use ghostscript. But if you think you need an easy solution, use ImageMagick. But ImageMagick internally calls the ghostscript. Using ghostscript or imagemagick give you a better solution. It is much faster than any other libraries.

有不同的库可以做到这一点。我已经用PDFBox实现了这一点。但在我看来,最有效的解决方案是使用ghostscript。但如果您认为需要一个简单的解决方案,请使用ImageMagick。但是 ImageMagick 在内部调用了 ghostscript。使用 ghostscript 或 imagemagick 为您提供更好的解决方案。它比任何其他库都要快得多。

回答by Nikita Jain

PDF to Bitmap (Android compatible code)

PDF转位图(Android兼容代码)

File pdfFile = new File(filePath);
PdfRenderer renderer = new PdfRenderer(ParcelFileDescriptor.open(pdfFile, ParcelFileDescriptor.MODE_READ_ONLY));

final int pageCount = renderer.getPageCount();
//Currently for a page, iterate for all the pages
PdfRenderer.Page page = renderer.openPage(pageCount);
int width =  page.getWidth();
int height = page.getHeight();

Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);

Bitmap to PNG (or any other format)

位图到 PNG(或任何其他格式)