8

我正在创建 PDF 并写入流作为响应。在写入流之前,我想在所有页面中添加背景图像作为水印,以便通过响应刷新的 PDF 文档是最后一个带有水印的文档。

嗨,这是我的代码示例。任何帮助将不胜感激

private static String generatePDF(HttpServletRequest request, HttpServletResponse   response, String fileName) throws Exception
{
    Document document = null;
    PdfWriter writer = null;
    FileOutputStream fos = null;
    try
    {
       fos = new FileOutputStream(fileName);
       Document document = new Document(PageSize.A4);
       writer = PdfWriter.getInstance(document, fos);
       document.open();

       /**
        * Adding tables and cells and other stuff required
        **/

       return pdfFileName;
  } catch (Exception e) {
       FileUtil.deleteFile(fileName);
       throw e
  } finally {
    if (document != null) {
        document.close();
    }
    fos.flush();
  }
}

我现在想使用以下代码添加背景图像并将输出 PDF 写入同一流

PdfReader sourcePDFReader = null;
try
{
   sourcePDFReader = new PdfReader(sourcePdfFileName);
   int noOfPages = sourcePDFReader.getNumberOfPages();
   PdfStamper stamp = new PdfStamper(sourcePDFReader, new FileOutputStream(destPdfFileName));
   int i = 0;
   Image templateImage = Image.getInstance(templateImageFile);
   templateImage.setAbsolutePosition(0, 0);
   PdfContentByte tempalteBytes;
   while (i < noOfPages) {
       i++;
       tempalteBytes = stamp.getUnderContent(i);
       tempalteBytes.addImage(templateImage);
   }
   stamp.close();
   return destPdfFileName;
} catch (Exception ex) {
   LOGGER.log(Level.INFO, "Error when applying tempalte image as watermark");
} finally {
     if (sourcePDFReader != null) {
         sourcePDFReader.close();
     }
}
4

3 回答 3

12

我使用布鲁诺的第一种(推荐)方法解决了这个问题。

1)使用事件创建页面事件助手onEndPage

class PDFBackground extends PdfPageEventHelper {

    @Override
    void onEndPage(PdfWriter writer, Document document) {
        Image background = Image.getInstance("myimage.png");
        // This scales the image to the page,
        // use the image's width & height if you don't want to scale.
        float width = document.getPageSize().getWidth();
        float height = document.getPageSize().getHeight();
        writer.getDirectContentUnder()
                .addImage(background, width, 0, 0, height, 0, 0);
    }

}

2)在创建你的作家时,注册你的页面事件助手:

PdfWriter writer = PdfWriter.getInstance(document, new FileOutputStream(file));
writer.setPageEvent(new PDFBackground());
于 2013-10-12T15:49:44.000 回答
4

我已经用布鲁诺的第二个选项解决了这个问题。这是代码。

public static String addBackgroundImageToPDF(ByteArrayOutputStream bos, String destPdfFileName, String templateImageFile)
{
  PdfReader sourcePDFReader = null;
  try
  {
        sourcePDFReader = new PdfReader(bos.toByteArray());
        int noOfPages = sourcePDFReader.getNumberOfPages();
        PdfStamper stamp = new PdfStamper(sourcePDFReader, new FileOutputStream(destPdfFileName));
        int i = 0;
        Image templateImage = Image.getInstance(templateImageFile);
        templateImage.setAbsolutePosition(0, 0);
        PdfContentByte tempalteBytes;
        while (i < noOfPages)
        {
              i++;
              tempalteBytes = stamp.getUnderContent(i);    
              tempalteBytes.addImage(templateImage);  
        }
         stamp.close();
        return destPdfFileName;
  }
  catch (Exception ex)
  {
        LOGGER.log(Level.INFO, "Error when applying template image as watermark");
  }
  finally
  {
        if (sourcePDFReader != null)
        {
              sourcePDFReader.close();
        }
  }
}
于 2013-09-18T14:54:57.193 回答
2

您可以在两个选项之间进行选择:

  1. 在页面事件中使用背景图片(到 'under'onEndPage(方法中的内容)/
  2. 在内存中创建第一个 PDF,然后使用您发布的代码在第二遍中添加背景图像。

我更喜欢选项1。

于 2012-10-02T06:26:18.360 回答