使用 printDOcumnet C# 在多页上打印 DatagridView 数据

Printing DatagridView Data on Multiple page using printDOcumnet C#

所以,我正在尝试打印 datagridview 数据,但问题是在页面高度超过限制后,它不会移动到下一页来打印剩余数据。我尝试通过计算项目来添加条件,但没有成功。请告诉我我的代码有什么问题。如果我添加项目编号的条件。页面不断增加,但所有页面都有相同的数据。

private void printDocument1_PrintPage(object sender, 
System.Drawing.Printing.PrintPageEventArgs e)
    {

        Image image = Resources.grocery;
        float pageWidth = e.PageSettings.PrintableArea.Width;
        float pageHeight = e.PageSettings.PrintableArea.Height;

        Font font = new Font("Arial", 12, FontStyle.Regular);
        float fontHeight = font.GetHeight();
        int startX = 40;
        int startY = 30;
        int offsetY = 30;

            e.Graphics.DrawImage(image, 0, 0, 250, 250);
            e.Graphics.DrawString("Invoice ID   : GO-" + saaale, font, Brushes.Black, new Point(570, offsetY));
            offsetY += (int)fontHeight;

            e.Graphics.DrawString("Invoice Date :" + theDate, font, Brushes.Black, new Point(570, offsetY+40));
            offsetY += (int)fontHeight;
            e.Graphics.DrawString("Due Date     : " + a, font, Brushes.Black, new Point(570, offsetY+80));
            offsetY += (int)fontHeight;


            e.Graphics.DrawString("Client Name: " + this.comboBox1.GetItemText(this.comboBox1.SelectedItem), font, Brushes.Black, new Point(570, offsetY + 120));
            offsetY += (int)fontHeight;
            e.Graphics.DrawString("----------------------------------------------------------------------------------------------------------------------------------------------------------------------------", new Font("Arial", 12, FontStyle.Bold), Brushes.Black, new Point(0, 290));
            offsetY += (int)fontHeight;

           e.Graphics.DrawString("S.No", font, Brushes.Black, new Point(10, offsetY + 280));
           offsetY += (int)fontHeight;
            e.Graphics.DrawString("Product Name", font, Brushes.Black, new Point(130, offsetY + 280));
            offsetY += (int)fontHeight;
            e.Graphics.DrawString("Quantity", font, Brushes.Black, new Point(440, offsetY + 280));
            offsetY += (int)fontHeight;
            e.Graphics.DrawString("Sale Price", font, Brushes.Black, new Point(580, offsetY + 280));
            offsetY += (int)fontHeight;
            e.Graphics.DrawString("Amount", font, Brushes.Black, new Point(750, offsetY + 280));
            offsetY += (int)fontHeight;
            e.Graphics.DrawString("----------------------------------------------------------------------------------------------------------------------------------------------------------------------------", new Font("Arial", 12, FontStyle.Bold), Brushes.Black, new Point(0, 330));
            offsetY += (int)fontHeight;
            int j = 340; //370
            int count111 = 0;

            for (int i = 0; i < dataGridView1.RowCount - 1; i++)
            {
                if (offsetY >= pageHeight)
                {
                    e.HasMorePages = true;
                    offsetY = 0;
                    return;
                }
                else
                {
                    e.Graphics.DrawString(dataGridView1.Rows[i].Cells[0].Value.ToString(), font, Brushes.Black, new Point(10, offsetY + j));
                    offsetY += (int)fontHeight;
                    e.Graphics.DrawString(dataGridView1.Rows[i].Cells[1].Value.ToString(), font, Brushes.Black, new Point(140, offsetY + j));
                    offsetY += (int)fontHeight;
                    e.Graphics.DrawString(dataGridView1.Rows[i].Cells[2].Value.ToString(), font, Brushes.Black, new Point(450, offsetY + j));
                    offsetY += (int)fontHeight;
                    e.Graphics.DrawString(dataGridView1.Rows[i].Cells[3].Value.ToString(), font, Brushes.Black, new Point(590, offsetY + j));
                    offsetY += (int)fontHeight;
                    e.Graphics.DrawString(dataGridView1.Rows[i].Cells[4].Value.ToString(), font, Brushes.Black, new Point(760, offsetY + j));
                    j = j + 30;
                    //count111++;
                    e.HasMorePages = false;

                }


            }
            e.Graphics.DrawString("----------------------------------------------------------------------------------------------------------------------------------------------------------------------------", new Font("Arial", 12, FontStyle.Bold), Brushes.Black, new Point(0, offsetY + j - offsetY));
            offsetY += (int)fontHeight;
            e.Graphics.DrawString("Total Amount : Rs " + sum, new Font("Arial", 12, FontStyle.Bold), Brushes.Black, new Point(550, offsetY + j + offsetY));
            offsetY += (int)fontHeight;
            // e.Graphics.DrawString("Thank You For Your Buisness ", new Font("Arial", 12, FontStyle.Bold), Brushes.DarkBlue, new Point(280, j + 400));




        //multipage trial




        //end
        //Bitmap bm = new Bitmap(this.dataGridView1.Width, this.dataGridView1.Height);

        //dataGridView1.DrawToBitmap(bm, new Rectangle(0, 0, this.dataGridView1.Width, this.dataGridView1.Height));
        //e.Graphics.DrawImage(bm, 0, 350);
    }

