使用 Java 将 pdf 转换为 Postscript

Convert pdf to Postscript using Java

我最近发布了一个如何将 PDF byte[] 转换为 Postscript 的问题。根据评论,不可能。

无论如何,我正在研究另一个关于如何将 pdf 转换为 Postscript 的问题。但是仍然无法正常工作。

我已经保存了 PDF,如何将现有的 PDF 转换为 Postscript?有什么方法可以修改下面的代码以获得结果吗?

import java.io.File;
import java.io.FileOutputStream;
import javax.print.DocFlavor;
import javax.print.DocPrintJob;
import javax.print.SimpleDoc;
import javax.print.StreamPrintService;
import javax.print.StreamPrintServiceFactory;
import javax.print.attribute.HashPrintRequestAttributeSet;
import javax.print.attribute.PrintRequestAttributeSet;

import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.printing.PDFPrintable;
import org.apache.pdfbox.printing.Scaling;

public class Printing {


        public static void main(String[] args) {
            try {
            DocFlavor flavor = DocFlavor.SERVICE_FORMATTED.PRINTABLE;
            String psMimeType = DocFlavor.BYTE_ARRAY.POSTSCRIPT.getMimeType();
            StreamPrintServiceFactory[] factories = StreamPrintServiceFactory.lookupStreamPrintServiceFactories(flavor, psMimeType);

            System.out.println ("Available PS services: " + factories.length);
            System.out.println ("Format: " + factories[0].getOutputFormat());

            FileOutputStream outStream = new FileOutputStream("/path/to/your.ps");
            StreamPrintService printService = factories[0].getPrintService(outStream);


            PrintRequestAttributeSet aset = new HashPrintRequestAttributeSet();
            aset.add(MediaSizeName.NA_LETTER);              

            PDDocument doc = PDDocument.load(new File("/path/to/my.pdf"));

            SimpleDoc pdfDoc = new SimpleDoc(new PDFPrintable(doc, Scaling.SCALE_TO_FIT, false), flavor, null);

            DocPrintJob newJob = printService.createPrintJob();
            newJob.print(pdfDoc, aset);

            outStream.close();

            }
            catch(Exception ex) {
                ex.printStackTrace();
            }
        }
}

编辑: 我尝试根据评论进行修改,但是当我尝试加载文件时崩溃 f:

public static void MakePS(String pathToPdf) throws PrinterException, IOException, PrintException {
            DocFlavor flavor = DocFlavor.SERVICE_FORMATTED.PRINTABLE;
            DocAttributeSet daset = new HashDocAttributeSet();

            StreamPrintServiceFactory[] factories =
                    StreamPrintServiceFactory.lookupStreamPrintServiceFactories(flavor,
                            DocFlavor.BYTE_ARRAY.POSTSCRIPT.getMimeType());
            if (factories.length == 0) {
                throw new PrinterException("No PostScript factories available");
            }
            File f = new File(pathToPdf);
            PDDocument document = null;
            try {
                document = PDDocument.load(f);
            } catch (IOException e) {
                System.out.println("Cannot load file to pdf document");
                e.printStackTrace();
            };

            // Attributes are specified by https://docs.oracle.com/javase/7/docs/api/
            // see package javax.print.attribute.standard
            PrintRequestAttributeSet aset = new HashPrintRequestAttributeSet();
            aset.add(MediaSizeName.NA_LETTER);
            aset.add(new PageRanges(1, document.getNumberOfPages()));

            FileOutputStream fos = new FileOutputStream(pathToPdf);
            factories[0].getPrintService(fos).createPrintJob().print(
                    new SimpleDoc(new PDFPrintable(document, Scaling.ACTUAL_SIZE, false), flavor, daset), aset);
            fos.close();
            document.close();
        }

尝试 PDDocument.load(f) 时出现以下错误:

16:37:05,448 ERROR [stderr] (pool-15-thread-1) Exception in thread "pool-15-thread-1" java.lang.NoClassDefFoundError: org/apache/pdfbox/pdmodel/PDDocument
16:37:05,449 ERROR [stderr] (pool-15-thread-1)  at com.app.servlet.PdfToPsFile.MakePS(PdfToPsFile.java:168)
16:37:05,450 ERROR [stderr] (pool-15-thread-1)  at com.app.servlet.PrintServlet.lambda$doGet(PrintServlet.java:151)
16:37:05,451 ERROR [stderr] (pool-15-thread-1)  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
16:37:05,451 ERROR [stderr] (pool-15-thread-1)  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
16:37:05,452 ERROR [stderr] (pool-15-thread-1)  at java.lang.Thread.run(Thread.java:748)
16:37:05,453 ERROR [stderr] (pool-15-thread-1) Caused by: java.lang.ClassNotFoundException: org.apache.pdfbox.pdmodel.PDDocument from [Module ".war:main" from Service Module Loader]
16:37:05,454 ERROR [stderr] (pool-15-thread-1)  at org.jboss.modules.ModuleClassLoader.findClass(ModuleClassLoader.java:211)
16:37:05,455 ERROR [stderr] (pool-15-thread-1)  at org.jboss.modules.ConcurrentClassLoader.performLoadClassUnchecked(ConcurrentClassLoader.java:459)
16:37:05,456 ERROR [stderr] (pool-15-thread-1)  at org.jboss.modules.ConcurrentClassLoader.performLoadClassChecked(ConcurrentClassLoader.java:408)
16:37:05,457 ERROR [stderr] (pool-15-thread-1)  at org.jboss.modules.ConcurrentClassLoader.performLoadClass(ConcurrentClassLoader.java:389)
16:37:05,457 ERROR [stderr] (pool-15-thread-1)  at org.jboss.modules.ConcurrentClassLoader.loadClass(ConcurrentClassLoader.java:134)
´´´

Tilman Hausherr 为我遇到的问题提供了正确的答案。到目前为止,我可以使用此代码生成一页 PS 文件。但不会产生额外的页面。我在这个 post 中,您可以通过 Postscript 命令以某种方式打印,这不会使文件膨胀。稍后将不得不研究这个。首先尝试解决如何添加额外的页面。这是代码:

public static void MakePSFile(String pathToPdf) {
        try {
            DocFlavor flavor = DocFlavor.SERVICE_FORMATTED.PRINTABLE;
            String psMimeType = DocFlavor.BYTE_ARRAY.POSTSCRIPT.getMimeType();
            StreamPrintServiceFactory[] factories = StreamPrintServiceFactory.lookupStreamPrintServiceFactories(flavor, psMimeType);

            System.out.println("Available PS services: " + factories.length);
            System.out.println("Format: " + factories[0].getOutputFormat());

            FileOutputStream outStream = new FileOutputStream("c:/psFile.ps");
            StreamPrintService printService = factories[0].getPrintService(outStream);


            PrintRequestAttributeSet aset = new HashPrintRequestAttributeSet();
            aset.add(MediaSizeName.NA_LETTER);

            PDDocument doc = PDDocument.load(new File(pathToPdf));

            SimpleDoc pdfDoc = new SimpleDoc(new PDFPrintable(doc, Scaling.SCALE_TO_FIT, false), flavor, null);

            DocPrintJob newJob = printService.createPrintJob();
            newJob.print(pdfDoc, aset);

            outStream.close();

        } catch (Exception ex) {
            ex.printStackTrace();
        }
    }