I generate several QRCodes and would like to print the barcodes one after another on an A4 size page in Print Preview Control. I also use this control: PrintBar I calculated, that about 5 QRCodes can be on an A4 format page, so I tried to split with HasMorePages.
Print Preview without HasMorePages: the A4 page with the QRCodes screenshot - the last QRCode should be on the last page.
I added e.HasMorePages and return, but is not working correctly...It counts the pages to infinite and after that crashes.
My code:
BeginPrint
private void printDocument1_BeginPrint(object sender, System.Drawing.Printing.PrintEventArgs e)
{
this.currentItem = 0;
}
PrintPage
private void printDocument1_PrintPage(object sender, System.Drawing.Printing.PrintPageEventArgs e)
{
String fontName = "Arial";
Font fontNormal = new Font(fontName, 12, System.Drawing.FontStyle.Regular);
float itemHeight = fontNormal.GetHeight(e.Graphics);
Brush normalColour = Brushes.Black;
float leftMargin = e.MarginBounds.Left;
float topMargin = e.MarginBounds.Top;
float printWidth = e.MarginBounds.Width;
float printHeight = e.MarginBounds.Height;
float rightMargin = leftMargin printWidth;
float currentPosition = topMargin;
float numberWidth = 70;
float lineWidth = printWidth - numberWidth;
float lineLeft = leftMargin;
float numberLeft = leftMargin lineWidth;
int items = 0;
foreach (DataRow dr in dt.Rows)
{
if (!dr[4].Equals(""))
items = Convert.ToInt32(dr[4].ToString());
else
items = 0;
}
noOfItems = items;
foreach (DataRow dr in dt.Rows)
{
Bitmap bt = null;
if (!dr[1].Equals(""))
{
if (!dr[4].Equals(""))
{
int nrcodes = Convert.ToInt32(dr[4].ToString());//in the 4th row the value means how many QRCodes should be generated
for (int i = 0; i < nrcodes; i )
{
if (i % 5 != 0)
{
bt = GenerateQRCODE(dr[1].ToString());//dr[1] QRCode value
e.Graphics.DrawImage(bt, leftMargin, currentPosition, 200, 200);
e.Graphics.DrawString(dr[1].ToString(), fontNormal, normalColour, leftMargin 40, currentPosition 180); //dr[1] - text under QR Code
}
else
{
e.HasMorePages = true;
return;
}
currentPosition = 200;
}
}
}
}
// e.HasMorePages = true;
}
CodePudding user response:
Yes, I need to print the same QR Code as many times as in the
dr[4]
column value. After that the next QR Code the same way.
In this case you need to keep track of the current DataRow
and n
copy to not repeat the same code for the same row and copy when you set e.HasMorePages = true;
. For the copies, request a new page if the bottom of the current output block exceeds the e.MarginBounds.Bottom
. To request a new page for each row, uncomment the last lines of the following example.
//
using System.Drawing.Printing;
// ...
private int curRow = 0;
private int curCopy = 0;
// Or from where you call `.Print();`
// Button.Click event for example.
private void printDocument1_BeginPrint(object sender, PrintEventArgs e)
{
curRow = 0;
curCopy = 0;
}
private void printDocument1_PrintPage(object sender, PrintPageEventArgs e)
{
var curY = e.MarginBounds.Y;
using (var fontNormal = new Font("Arial", 12))
using (var sf = new StringFormat())
{
sf.Alignment = sf.LineAlignment = StringAlignment.Center;
int itemHeight = (int)fontNormal.GetHeight(e.Graphics) 10;
for (int row = curRow; row < dt.Rows.Count; row )
{
DataRow dr = dt.Rows[row];
if (!string.IsNullOrEmpty(dr.Field<string>(1)) &&
int.TryParse(dr.Field<string>(4)?.ToString(), out int copies))
{
for (int i = curCopy; i < copies; i )
{
var imgRect = new Rectangle(e.MarginBounds.X, curY, 200, 200);
var labelRect = new Rectangle(
imgRect.X,
imgRect.Bottom,
imgRect.Width,
itemHeight);
if (curY imgRect.Height labelRect.Height >= e.MarginBounds.Bottom)
{
curCopy = i;
e.HasMorePages = true;
return;
}
e.Graphics.DrawImage(bmp, imgRect);
e.Graphics.DrawString(dr[1].ToString(),
fontNormal, Brushes.Black,
labelRect, sf);
curY = labelRect.Bottom 30;
}
}
curRow = row 1;
curCopy = 0;
// Uncomment if you want to start a new
// page for each row.
//if (row < dt.Rows.Count - 1)
//{
// e.HasMorePages = true;
// break;
//}
}
}