不幸的是,我认为 DataGridView 不支持 PrintDocument。因此,您必须自己管理在网格中的循环。发布的代码似乎使事情变得比它必须的更复杂。主要问题是您正在检查网格行循环内的更多页面。这行不通。

目前 PrintPage 方法似乎在网格中循环,但是,正如您在问题中注意到的那样……它总是从每一页网格中行的开头开始。使用 for 循环 i 索引作为当前正在打印的网格行的索引将无法以这种方式工作。它当然解释了为什么它总是从头开始,但它也很可能永远不会结束并且是一个无限循环。

因此,很明显您将不得不保留一个 GLOBAL 索引变量,该变量保存要打印的当前行的行索引。这样,每次进入PrintPage方法时,都可以使用这个全局变量索引来跟踪当前要打印的行。

这表明需要满足两 (2) 个条件才能表明需要新页面……即……您有更多行要打印并且您已到达打印页面的底部。

下面的伪代码是帮助解决此问题的简单指南。

首先,创建一个全局变量来跟踪当前需要打印的行。有一个全局变量可以跟踪当前(垂直)打印行位置相对于页面高度的位置。

int CurrentDGVRowIndex = 0;
currentPrint_Vertical_Value = 30;

然后在PrintPage方法中,我们可以使用这些变量来检查是否已经到达网格中打印行的末尾,此外,我们可以使用它们来查看是否有更多行要打印,我们已到达页面底部。

private void printDocument1_PrintPage(object sender, System.Drawing.Printing.PrintPageEventArgs e) {
  float pageHeight = e.PageSettings.PrintableArea.Height;
  currentPrint_Vertical_Value = 30;
  PrintHeader(e);

 // keep printing until either there are no more rows to print OR we reach the end of the page
  while ((currentPrint_Vertical_Value < pageHeight) &&
         (CurrentDGVRowIndex < dataGridView1.Rows.Count - 1)) {
   // print a single row
    e.Graphics.DrawString(dataGridView1.Rows[CurrentDGVRowIndex].Cells[0].Value.ToString(), font, Brushes.Black, new Point(10, currentPrint_Vertical_Value));
    e.Graphics.DrawString(dataGridView1.Rows[CurrentDGVRowIndex].Cells[1].Value.ToString(), font, Brushes.Black, new Point(140, currentPrint_Vertical_Value));
    e.Graphics.DrawString(dataGridView1.Rows[CurrentDGVRowIndex].Cells[2].Value.ToString(), font, Brushes.Black, new Point(450, currentPrint_Vertical_Value));
    e.Graphics.DrawString(dataGridView1.Rows[CurrentDGVRowIndex].Cells[3].Value.ToString(), font, Brushes.Black, new Point(590, currentPrint_Vertical_Value));
    e.Graphics.DrawString(dataGridView1.Rows[CurrentDGVRowIndex].Cells[4].Value.ToString(), font, Brushes.Black, new Point(760, currentPrint_Vertical_Value));
    currentPrint_Vertical_Value = currentPrint_Vertical_Value + 30;
   // increment to the next grid row
    CurrentDGVRowIndex++;
  }

一旦我们退出这个 while 循环,我们就知道一个(或两个)条件已经满足。

1) 我们 运行 需要打印的行数

2) 我们已经到达页面底部。

鉴于此,我们只需检查是否需要打印更多页面。检查最后打印行的行索引。如果它等于网格中的总行数,那么我们就完成了。如果没有,那么我们知道我们已经到达可打印区域的末尾,需要再次调用 PrintPage 方法。

  if (CurrentDGVRowIndex == dataGridView1.RowCount - 1) {
    // no more rows in the grid to print – print summary and exit/
    PrintFooter(e);
    e.HasMorePages = false;
  }
  else {
    // there are more rows to print therefore we have more pages
    e.HasMorePages = true;
  }
}

希望对您有所帮助。