如何以编程方式从PrintDocument打印特定页面
本文关键字:打印 PrintDocument 编程 方式 | 更新日期: 2023-09-27 18:11:25
是否有一种方法可以仅从System.Drawing.Printing.PrintDocument
以编程方式打印选定的页面(例如:3 - 5页)?
我正在使用这个代码:
myPrintDocument.Print();
但是这样我就不能以编程方式跳过页面了。我考虑过显示PrintDialog类的修改版本的可能性,跳过我不想要的页面,打印文档并以编程方式关闭PrintDialog窗口(以便它只闪烁)。但是那样会有点麻烦。
可以在PrintDocument.BeginPrint
事件中设置PrinterSettings
放置打印代码的PrintDocument.PrintPage
事件将由Print Controller for Every Page引发,直到PrinterSettings
中设置的最后一页。例如,如果您有一个10页的PrintDocument
,并且您设置了PrintDocument.PrinterSettings.ToPage = 5
,那么打印控制器将为每个页面引发PrintPage
事件,直到它处理第5页。
如果您跳过页面,例如从PrinterSettings.FromPage = 3
跳到ToPage = 5
,那么打印控制器将引发PrintPage
事件3次。从3到5,每次计数一个PrintPage
事件。
打印控制器不决定PrintPage
事件打印什么内容。对于范围内的每个计算页面,它只引发一次事件。例如,如果您将FromPage = 4
指定为FromPage = 6
,打印控制器将引发完全相同数量的PrintPage
事件,而且它甚至不知道其中的区别!它不知道用PrintPage
事件打印的是哪个页面。它只知道触发PrintPage
事件3次。
我的观点是,你的代码在PrintPage
事件必须处理所有你跳过的页面没有绘制任何东西。然后,在同一个PrintPage
事件中的代码必须处理并绘制"当前页面"。然后返回,以便打印控制器可以引发下一个PrintPage
事件。
void Setup_Printing()
{
myPrintDocument.BeginPrint += On_BeginPrint;
myPrintDocument.PrintPage += On_PrintPage;
}
// Page Index variable
int indexCuurentPage = 0;
void On_BeginPrint(object sender, PrintEventArgs e)
{
indexCuurentPage = 0;
((PrintDocument)sender).PrinterSettings.PrintRange = PrintRange.SomePages;
((PrintDocument)sender).PrinterSettings.FromPage = 3;
((PrintDocument)sender).PrinterSettings.ToPage = 5;
}
void On_PrintPage(object sender, PrintPageEventArgs ppea)
{
// Set up a loop to process pages.
bool bProcessingPages = true;
while (bProcessingPages)
{
indexCurrentPage++;
// Set isPageInRange flag to true if this indexCurrentPage is in the selected range of pages
bool isPageInRange = (theCurrentPage >= ppea.PageSettings.PrinterSettings.FromPage);
isPageInRange = isPageInRange && (theCurrentPage =< ppea.PageSettings.PrinterSettings.ToPage);
if (isPageInRange)
{
// Process your data and print this page then exit the loop.
try
{
//// TO DO - Process Data ////
//// TO DO - Draw Data to ppea.Graphics ////
// Note: Do not set the ppea.HasMorePages to true. Let the Printer Controller do it.
}
catch
{
// Abort printing more pages if there was an error.
ppea.HasMorePages = false;
}
// Set the loop exit flag. We could use "return;" instead if we do not want to do more.
bProcessingPages = false;
}
else
{
// Process your data and Do Not Draw on the ppea.Graphics.
try
{
//// TO DO - Process Data ////
}
catch
{
// Abort printing more pages if there was an error.
ppea.HasMorePages = false;
// Set the loop exit flag. We could use "return;" instead if we do not want to do more.
bProcessingPages = false;
}
// Stay in the processing loop until you either need to actually Print a Page
// or until you run out of data and pages to print.
}
// check to see if we ran out of pages to print
if (indexCurrentPage >= ppea.PageSettings.PrinterSettings.ToPage)
{
// Done. We do not need to set the HasMorePages = false
bProcessingPages = false;
}
} // end while processing pages
// The print controller will decide to raise the next PrintPage event if it needs to.
// If You set the ppea.HasMorePages = false, then it will stop any more page events.
// If You set the ppea.HasMorePages = true,
// then I'm not sure what the print controller will do if it ran out of pages!
}
这样怎么样?
PrinterSettings printSettings = new PrinterSettings()
{
FromPage = 3,
ToPage = 5
};
PrintDocument myPrintDocument = new PrintDocument()
{
PrinterSettings = printSettings
};
myPrintDocument.Print();