我正在研究具有一些相当复杂要求的文档渲染器。我现在正在专门处理的部分是能够在给定文档的长度未知的最后一页,第一页和每个中间页上使用不同的页边距(第一页也可以包含也有不同的边距),这是由用户输入(一定程度上)驱动的。
我已经看到一些示例,这些示例通过使用document.SetMargins(...)和document.NewPage()来完成不同页面上的页边距(例如在this question中)。问题是我不知道最后一页何时出现,可能有足够的内容显示1页或20页。
我尝试使用页面事件来更改页面结束事件中的文档页边距,这似乎适用于页眉和页脚表(因为第一页,中间页和最后一页也可能具有不同的页眉/页脚),但没有最后一页的内容。
更新:我适应使用自定义渲染器(如下所示的覆盖刷新方法,以及生成测试pdf的主要流程)。对于这种情况,我不太了解最后一页的areabreak应该做什么。据我了解,它用于在渲染器之间切换(在多列和单列之间),然后在切换渲染器后添加更多内容。这种情况更类似于resultRenderer.Move(x,y)示例,但是通过各种方法查看,似乎没有调整画布大小的选项。
void Main()
{
PdfDocument pdf = new PdfDocument(new PdfWriter(Dest));
PageSize pageSize = PageSize.A4;
Document doc = new Document(pdf, pageSize, false);
HeaderHandler hh = new HeaderHandler(doc);
DocumentRenderer renderer = new CustomRenderer(doc, hh);
hh.First = new Margin(72f, 36f, 36f, 36f);
hh.Last = new Margin (72f, 72f, 36f, 36f);
hh.Middle = new Margin();
doc.SetRenderer(renderer);
pdf.AddEventHandler(PdfDocumentEvent.END_PAGE, hh);
var elementList = new List<IElement>();
for (var i = 0; i < 20; i ++)
{
// adds various types of elements, both block and leaf elements
AddItemToList(elementList, i);
}
foreach (var e in elementList)
{
var blockElement = e as IBlockElement;
var leafElement = e as ILeafElement;
if (blockElement != null)
{
doc.Add(blockElement);
}
else if (leafElement != null)
{
var para = new Paragraph();
para.Add(leafElement);
doc.Add(para);
}
}
// go to the last page -- this seems like something that would be put in only after changing the style of a given set of content (between multiple columns and a single column
doc.Add(new AreaBreak(AreaBreakType.LAST_PAGE));
// this causes all pages to use the HH Last Margin as thats the last margin to get set
renderer.Flush();
// without this it doesn't appear to use any of the margins defined in the renderer.
doc.Relayout();
doc.Close();
}
protected override void FlushSingleRenderer(IRenderer resultRenderer)
{
int pageNum = resultRenderer.GetOccupiedArea().GetPageNumber();
Margin margin = new Margin();
if (pageNum == 1)
{
margin.Top = HH.First.Top;
margin.Right = HH.First.Right;
margin.Bottom = HH.First.Bottom;
margin.Left = HH.First.Left;
// doc.SetMargins(72 + hh.GetHeaderHeight(), 36, 36 + hh.GetFooterHeight(), 36);
}
else if (pageNum == document.GetPdfDocument().GetNumberOfPages())
{
margin.Top = HH.Last.Top;
margin.Right = HH.Last.Right;
margin.Bottom = HH.Last.Bottom;
margin.Left = HH.Last.Left;
}
else
{
margin.Top = HH.Middle.Top;
margin.Right = HH.Middle.Right;
margin.Bottom = HH.Middle.Bottom;
margin.Left = HH.Middle.Left;
}
margin.Top += HH.GetHeaderHeight();
margin.Bottom += HH.GetFooterHeight();
base.document.SetMargins(margin.Top, margin.Right, margin.Bottom, margin.Left);
base.FlushSingleRenderer(resultRenderer);
}
其他可能相关的信息:
现在,我只是使用document.Add(x)方法将列表块级元素添加到文档中。
我改编了this best question以在同一页面结束事件中同时处理页脚和页眉。
非常感谢您的帮助。