C# PrintPage PrintPageEventHandler打印的副本太多
我必须为我们公司生产的产品打印装运标签 为了帮助自己了解这些标签的效果,我使用Windows窗体设计了它们。这使我能够定位文本,正确设置字体等。使用C# PrintPage PrintPageEventHandler打印的副本太多,c#,winforms,printing,C#,Winforms,Printing,我必须为我们公司生产的产品打印装运标签 为了帮助自己了解这些标签的效果,我使用Windows窗体设计了它们。这使我能够定位文本,正确设置字体等。使用标签控件,添加自定义条形码控件,并使用面板控件将项目分组到框中 每页有两(2)个标签 当我的代码打印标签文档时,我请求2、4或6份副本。偶尔也会使用打印预览。在这种情况下,我必须重置创建的标签数量 但是,当文档打印时: 如果请求2份,代码将打印2张纸(4个标签) 如果请求4份,代码将打印8张纸(16个标签) 如果请求6份,代码将打印多达18页(36
标签
控件,添加自定义条形码
控件,并使用面板
控件将项目分组到框中
每页有两(2)个标签
当我的代码打印标签文档时,我请求2、4或6份副本。偶尔也会使用打印预览。在这种情况下,我必须重置创建的标签数量
但是,当文档打印时:
- 如果请求2份,代码将打印2张纸(4个标签)
- 如果请求4份,代码将打印8张纸(16个标签)
- 如果请求6份,代码将打印多达18页(36个标签)
public int Print(string docName, int rows, int columns, int copies) {
short shortCopies = (short)copies;
LabelsHorizontal = rows;
LabelsVertical = columns;
Size docSize = PrintPreview.Document.DefaultPageSettings.Bounds.Size;
float height = 0.8F * Screen.PrimaryScreen.WorkingArea.Size.Height;
float width = (height * docSize.Width) / docSize.Height;
Size winSize = new Size((int)width, (int)height);
PrintPreview.Height = winSize.Height;
PrintPreview.Width = winSize.Width;
if (!String.IsNullOrEmpty(docName)) {
PrintPreview.Document.DocumentName = docName;
}
PrintPreview.Document.PrinterSettings.Copies = shortCopies;
PrintPreview.SettingsFilename = Settings.PageSettingsLocation;
if (!PrintPreview.PrinterSelected) {
if (PrintPreview.ShowPrinterSelectDialog() != DialogResult.OK) {
return 0;
}
}
labelQtyPrinted = 0;
if (ShowPrintPreview) {
PrintPreview.ShowDialog();
} else {
PrintPreview.PrintDocument();
}
return labelQtyPrinted;
}
// Resets the Label Count between PrintPreview and Print
private void PrintPreview_OnPrintClicked(object sender, EventArgs e) {
labelQtyPrinted = 0;
}
我必须编写一个自定义的PrintPreview类,它将PrintPreviewDialog
作为基类,这样我就可以用这个printButton\u Click方法覆盖它的打印按钮:
// Handles the Printing of the Document
internal void printButton_Click(object sender, EventArgs e) {
if (OnPrintClicked != null) {
OnPrintClicked(sender, e); // this resets my labelQtyPrinted value shown above
}
Document.Print();
printed = true;
Close();
}
在Print
方法(第一段代码)中,PrintPreview.PrintDocument()
只是调用printButton\u Click
事件的代码
我的PrintPageEventHandler如下所示:
private void Document_Printed(object sender, PrintPageEventArgs e) {
if (PrintPreview.Document.PrinterSettings.Copies <= labelQtyPrinted) {
throw new Exception("Run Away Printer");
}
float scale;
SizeF pageSize = new SizeF(
PrintPreview.Document.DefaultPageSettings.PaperSize.Width,
PrintPreview.Document.DefaultPageSettings.PaperSize.Height
);
Margins m = PrintPreview.Document.DefaultPageSettings.Margins;
float printableHeight = pageSize.Height - (m.Top + m.Bottom);
float printableWidth = pageSize.Width - (m.Left + m.Right);
if (printableWidth < printableHeight) {
if (labelSize.Width < labelSize.Height) {
float r1 = (printableWidth) / labelSize.Width;
float r2 = (printableHeight) / labelSize.Height;
scale = (r1 < r2) ? r1 : r2;
} else {
scale = (printableWidth) / labelSize.Width;
}
} else {
if (labelSize.Width < labelSize.Height) {
scale = (printableHeight) / labelSize.Height;
} else {
float r1 = (printableWidth) / labelSize.Width;
float r2 = (printableHeight) / labelSize.Height;
scale = (r1 < r2) ? r1 : r2;
}
}
float lh = scale * labelSize.Height;
float lw = scale * labelSize.Width;
float ml = scale * m.Left;
float mt = scale * m.Top;
Graphics G = e.Graphics;
G.SmoothingMode = smoothMode;
G.TextRenderingHint = TextRenderingHint.AntiAlias;
for (int i = 0; i < LabelsHorizontal; i++) {
float dx = i * (lw + ml); // Horizontal shift * scale
for (int j = 0; j < LabelsVertical; j++) {
float dy = j * (lh + mt); // Vertical shift * scale
#region ' Panels '
foreach (Panel item in panels) {
float h = scale * item.Size.Height;
float w = scale * item.Size.Width;
float x = (ml + dx) + scale * item.Location.X;
float y = (mt + dy) + scale * item.Location.Y;
using (SolidBrush b = new SolidBrush(item.BackColor)) {
G.FillRectangle(b, x, y, w, h);
}
using (Pen p = new Pen(Brushes.Black)) {
G.DrawRectangle(p, x, y, w, h);
}
}
#endregion
#region ' Logo '
if (logo != null) {
float h = scale * logo.Height;
float w = scale * logo.Width;
float x = (ml + dx) + scale * logoPt.X;
float y = (mt + dy) + scale * logoPt.Y;
G.DrawImage(logo, x, y, w, h);
}
#endregion
#region ' Labels '
foreach (Label item in labels) {
float h = scale * item.Size.Height;
float w = scale * item.Size.Width;
float x = (ml + dx) + scale * item.Location.X;
float y = (mt + dy) + scale * item.Location.Y;
Color c = PrintPreview.Document.DefaultPageSettings.Color ? item.ForeColor : Color.Black;
Font font = new Font(item.Font.FontFamily, scale * item.Font.Size, item.Font.Style);
using (SolidBrush b = new SolidBrush(c)) {
StringFormat format = GetStringFormatFromContentAllignment(item.TextAlign);
format.FormatFlags = StringFormatFlags.NoClip | StringFormatFlags.NoWrap;
format.Trimming = StringTrimming.None;
PointF locationF = new PointF(x, y);
SizeF size = new SizeF(w, h);
RectangleF r = new RectangleF(locationF, size);
G.DrawString(item.Text, font, b, r, format);
}
}
#endregion
#region ' Barcodes '
foreach (AcpBarcodeControl item in barcodes) {
Image img = item.GetBarcodeImage(item.BarcodeText);
if (img != null) {
float h = scale * item.Size.Height;
float w = scale * item.Size.Width;
float x = (ml + dx) + scale * item.Location.X;
float y = (mt + dy) + scale * item.Location.Y;
G.DrawImage(img, x, y, w, h);
}
}
#endregion
labelQtyPrinted++;
if (labelQtyPrinted == PrintPreview.Document.PrinterSettings.Copies) {
e.HasMorePages = false;
return;
}
}
e.HasMorePages = (labelQtyPrinted < PrintPreview.Document.PrinterSettings.Copies);
}
}
private void Document\u打印(对象发送者,PrintPageEventArgs e){
如果(PrintPreview.Document.PrinterSettings.Copies)我知道了
哎呀
好吧,如果有人在乎的话,这里有个交易:我需要每页打印两(2)个标签
我要做的是计算要打印多少页,使用垂直和水平打印的标签数量
我添加了变量labelsRequested
,并将现有变量labelQtyPrinted
更改为labelsPrinted
:
private int labelsPrinted;
private int labelsRequested;
我的publicPrint
方法更改为:
public int Print(string docName, int rows, int columns, int copies) {
LabelsHorizontal = rows;
LabelsVertical = columns;
if (!String.IsNullOrEmpty(docName)) {
PrintPreview.Document.DocumentName = docName;
}
labelsRequested = copies;
//PrintPreview.Document.PrinterSettings.Copies = (short)copies;
PrintPreview.SettingsFilename = Settings.PageSettingsLocation;
if (!PrintPreview.PrinterSelected) {
if (PrintPreview.ShowPrinterSelectDialog() != DialogResult.OK) {
return 0;
}
}
if (ShowPrintPreview) {
Size docSize = PrintPreview.Document.DefaultPageSettings.Bounds.Size;
float height = 0.8F * Screen.PrimaryScreen.WorkingArea.Size.Height;
float width = (height * docSize.Width) / docSize.Height;
Size winSize = new Size((int)width, (int)height);
PrintPreview.Height = winSize.Height;
PrintPreview.Width = winSize.Width;
PrintPreview.Document.PrinterSettings.Copies = (short)labelsRequested; // this may cause problems
PrintPreview.ShowDialog();
} else {
PrintPreview.PrintDocument();
}
return labelsPrinted;
}
现在,我不再像以前那样添加print\u Click
事件处理程序,而是将文档的BeginPrint
和EndPrint
连接起来,如下所示:
void Document_BeginPrint(object sender, PrintEventArgs e) {
labelsPrinted = 0;
float fPerPage = LabelsHorizontal * LabelsVertical;
if (1 < fPerPage) {
float fQty = labelsRequested;
float fTotal = fQty / fPerPage;
PrintPreview.Document.PrinterSettings.Copies = (short)fTotal;
}
}
void Document_EndPrint(object sender, PrintEventArgs e) {
Printed = (labelsPrinted == labelsRequested);
}
@约翰·桑德斯:为什么你要从我的标题中去掉C
?因为你应该使用标签而不是标题来更好地识别(分类)你的问题。See@Steve是对的。我通常不会向1000个或更多代表的用户讲解这一点,但标记是标记的位置,而不是标题。通过实现PrintDocument.BeginPrint事件的处理程序来重置页面计数器。使用调试器查看计数的情况。将退出条件放在for循环中看起来非常简单ishy。我猜打印方式可能会超过页面的结尾,打印机驱动程序会将其拆分为多个页面。@nobugs:当我在电脑上测试时(使用Adobe PDF的Windows 7),正确的打印页数。BeginPrint
有一个例程可以将计数设置为零,EndPrint
有一个例程可以设置AllPrinted=(labelQtyPrinted==PrintPreview.Document.PrinterSettings.Copies)
这怎么会没有更多的投票?当我找到这个时,我正在寻求帮助做同样的事情。谢谢!!!谢谢,@dev_JORD。我很高兴其他人从中得到了一些帮助!
private void Document_Printed(object sender, PrintPageEventArgs e) {
float scale;
SizeF pageSize = new SizeF(
PrintPreview.Document.DefaultPageSettings.PaperSize.Width,
PrintPreview.Document.DefaultPageSettings.PaperSize.Height
);
Margins m = PrintPreview.Document.DefaultPageSettings.Margins;
float printableHeight = pageSize.Height - (m.Top + m.Bottom);
float printableWidth = pageSize.Width - (m.Left + m.Right);
if (printableWidth < printableHeight) {
if (labelSize.Width < labelSize.Height) {
float r1 = printableWidth / labelSize.Width;
float r2 = printableHeight / labelSize.Height;
scale = (r1 < r2) ? r1 : r2;
} else {
scale = printableWidth / labelSize.Width;
}
} else {
if (labelSize.Width < labelSize.Height) {
scale = (printableHeight) / labelSize.Height;
} else {
float r1 = printableWidth / labelSize.Width;
float r2 = printableHeight / labelSize.Height;
scale = (r1 < r2) ? r1 : r2;
}
}
float lh = scale * labelSize.Height;
float lw = scale * labelSize.Width;
float ml = scale * m.Left;
float mt = scale * m.Top;
Graphics G = e.Graphics;
G.SmoothingMode = smoothMode;
G.TextRenderingHint = TextRenderingHint.AntiAlias;
for (int i = 0; (i < LabelsHorizontal) && !e.Cancel; i++) {
float dx = i * (lw + ml); // Horizontal shift * scale
for (int j = 0; (j < LabelsVertical) && !e.Cancel; j++) {
float dy = j * (lh + mt); // Vertical shift * scale
#region ' Panels '
foreach (Panel item in panels) {
float h = scale * item.Size.Height;
float w = scale * item.Size.Width;
float x = (ml + dx) + scale * item.Location.X;
float y = (mt + dy) + scale * item.Location.Y;
using (SolidBrush b = new SolidBrush(item.BackColor)) {
G.FillRectangle(b, x, y, w, h);
}
using (Pen p = new Pen(Brushes.Black)) {
G.DrawRectangle(p, x, y, w, h);
}
}
#endregion
#region ' Logo '
if (logo != null) {
float h = scale * logo.Height;
float w = scale * logo.Width;
float x = (ml + dx) + scale * logoPt.X;
float y = (mt + dy) + scale * logoPt.Y;
G.DrawImage(logo, x, y, w, h);
}
#endregion
#region ' Labels '
foreach (Label item in labels) {
float h = scale * item.Size.Height;
float w = scale * item.Size.Width;
float x = (ml + dx) + scale * item.Location.X;
float y = (mt + dy) + scale * item.Location.Y;
Color c = PrintPreview.Document.DefaultPageSettings.Color ? item.ForeColor : Color.Black;
Font font = new Font(item.Font.FontFamily, scale * item.Font.Size, item.Font.Style);
using (SolidBrush b = new SolidBrush(c)) {
StringFormat format = GetStringFormatFromContentAllignment(item.TextAlign);
format.FormatFlags = StringFormatFlags.NoClip | StringFormatFlags.NoWrap;
format.Trimming = StringTrimming.None;
PointF locationF = new PointF(x, y);
SizeF size = new SizeF(w, h);
RectangleF r = new RectangleF(locationF, size);
G.DrawString(item.Text, font, b, r, format);
}
}
#endregion
#region ' Barcodes '
foreach (AcpBarcodeControl item in barcodes) {
Image img = item.GetBarcodeImage(item.BarcodeText);
if (img != null) {
float h = scale * item.Size.Height;
float w = scale * item.Size.Width;
float x = (ml + dx) + scale * item.Location.X;
float y = (mt + dy) + scale * item.Location.Y;
G.DrawImage(img, x, y, w, h);
}
}
#endregion
labelsPrinted++;
}
}
}