关于 WPF 的 DocumentPaginator 的严格理论问题:
使用 WPF DocumentPaginator 类打印多页文档时,分页器是否将其请求的所有 DocumentPages 保留在内存中,直到文档完成打印为止?或者它是否曾经在打印作业完成之前处理掉不再需要的任何 DocumentPages(即释放内存)?有没有办法在打印过程中手动告诉分页器释放旧的/不需要的 DocumentPages 而不会遇到异常?
非常感谢您对此的帮助!
关于 WPF 的 DocumentPaginator 的严格理论问题:
使用 WPF DocumentPaginator 类打印多页文档时,分页器是否将其请求的所有 DocumentPages 保留在内存中,直到文档完成打印为止?或者它是否曾经在打印作业完成之前处理掉不再需要的任何 DocumentPages(即释放内存)?有没有办法在打印过程中手动告诉分页器释放旧的/不需要的 DocumentPages 而不会遇到异常?
非常感谢您对此的帮助!
我遇到了和你一样的问题。
它不会处理较早加载的页面。我为解决这个问题所做的就是在 GetPage() 方法的末尾保存对加载页面的引用,并在 GetPage 方法的开头处理最后加载的页面。
这里是您附加问题的答案:
我的印象是 System.Windows.Controls.PrintDialog.Print(DocumentPaginator, title) 的实现是这样的:
Public void PrintDocument(DocumentPaginator paginator, string title)
{
Dictionary<int, DocumentPage> pages = new Dictionary<int DocumentPage>();
for(int i=0; i<paginator.PageCount(); i++)
{
pages.Add(i, paginator.GetPage(i));
UnknownPrinterEngine.SendPageToPrinter(pages(i)); //this is just imagination
}
}
如果实现确实是这样,则对每个已处理页面的本地引用将保持活动状态(在字典中),直到方法执行完成。--> 没有内存会被释放。
我做了什么来避免这种情况(扩展 DocumentPaginator 的类中的 GetPage 实现):
DocumentPage lastLoadedPage = null;
public DocumentPage GetPage(int pageNumber)
{
if(lastLoadedPage != null)
{
lastLoadedPage.Dispose()
}
//MyPrintControl should be your custom UserControl which represents the page to print
myPrintControl pageContent = new MyPrintControl();
pageContent.Width = PageSize.Width;
pageContent.Height = PageSize.Height;
pageContent.Measure(PageSize);
pageContent.Arrange(new Rect(new Point(0,0), PageSize));
DocumentPage actualPage = New DocumentPage(pageContent);
lastLoadedPage = actualPage;
return actualPage;
}
最后,您应该实现 IDisposable 接口并在 Dispose 方法中清理 lastLoadedPage 字段以释放最后一页的内存。
调查System.Windows.Xps.VisualsToXpsDocument
这解决了我在创建大型 xps 文档时内存不足的问题。也调查一下PrintQueue.CreateXpsDocumentWriter(somePrintQueue)
。抱歉,我没有足够的代表来发表评论。