[itextsharp][005]加入pdf到另一個pdf(AddPdfToAnotherPdf)

itextsharp, 加入pdf到另一個pdf(AddPdfToAnotherPdf)

此篇主要是要介紹如何將pdf加入到另外一個pdf:

首先當然要先新增原本的 parent pdf:

Document parentDoc = new Document(PageSize.A8);
PdfWriter parentWriter = PdfWriter.GetInstance(parentDoc, new FileStream("parent.pdf", FileMode.Create));
parentDoc.Open();
parentDoc.Add(new Paragraph("this is parent pdf..."));

接下來新增child pdf, 準備將child pdf加入到parent pdf中:

//create child pdf
Document childDoc = new Document(PageSize.A9);
string childFileName = "child.pdf";
PdfWriter childWriter = PdfWriter.GetInstance(childDoc, new FileStream(childFileName, FileMode.Create));
childDoc.Open();
childDoc.Add(new Paragraph("this is child pdf"));
childDoc.Close();

此步驟就是把child pdf加入到parent pdf中,先利用PdfReader物件讀取出child pdf, 然後透過PdfWriter.GetImportedPage()將PdfReader物件轉換成PdfImportedPage物件,最後再透過AffineTransform物件指定child pdf的縮放比例以及要插入到parent pdf的座標之後,就可以直接利用PdfWriter.DirectContent.AddTemplate()把child pdf加入到parent pdf裡面囉:

//create child pdf
Document childDoc = new Document(PageSize.A9);
string childFileName = "child.pdf";
PdfWriter childWriter = PdfWriter.GetInstance(childDoc, new FileStream(childFileName, FileMode.Create));
childDoc.Open();
childDoc.Add(new Paragraph("this is child pdf"));
childDoc.Close();
//add child to parent            
var reader = new PdfReader(childFileName);
//第一頁的index是1不是0喔
var imp = parentWriter.GetImportedPage(reader, 1);
PdfContentByte cb = parentWriter.DirectContent;            
AffineTransform af = new AffineTransform();
//指定座標以及縮放
af.Translate(33, 33);
//縮放50%
af.Scale(0.5f, 0.5f);
cb.AddTemplate(imp, af);            
parentDoc.Close();

產出的pdf結果:這樣就成功把child pdf 加入到parent pdf囉!

完整程式碼:

//create parentpdf
Document parentDoc = new Document(PageSize.A8);
PdfWriter parentWriter = PdfWriter.GetInstance(parentDoc, new FileStream("parent.pdf", FileMode.Create));
parentDoc.Open();
parentDoc.Add(new Paragraph("this is parent pdf..."));

//create child pdf
Document childDoc = new Document(PageSize.A9);
string childFileName = "child.pdf";
PdfWriter childWriter = PdfWriter.GetInstance(childDoc, new FileStream(childFileName, FileMode.Create));
childDoc.Open();
childDoc.Add(new Paragraph("this is child pdf"));
childDoc.Close();
//add child to parent            
var reader = new PdfReader(childFileName);
//第一頁的index是1不是0喔
var imp = parentWriter.GetImportedPage(reader, 1);
PdfContentByte cb = parentWriter.DirectContent;            
AffineTransform af = new AffineTransform();
//指定座標以及縮放
af.Translate(33, 33);
//縮放50%
af.Scale(0.5f, 0.5f);
cb.AddTemplate(imp, af);            
parentDoc.Close();

//一定要資源釋放,否則無法刪除
reader.Dispose();            

本文使用iTextSharp版本:5.5.8

iTextSharp 4.1.6測試結果:

沒有AffineTransform物件可供設定縮放以及插入的座標,需改用System.Drawing.Drawing2D.Matrix物件設定縮放,並且改成在PdfWriter.DirectContent.AddTemplate()設定要插入的座標。有一點要注意就是,此版本插入pdf的時候會去更動到parent.DirectContent設定值(PdfWriter.DirectContent.Transform()會動到設定),因此建議利用cb.RestoreState()還原原本的設定,以免影響後續的程式碼動作。除此之外PdfReader的資源釋放寫法需改為PdfReader.Close(),因為PdfReader.Dispose()在此版本不能使用:

//add child to parent            
var reader = new PdfReader(childFileName);
//第一頁的index是1不是0喔
var imp = parentWriter.GetImportedPage(reader, 1);
//version 4.1.6 改用縮放工具System.Drawing.Drawing2D.Matrix();
var tm = new System.Drawing.Drawing2D.Matrix();
//這樣表示縮放為50%的大小
tm.Scale(0.5f, 0.5f);            
//執行加入的動作
var cb = parentWriter.DirectContent;
cb.SaveState();//轉換大小之前先儲存原本狀態
cb.Transform(tm);
cb.AddTemplate(imp, 33, 33);
cb.RestoreState();//恢復原本狀態            
parentDoc.Close();

//一定要資源釋放,否則無法刪除
//reader.Dispose();在 version 4.1.6無法使用
//reader.Dispose();
reader.Close();            
tm.Dispose();

version 4.1.6產出的pdf結果:可以發現child.pdf的位置跟version 5.5.8產出的位置不太一樣,可以推測此兩個版本的座標單位長度略有不同,實際上使用時再依照需求作微調即可。

由於version 4.1.6跟version5.5.8差異不小,為了方便參考,version4.1.6的完整程式碼也附上:

//create parentpdf
Document parentDoc = new Document(PageSize.A8);
PdfWriter parentWriter = PdfWriter.GetInstance(parentDoc, new FileStream("parent_4_1_6.pdf", FileMode.Create));
parentDoc.Open();
parentDoc.Add(new Paragraph("this is parent pdf..."));

//create child pdf
Document childDoc = new Document(PageSize.A9);
string childFileName = "child.pdf";
PdfWriter childWriter = PdfWriter.GetInstance(childDoc, new FileStream(childFileName, FileMode.Create));
childDoc.Open();
childDoc.Add(new Paragraph("this is child pdf"));
childDoc.Close();
//add child to parent            
var reader = new PdfReader(childFileName);
//第一頁的index是1不是0喔
var imp = parentWriter.GetImportedPage(reader, 1);
//version 4.1.6 改用縮放工具System.Drawing.Drawing2D.Matrix();
var tm = new System.Drawing.Drawing2D.Matrix();
//這樣表示縮放為50%的大小
tm.Scale(0.5f, 0.5f);            
//執行加入的動作
var cb = parentWriter.DirectContent;
cb.SaveState();//轉換大小之前先儲存原本狀態
cb.Transform(tm);
cb.AddTemplate(imp, 33, 33);
cb.RestoreState();//恢復原本狀態            
parentDoc.Close();

//一定要資源釋放,否則無法刪除
//reader.Dispose();在 version 4.1.6無法使用
//reader.Dispose();
reader.Close();            
tm.Dispose();

if (File.Exists(childFileName) == true)
{
	File.Delete(childFileName);
}

這篇大概是這樣。。。