【问题标题】:Output PDF using ServletOutputStream使用 ServletOutputStream 输出 PDF
【发布时间】:2011-08-24 00:39:54
【问题描述】:

我只是想问一下是否有使用 ServletOutputStream 在网页中输出 PDF 的方法?例如,如果没有安装 Adob​​e 插件或未使用 Chrome,我想让 PDF 仍然显示。

【问题讨论】:

    标签: java pdf web


    【解决方案1】:

    用户将必须在其 PC 上安装某种类型的 PDF 查看器来打开/阅读 PDF 文件,无论是 Adob​​e Reader 还是其他软件。您可以通过发送正确的 HTTP 标头向用户发送 PDF 文件,以便在浏览器中打开或下载(另存为附件)。具体来说:

    Content-type: application/pdf
    Content-Disposition: attachment; filename=downloaded.pdf
    Content-Length: XXX
    Content-Transfer-Encoding: base64
    

    Content-Disposition 标头是建议下载与“在浏览器中打开”的标头。一旦您 已发送标头,发送一个空行,然后写出您的数据(通常为 base64 编码)。

    【讨论】:

    • 再次,要求是“未安装插件/仅使用本机 Java sdks/无小程序/无 jsf”。
    • 好吧,你大概可以使用Java从文件中读取PDF文件和通用静态图像文件,在没有插件的情况下绝对可以在浏览器中查看。
    • 查看这篇文章,了解如何实现这一点的想法/指针:stackoverflow.com/questions/550129/…
    • 当然我可以这样做,但问题是每个图像的导航以及处理后图像的存储位置,当我建议 Applets 和 JSF 时,我得到了红灯。感谢老兄的勇敢尝试! ^^
    • 什么导航?保存您在服务器上创建的图像(通过 Java FileOutputStream 输出),然后将它们一个接一个地放入您的 HTML 文档中:` 等. 如果图像太多而无法在一页上显示,请添加一些指向多个 HTML 页面的链接。不难!
    【解决方案2】:

    你的 servlet 可以输出它想要的任何类型的文档;但是,浏览器只会显示它知道如何显示的文档,无论是本机(例如 HTML、文本、GIF、PNG、JPG 等)还是通过插件(PDF、SWF 等)。

    如果您的 servlet 输出一个有效的 PDF 文档,而浏览器无法在本地显示它(如 Chrome 可以)或无法加载插件来呈现它(如 Adob​​e),那么它可能会要求用户保存它或选择一个可以显示它的程序。

    【讨论】:

    • 谢谢!我想我现在应该放弃了。 :)
    • 不要放弃!只要弄清楚什么是可能的,什么是不可能的,然后从那里开始!
    • 但要求是“未安装插件/仅使用本机 Java sdks/无小程序/无 jsf”。
    • 呃,我说的很笼统。如果您被要求做一些不可能的事情,请向您的雇主解释为什么这些要求是不可能的并提供解决方法。
    • 是的,我也是这么想的,这是不可能的。老板终于放弃了。感谢您的支持,您的想法并没有浪费,我今天学到了一些新东西。 :)
    【解决方案3】:

    +1 因为是一个有效的问题。

    客户端

    您可以使用 pdf.js 来自 mozilla 的 javascript 库将 pdf 显示为图像

    服务器端

    如果您的 pdf 位于文件系统 modified from here

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String pdfFileName = "pdf-test.pdf";
        String contextPath = getServletContext().getRealPath(File.separator);
        File pdfFile = new File(contextPath + pdfFileName);
    
        response.setContentType("application/pdf");
        response.addHeader("Content-Disposition", "inline; filename=" + pdfFileName)
        response.setContentLength((int) pdfFile.length());
    
        FileInputStream fileInputStream = new FileInputStream(pdfFile);
        OutputStream responseOutputStream = response.getOutputStream();
        int bytes;
        while ((bytes = fileInputStream.read()) != -1) {
            responseOutputStream.write(bytes);
        }
    }
    

    如果您使用 pdfbox 之类的库在内存中生成 pdf

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        int marginTop = 30;
        String title = "HELLO WORLD";
    
        final PDFont fontData = PDType1Font.HELVETICA;
        final int fontSize = 8;
    
        //java8 color issue
        System.setProperty("sun.java2d.cmm", "sun.java2d.cmm.kcms.KcmsServiceProvider");
    
        final PDPage page = new PDPage();
        final PDFont fontLabel = PDType1Font.HELVETICA_BOLD;
        final int titleFontSize = 12;
        float heightLabelText = fontLabel.getFontDescriptor().getFontBoundingBox().getHeight() / 1000 * fontSize;
    
        try (final PDDocument pdf = new PDDocument())
        {
            pdf.addPage(page);
            try (PDPageContentStream stream = new PDPageContentStream(pdf, page)) {
                float top = page.getMediaBox().getHeight() - marginTop;
    
                float titleWidth = fontLabel.getStringWidth(title) / 1000 * titleFontSize;
    
                stream.setFont(fontLabel, titleFontSize);
                stream.beginText();
                stream.newLineAtOffset((page.getMediaBox().getWidth() - titleWidth) / 2, top - 25);
                stream.showText(title);
                stream.endText();
            }
            try(ByteArrayOutputStream output = new ByteArrayOutputStream()) {
                pdf.save(output);
                resp.setContentType("application/pdf");
                resp.addHeader("Content-Disposition", "inline; filename=\"yourFile" + "-" + new Random().nextInt() + ".pdf" + "\"");
                byte[] bytes = output.toByteArray();
                resp.getOutputStream().write(bytes);
                resp.setContentLength((int) bytes.length);
            }
    
        }
    }
    

    【讨论】:

      猜你喜欢
      • 2015-02-27
      • 2014-09-05
      • 2016-08-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-30
      • 1970-01-01
      • 2015-04-23
      相关资源
      最近更新 更多