۱۳۹۰/۰۴/۱۷

نمايش تعداد كل صفحات در iTextSharp


در مورد نحوه‌ي نمايش شماره صفحه جاري در مثلا header يك گزارش PDF تهيه شده به كمك writer.PageNumber و ارث بري از كلاس PdfPageEventHelper،‌ در پايان مطلب فارسي نويسي در iTextSharp توضيح داده شد. اين مورد جزو ضروريات يك گزارش خوب است، اما عموما نياز است تا تعداد كل صفحات هم نمايش داده شود. مثلا صفحه n از 100 جايي در تمام صفحات درج شود و ... هيچ خاصيتي به نام TotalNumberOfPages را در اين كتابخانه نمي‌توان يافت. علت هم اين است كه تعداد واقعي كل صفحات فقط در حين بسته شدن شيء Document مشخص مي‌شود و نه در هنگام تهيه صفحات. بنابراين نكته تهيه و نمايش تعداد صفحات، در iTextSharp به صورت خلاصه به شرح زير است:
الف) بايد در همان كلاسي كه از PdfPageEventHelper به ارث رسيده است، متد OnCloseDocument را تحريف (override) كرد. در اينجا به خاصيت writer.PageNumber دسترسي داريم و writer.PageNumber - 1 مساوي است با تعداد كل صفحات.
ب) در مرحله بعد نياز است تا اين عدد را به نحوي به تمام صفحات توليد شده اضافه كنيم. اين كار هم ساده است و مبتني است بر بكارگيري يك PdfTemplate :
  • در متد تحريف شده‌ي OnOpenDocument ، يك قالب PDF ساده را توليد مي‌كنيم (مثلا يك مستطيل كوچك خالي).
  • سپس در متد OnEndPage ، اين قالب را به انتهاي تمام صفحات در حال توليد اضافه خواهيم كرد.
  • زمانيكه متد OnCloseDocument فراخوانده شد، عدد تعداد كل صفحات را در اين قالب كه به تمام صفحات اضافه شده، درج خواهيم كرد. به اين ترتيب اين عدد به صورت خودكار در تمام صفحات نمايش داده خواهد شد.

پياده سازي اين توضيحات را در ادامه ملاحظه خواهيد كرد:
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;

namespace iTextSharpTests
{
public class PdfWriterPageEvents : PdfPageEventHelper
{
PdfContentByte _pdfContentByte;
// عدد نهايي تعداد كل صفحات را در اين قالب قرار خواهيم داد
PdfTemplate _template;
BaseFont _baseFont;

public override void OnOpenDocument(PdfWriter writer, Document document)
{
_baseFont = BaseFont.CreateFont(BaseFont.HELVETICA, BaseFont.CP1252, BaseFont.NOT_EMBEDDED);
_pdfContentByte = writer.DirectContent;
_template = _pdfContentByte.CreateTemplate(50, 50);
}

public override void OnEndPage(PdfWriter writer, Document document)
{
base.OnEndPage(writer, document);
String text = writer.PageNumber + "/";
float len = _baseFont.GetWidthPoint(text, 8);
Rectangle pageSize = document.PageSize;
_pdfContentByte.SetRGBColorFill(100, 100, 100);
_pdfContentByte.BeginText();
_pdfContentByte.SetFontAndSize(_baseFont, 8);
_pdfContentByte.SetTextMatrix(pageSize.GetLeft(40), pageSize.GetBottom(30));
_pdfContentByte.ShowText(text);
_pdfContentByte.EndText();
//در پايان هر صفحه يك جاي خالي را مخصوص تعداد كل صفحات رزرو خواهيم كرد
_pdfContentByte.AddTemplate(_template, pageSize.GetLeft(40) + len, pageSize.GetBottom(30));
}
public override void OnCloseDocument(PdfWriter writer, Document document)
{
base.OnCloseDocument(writer, document);
_template.BeginText();
_template.SetFontAndSize(_baseFont, 8);
_template.SetTextMatrix(0, 0);
//درج تعداد كل صفحات در تمام قالب‌هاي اضافه شده
_template.ShowText((writer.PageNumber - 1).ToString());
_template.EndText();
}
}

public class AddTotalNoPages
{
public static void CreateTestPdf()
{
using (var pdfDoc = new Document(PageSize.A4))
{
var pdfWriter = PdfWriter.GetInstance(pdfDoc, new FileStream("tpn.pdf", FileMode.Create));
pdfWriter.PageEvent = new PdfWriterPageEvents();
pdfDoc.Open();


pdfDoc.Add(new Phrase("Page1"));
pdfDoc.NewPage();
pdfDoc.Add(new Phrase("Page2"));
pdfDoc.NewPage();
pdfDoc.Add(new Phrase("Page3"));
}
}
}
}