在WPF中利用XPS文档实现打印功能
摘要#
WPF重新规划了打印模型,将所有编码围绕System.Windows.Controls.PrintDialog
,使用PrintDialog
类可显示Print对话框、设置打印机首选项等等,并且可将元素、文档以及低级的可视化元素直接发送给打印机。在WPF中实现打印的方式也有好几种,本文将使用XPS的方式简单实现一下打印功能。
代码实现#
1、准备FlowDocument
模板以及模板中要显示的数据,之前已经分享过一篇该文章,传送门==>在WPF中将XAML文档转换为PDF文件导出 有需要跳转过去看一下,这里不再重复阐述
2、将数据填充至FlowDocument
private FlowDocument FillFlowDocument()
{
var doc = (FlowDocument)Application.LoadComponent(new Uri("/WPF_XPSDocumentPrint_Demo;component/Resources/StudentTemplate.xaml", UriKind.RelativeOrAbsolute));
doc.DataContext = new Models.Student
{
Name = "傲慢与偏见",
Class = "三年一班",
Chinese = 99,
Math = 59,
English = 66,
Comments = "此乃难得一见的奇才,未来可期!!!(Tips:这文字是绑定的,不是静态数据)"
};
return doc;
}
3、使用Package
开辟一个容器将模板写入
private FixedDocumentSequence _StudentDocument;
/// <summary>
/// 模板文档(绑定至前端要显示的文档视图中)
/// </summary>
public FixedDocumentSequence StudentDocument
{
get { return _StudentDocument; }
set { _StudentDocument = value; RaisePropertyChanged(); }
}
private delegate void LoadXpsMethod();
private MemoryStream ms;
private Package package;
private Uri DocumentUri;
public MainWindowViewModel()
{
var doc = FillFlowDocument();
Application.Current.Dispatcher.BeginInvoke(
new LoadXpsMethod(() => FillDocumentViewer(doc)), DispatcherPriority.ApplicationIdle);
}
private void FillDocumentViewer(FlowDocument doc)
{
try
{
ms = new MemoryStream();
package = Package.Open(ms, FileMode.Create, FileAccess.ReadWrite);
DocumentUri = new Uri("pack://InMemoryDocument.xps");
PackageStore.AddPackage(DocumentUri, package);
XpsDocument xpsDocument = new XpsDocument(package, CompressionOption.Fast, DocumentUri.AbsoluteUri);
XpsDocumentWriter writer = XpsDocument.CreateXpsDocumentWriter(xpsDocument);
writer.Write(((IDocumentPaginatorSource)doc).DocumentPaginator);
StudentDocument = xpsDocument.GetFixedDocumentSequence();
xpsDocument.Close();
}
catch (Exception e)
{
MessageBox.Show("读取打印模板错误:{0}", e.ToString());
}
}
简单说下思路,就是先加载文档模板,并通过设置上下文给模板绑定数据,开辟一个内存流,使用Package
创建这个模板包,再写入到XPS文档中,最后通过XPS获取到一个FixedDocumentSequence
文档序列绑定到前台。
4、最后记得做一下必要的释放
public void Dispose()
{
PackageStore.RemovePackage(DocumentUri);
if (package != null)
{
package.Close();
package = null;
}
if (ms != null)
{
ms.Close();
ms = null;
}
DocumentUri = null;
}
效果#
源代码#
作者:傲慢与偏见
出处:https://www.cnblogs.com/chonglu/p/16916867.html
版权:本作品采用「署名-非商业性使用-相同方式共享 4.0 国际」许可协议进行许可。
声明:如果本文对您有帮助,请点击【推荐】您的赞赏将鼓励我继续创作!想跟我一起进步么?那就【关注】我吧
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· 阿里巴巴 QwQ-32B真的超越了 DeepSeek R-1吗?
· 【译】Visual Studio 中新的强大生产力特性
· 【设计模式】告别冗长if-else语句:使用策略模式优化代码结构
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义