ASP.NET ile PDF oluşturma

Bu yazımızda asp.net ile dinamik olarak PDF dosyası oluşturmayı adım adım inceleyeceğiz.

Amacımız, elimizde hazır olan bir html çıktısını PDF olarak sunmak.

Pekçok kaynakta pdf oluşturup içerisine sabit bilgiler yazmayı bulabilirsiniz. Ama hepimiz veritabanından / kullanıcıdan / webservisinden aldığımız bilgileri aspx sayfamızda sunarız, işte ben de bu noktada bu elimizde hazır bulunan HTML çıktısını PDF'e dönüştürmeden bahsetmek istiyorum.

Bunun için ihtiyacımız olan iTextSharp.dll dosyasını web sitemize refere etmek. Bu dll dosyasını http://dalt.in/i2DAj adresinden indirebilirsiniz.

1) öncelikle projemize refere ettiğimiz dll i ve daha sonra gerekecek namespace leri using ile tanımlayalım:

using System.Web.UI.HtmlControls;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
using iTextSharp.text.html.simpleparser;
using System.Text.RegularExpressions;

2) ASPX sayfamızın nasıl teşekkül edeceği çok önemli değil, örnek olsun diye şöyle olduğunu düşünelim:

<body>
<form id="form1" runat="server">
<div>
Deneme metni
<br />
<asp:Label ID="lbl" runat="server" Text="Bu bir label dir" />
<br /><br />
<asp:GridView ID="gv" runat="server" />
<table border="1">
<tr>
<td>
1.1
</td>
<td>
1.2
</td>
</tr>
<tr>
<td>
2.1
</td>
<td>
2.2
</td>
</tr>
</table>
<img src="/images/connected.jpg" />
deneme metni2
</div>
</form>
</body>

3) iTextSharp resimlerin yollarını relative ("/images/resim.jpg") olarak değil absolute olarak ("D:\Siteler\OrnekSite\Web\images\resim.jpg") işleyebildiği için resim yollarını otomatik olarak absolute olarak değiştiren bir metoda ihtiyacımız var:

public string RelativeToAbsoluteURLS(string text)
{
if (String.IsNullOrEmpty(text))
return text; string absoluteUrl = Request.PhysicalApplicationPath;
String value = Regex.Replace(text, "<(.*?)(src)=\"(?!http)(.*?)\"(.*?)>", "<$1$2=\"" + absoluteUrl + "$3\"$4>", RegexOptions.IgnoreCase | RegexOptions.Multiline);
return value.Replace(absoluteUrl + "/", absoluteUrl);
}

4) Sayfamızda gridview kullanacaksak, sonradan "'GridView' türündeki 'gv' denetimi runat=server değerine sahip bir form etiketine yerleştirilmelidir. " şeklinde bir hata almamak için şöyle boş bir metoda da ihtiyacımız var:

public override void VerifyRenderingInServerForm(Control control)
{ }

5) Şimdi gelelim PDF imizi oluşturmaya:

Önce gridviewimizi ve/veya diğer nesneleri verilerle dolduralım,

IEnumerable<int> data = Enumerable.Range(1, 4);
gv.DataSource = data;
gv.DataBind();
lbl.Text = DateTime.Now.ToString();

PDF oluşturmak için boş bir HtmlPage ve boş bir form gerekiyor. ardından aspx sayfamızdaki form1 in içeriğini PDF'e dönüştüreceğimizi belirtiyoruz ve tüm içeriği bir değişkene atıyoruz.

Page p = new Page();
HtmlForm f = new HtmlForm();
f.Controls.Add(form1);
p.Controls.Add(f);
StringWriter sw = new StringWriter();
HtmlTextWriter htw = new HtmlTextWriter(sw);
f.Controls[0].RenderControl(htw);
string content = sw.ToString();

A4 boyutundaki PDF imizi oluşturalım ve açalım:

Document doc = new Document(iTextSharp.text.PageSize.A4);
MemoryStream output = new MemoryStream();
PdfWriter.GetInstance(doc, output);
doc.Open();

İçerikte resim varsa yolunu mutlak olarak değiştirelim ve tüm içeriği PDF elementlerine dönüştürelim ve oluşturulan tüm itemları pdf dosyamıza ekleyelim:

content = RelativeToAbsoluteURLS(content);
List<IElement> dizi = HTMLWorker.ParseToList(new StringReader(content), null); foreach (var item in dizi)
doc.Add(item);

Kendi istediğimiz bilgileri de ekleyebiliriz:

boş bir satır:

Phrase phrase = new Phrase(Environment.NewLine);
doc.Add(phrase);

formatlı bir link:

Font font = new Font(Font.FontFamily.HELVETICA, 14f, 1, BaseColor.RED);
font.SetFamily("Arial");
Anchor anc = new Anchor("Devrim Altınkurt", font);
anc.Reference = "http://www.daltinkurt.com";
doc.Add(anc);
 

bir paragraf:

doc.Add(new iTextSharp.text.Paragraph("bu bir paragraf :)"));

 PDF imiz oluşturuldu, önce kapatalım;

doc.Close();

sonra da bu PDF'i tarayıcı penceremizde gösterelim veya kullanıcının download etmesini sağlayalım:

Response.Clear();
// tarayıcıda göstermek için: Response.AddHeader("content-disposition", "inline;"); // download ettirmek için:
//Response.AddHeader("content-disposition", "attachment;filename=dosyaadi.pdf;");
Response.ContentType = "application/pdf";
Response.BinaryWrite(output.ToArray());
Response.End();

Ve sonuç:

İşte bu kadar. Merak etmeyin dosyaların tamamını buradan bulabilirsiniz.

iTextSharp ile ilgili çeşitli kitaplar var, bunlardan bazılarını buradan e-book formatında indirebilirsiniz.

Ayrıca bu adreste de örnek kodlar var, incelemek isteyebilirsiniz.

Herkese kolay gelsin :)