Java 處理PDF文檔(一):頁眉頁腳、水印、背景、附件
阿新 • • 發佈:2019-01-21
ack ioe 條碼 lib int ont proc rand graph 前言
本文將介紹通過Java編程來處理PDF文檔的一些方法,因為一篇文檔的處理可能包括很多內容,比如文檔安全性設置(水印、加密/解密)、文本/圖片/圖形操作、註釋、附件、域、文檔轉換(其他文件格式轉為PDF或PDF轉為其他文件格式)、表格、書簽、文本/圖片讀取、文檔合並拆分等等,針對不同的程序設計需求,這裏對PDF操作的需求也就不同。在接下來的文章中,也將分次介紹Java代碼示例的具體操作方法。
本次Java操作PDF文檔要點概括:
本文將介紹通過Java編程來處理PDF文檔的一些方法,因為一篇文檔的處理可能包括很多內容,比如文檔安全性設置(水印、加密/解密)、文本/圖片/圖形操作、註釋、附件、域、文檔轉換(其他文件格式轉為PDF或PDF轉為其他文件格式)、表格、書簽、文本/圖片讀取、文檔合並拆分等等,針對不同的程序設計需求,這裏對PDF操作的需求也就不同。在接下來的文章中,也將分次介紹Java代碼示例的具體操作方法。
本次Java操作PDF文檔要點概括:
- 添加頁眉/頁腳
- 添加PDF文本水印、圖片水印
- 設置PDF文檔背景色:純色、圖片背景色
- 添加附件到PDF(2種方式)
關於使用工具:Spire.PDF for Java
這款PDF控件是E-iceblue公司發布的Java系列產品之一,目前為止該系列下有Spire.PDF、Spire.Barcode(二維碼、條碼控件)、 Spire.Presentation(PPT控件)等三個控件,都有免費版Free Spire系列,這點比較好,對於不熟悉該控件時,測試和使用都比較方便。當然,程序上對文檔的操作有更高的要求時,建議還是使用商業版,畢竟更強大的功能對你的程序設計是百利而無一害的。要下載Spire.PDF for Java可通過以下途徑:
2.CSDN: https://download.csdn.net/download/miaonly/10867030 (免費版)
3.51CTO: http://down.51cto.com/data/2457197 (免費版)
Jar文件導入:
步驟1:在Java程序中新建一個文件夾可命名為Lib。下載安裝包後,解壓,將解壓後的文件夾下的子文件夾lib中的Spire.Pdf.jar和Spire.Common.jar兩個文件復制到程序中新建的文件夾下,如下圖:
步驟2:建好文件夾後,引用兩個文件:選中這兩個jar文件,點擊鼠標右鍵,選擇“Build Path” – “Add to Build Path”。如下圖:
代碼示例(供參考),這裏示例代碼僅供列出實現功能需求效果,具體實現效果,請結合實際程序項目進行測試,如遇問題不好解決的話可聯系Q: 2181348176。【示例1】頁眉頁腳
import java.awt.*; import java.awt.geom.Dimension2D; import com.spire.pdf.*; import com.spire.pdf.automaticfields.PdfAutomaticField; import com.spire.pdf.automaticfields.PdfCompositeField; import com.spire.pdf.automaticfields.PdfPageCountField; import com.spire.pdf.automaticfields.PdfPageNumberField; import com.spire.pdf.graphics.*; public class HeaderFooter { public static void main(String[] args) throws Exception { //創建 PdfDocument 對象 PdfDocument doc = new PdfDocument(); //創建PdfMargins對象, 並設置的頁邊距 PdfMargins margin = new PdfMargins(60,60,40,40); //調用 addHeaderAndFooter()方法添加頁眉頁腳 addHeaderAndFooter(doc, PdfPageSize.A4, margin); //保存文檔 doc.saveToFile("output/headerFooter.pdf"); doc.close(); } static void addHeaderAndFooter(PdfDocument doc, Dimension2D pageSize, PdfMargins margin) { PdfPageTemplateElement header = new PdfPageTemplateElement(margin.getLeft(), pageSize.getHeight()); doc.getTemplate().setLeft(header); PdfPageTemplateElement topSpace = new PdfPageTemplateElement(pageSize.getWidth(), margin.getTop()); topSpace.setForeground(true); doc.getTemplate().setTop(topSpace); //添加頁眉 PdfTrueTypeFont font= new PdfTrueTypeFont(new Font("Arial Unicode MS",Font.PLAIN,10),true); PdfStringFormat format = new PdfStringFormat(PdfTextAlignment.Left); String label = "2018年 年度會議報告"; Dimension2D dimension2D = new Dimension(); dimension2D.setSize(font.measureString(label, format)); float y = topSpace.getHeight() - font.getHeight() - 1; PdfPen pen = new PdfPen(new PdfRGBColor(Color.black), 0.75f); topSpace.getGraphics().setTransparency(0.5f); topSpace.getGraphics().drawLine(pen, margin.getLeft(), y, pageSize.getWidth() - margin.getRight(), y); y = y - 1 - (float) dimension2D.getHeight(); topSpace.getGraphics().drawString(label, font, PdfBrushes.getBlack(), margin.getLeft(), y, format); PdfPageTemplateElement rightSpace = new PdfPageTemplateElement(margin.getRight(), pageSize.getHeight()); doc.getTemplate().setRight(rightSpace); //添加顯示當前頁及總頁數的域作為頁腳 PdfPageTemplateElement footer = new PdfPageTemplateElement(pageSize.getWidth(), margin.getBottom()); footer.setForeground(true); doc.getTemplate().setBottom(footer); y = font.getHeight() + 1; footer.getGraphics().setTransparency(0.5f); footer.getGraphics().drawLine(pen, margin.getLeft(), y, pageSize.getWidth() - margin.getRight(), y); y = y + 1; PdfPageNumberField pageNumber = new PdfPageNumberField(); PdfPageCountField pageCount = new PdfPageCountField(); PdfCompositeField pageNumberLabel = new PdfCompositeField(); pageNumberLabel.setAutomaticFields(new PdfAutomaticField[]{pageNumber, pageCount}); pageNumberLabel.setBrush(PdfBrushes.getBlack()); pageNumberLabel.setFont(font); format = new PdfStringFormat(PdfTextAlignment.Right); pageNumberLabel.setStringFormat(format); pageNumberLabel.setText("第{0}頁 共{1}頁"); pageNumberLabel.setBounds(footer.getBounds()); pageNumberLabel.draw(footer.getGraphics(), pageSize.getWidth() - margin.getLeft(), y); } }
頁眉頁腳實現效果:
【示例2】添加水印
這裏將分別使用insertTextWatermark(PdfPageBase page, String watermark)方法以及page.SetBackgroundImage(String arg0)方法來設置文本水印和圖片水印。
1.文本水印
import com.spire.pdf.*;
import com.spire.pdf.graphics.*;
import java.awt.*;
import java.awt.geom.*;
public class Textwatermark {
public static void main(String[] args) {
//創建PdfDocument類的對象
PdfDocument pdf = new PdfDocument();
//加載測試文檔
pdf.loadFromFile("test.pdf");
//獲取測試文檔中的第一頁
PdfPageBase page = pdf.getPages().get(0);
//調用insertWatermark()方法添加文本水印
insertWatermark(page, "TOP SECRET");
//保存文檔
pdf.saveToFile("out/textWaterMark.pdf");
}
static void insertWatermark(PdfPageBase page, String watermark) {
Dimension2D dimension2D = new Dimension();
dimension2D.setSize(page.getCanvas().getClientSize().getWidth() / 5, page.getCanvas().getClientSize().getHeight() / 5);
PdfTilingBrush brush = new PdfTilingBrush(dimension2D);
brush.getGraphics().setTransparency(0.4F);
brush.getGraphics().save();
brush.getGraphics().translateTransform((float) brush.getSize().getWidth() / 5, (float) brush.getSize().getHeight() / 5);
brush.getGraphics().rotateTransform(-45);
brush.getGraphics().drawString(watermark, new PdfFont(PdfFontFamily.Helvetica, 15), PdfBrushes.getViolet(), 0 , 0 , new PdfStringFormat(PdfTextAlignment.Center));
brush.getGraphics().restore();
brush.getGraphics().setTransparency(1);
Rectangle2D loRect = new Rectangle2D.Float();
loRect.setFrame(new Point2D.Float(0, 0), page.getCanvas().getClientSize());
page.getCanvas().drawRectangle(brush, loRect);
}
}
文本水印效果:
2.圖片水印
import com.spire.pdf.*;
import java.awt.geom.Rectangle2D;
public class Imgwatermark {
public static void main(String[] args) {
//實例化PdfDocument類的對象,並加載測試文檔
PdfDocument doc = new PdfDocument();
doc.loadFromFile("test.pdf");
//獲取文檔第1頁
PdfPageBase page = doc.getPages().get(0);
//加載圖片,設置為背景水印
page.setBackgroundImage("logo.png");
//指定水印在文檔中的位置及圖片大小
Rectangle2D.Float rect = new Rectangle2D.Float();
rect.setRect(150, 150, 300, 150);
page.setBackgroundRegion(rect);
//保存文檔
doc.saveToFile("output/imageWaterMark.pdf");
doc.close();
}
}
圖片水印添加效果:
【示例3】添加背景色
1.添加純色背景色
import com.spire.pdf.PdfDocument;
import com.spire.pdf.PdfPageBase;
import java.awt.*;
public class SetBackgroundColor1 {
public static void main(String[] args) {
//加載PDF文檔
PdfDocument doc = new PdfDocument();
doc.loadFromFile("test.pdf");
PdfPageBase page;
//獲取文檔的總頁數
int pageCount = doc.getPages().getCount();
//遍歷頁面,設置背景顏色
for(int i = 0; i < pageCount; i ++) {
page = doc.getPages().get(i);
page.setBackgroundColor(Color.yellow);
}
//保存文檔
doc.saveToFile("BackgroundColor.pdf");
}
}
純色背景色效果:
2.添加圖片背景
import com.spire.pdf.PdfDocument;
import com.spire.pdf.PdfPageBase;
public class SetBackgroundColor2 {
public static void main(String[] args) {
//加載PDF文檔
PdfDocument doc = new PdfDocument();
doc.loadFromFile("test.pdf");
PdfPageBase page;
//獲取文檔的總頁數
int pageCount = doc.getPages().getCount();
//遍歷頁面,設置背景圖片
for(int i = 0; i < pageCount; i ++) {
page = doc.getPages().get(i);
page.setBackgroundImage("tp.png");
}
//保存文檔
doc.saveToFile("BackgroundImage2.pdf");
}
}
圖片背景色效果:
【示例4】添加附件
import com.spire.pdf.PdfDocument;
import com.spire.pdf.annotations.*;
import com.spire.pdf.attachments.PdfAttachment;
import com.spire.pdf.graphics.*;
import java.awt.*;
import java.awt.geom.Dimension2D;
import java.awt.geom.Rectangle2D;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
public class AttachFiles {
public static void main(String[] args) throws IOException {
//實例化PdfDocument類的對象
PdfDocument doc = new PdfDocument();
//加載需要添加附件的PDF文檔
doc.loadFromFile("test.pdf");
//加載附件文檔(Excel)並作為附件添加到PDF
PdfAttachment attachment = new PdfAttachment("Sample.xlsx");
doc.getAttachments().add(attachment);
//在PDF頁面指定位置繪制標簽
String label = "TestReport.docx";
PdfTrueTypeFont font = new PdfTrueTypeFont(new Font("Arial", Font.BOLD, 14));
double x = 40;
double y = doc.getPages().get(0).getActualSize().getHeight() -800;
doc.getPages().get(0).getCanvas().drawString(label, font, PdfBrushes.getOrange(), x, y);
//以註釋的形式添加附件到PDF
String filePath = "測試文檔.docx";
byte[] data = toByteArray(filePath);
Dimension2D size = font.measureString(label);
Rectangle2D bound = new Rectangle2D.Float((float) (x + size.getWidth() + 3), (float) y, 10, 15);
PdfAttachmentAnnotation annotation = new PdfAttachmentAnnotation(bound, filePath, data);
annotation.setColor(new PdfRGBColor(new Color(0, 128, 128)));
annotation.setFlags(PdfAnnotationFlags.Default);
annotation.setIcon(PdfAttachmentIcon.Graph);
annotation.setText("點擊打開測試報告文檔.docx");
doc.getPages().get(0).getAnnotationsWidget().add(annotation);
//保存文檔
doc.saveToFile("Attachments.pdf");
}
//讀取文件到byte數組
public static byte[] toByteArray(String filePath) throws IOException {
File file = new File(filePath);
long fileSize = file.length();
if (fileSize > Integer.MAX_VALUE) {
System.out.println("file too big...");
return null;
}
FileInputStream fi = new FileInputStream(file);
byte[] buffer = new byte[(int) fileSize];
int offset = 0;
int numRead = 0;
while (offset < buffer.length
&& (numRead = fi.read(buffer, offset, buffer.length - offset)) >= 0) {
offset += numRead;
}
if (offset != buffer.length) {
throw new IOException("Could not completely read file "
+ file.getName());
}
fi.close();
return buffer;
}
}
附件添加效果:
以上是本次關於Java操作PDF文檔代碼示例。
關於Java 加密、解密PDF文檔,請參閱這篇文章;
關於Java 合並、拆分PDF文檔,請參閱這篇文章。
Java 處理PDF文檔(一):頁眉頁腳、水印、背景、附件