【问题标题】:Printing DataGridView in PrintDocument在 PrintDocument 中打印 DataGridView
【发布时间】:2014-04-30 02:47:34
【问题描述】:

我是 vb.net 的新手,我和我的团队正在开发一个系统,我们主要使用 DataGridView 从 SQL Server 数据库中查看我们的记录。

这是我的问题,我有两个 DataGridView,其中一个提取 ID 和学生姓名,而另一个提取记录(学生的成绩)基于所选的另一个 DataGridView 行。我已经可以打印记录,但是当我关闭 PrintDocument(不退出表格)并选择另一个学生并在 PrintDocument 中再次查看时,

它给了我一个错误提示

"Index was out of range. Must be non-negative and less than the size of the collection. Parameter name: index"

出现后续问题,当我有此代码"cell.RowIndex - 1" 时,DatagridView 中的第一条记录无法在 PrintDocument 中打印,当我擦除代码中的“-1”时,标题变为疯了,有时它们会变成空白(带边框),有时它们真的不显示,只显示记录。

这是发生错误的地方:

 e.Graphics.DrawString(DataGridView1.Rows(cell.RowIndex - 1) 
    .Cells(cell.ColumnIndex).FormattedValue.ToString, .Font, 
     Brushes.Black, rc, frmt)

这是我的代码:

Private Sub PrintDocument1_PrintPage(ByVal sender As System.Object, ByVal e As System.Drawing.Printing.PrintPageEventArgs) Handles PrintDocument1.PrintPage
    With DataGridView1
        Dim frmt As StringFormat = New StringFormat(StringFormatFlags.LineLimit)
        frmt.LineAlignment = StringAlignment.Center
        frmt.Trimming = StringTrimming.EllipsisCharacter

        Dim HeaderFont As Font = New Drawing.Font("Times New Roman", 20)
        Dim reportFont As Font = New Drawing.Font("Times New Roman", 14)
        Dim nrmlfnt As Font = New Drawing.Font("Calbiri", 10)
        Dim drawBrush As New SolidBrush(Color.Black)
        Dim blackpen As New Pen(Color.Black, 1)

        e.Graphics.DrawString("First Fruits Christian Academy", HeaderFont, drawBrush, 250, 50)
        e.Graphics.DrawString("Purok 17 Hindangon, Valencia City Bukidnon", reportFont, drawBrush, 245, 80)
        e.Graphics.DrawString("Student Grade", reportFont, drawBrush, 370, 125)
        e.Graphics.DrawString("Name: " & txtName.Text & "", nrmlfnt, drawBrush, 100, 180)
        e.Graphics.DrawString("Gender: " & txtGender.Text & "", nrmlfnt, drawBrush, 600, 180)
        e.Graphics.DrawString("Grade & Section: " & cboYearLevel.Text & " - " & cboSection.Text & "", nrmlfnt, drawBrush, 100, 200)

        Dim y As Single = e.MarginBounds.Top + 125
        Do While mRow < .RowCount
            Dim row As DataGridViewRow = .Rows(mRow)
            Dim x As Single = e.MarginBounds.Left
            Dim h As Single = 0
            For Each cell As DataGridViewCell In row.Cells
                Dim rc As RectangleF = New RectangleF(x, y, cell.Size.Width - 20, cell.Size.Height)
                e.Graphics.DrawRectangle(Pens.Black, rc.Left, rc.Top, rc.Width, rc.Height)
                    If (newpage) Then
                        e.Graphics.DrawString(DataGridView1.Columns(cell.ColumnIndex).HeaderText, .Font, Brushes.Black, rc, frmt)
                    Else
                    e.Graphics.DrawString(DataGridView1.Rows(cell.RowIndex - 1).Cells(cell.ColumnIndex).FormattedValue.ToString, .Font, Brushes.Black, rc, frmt)
                    End If
                x += rc.Width
                h = Math.Max(h, rc.Height)
            Next
            newpage = False
            y += h
            mRow += 1
            If y + h > e.MarginBounds.Bottom Then
                e.HasMorePages = True
                newpage = True
                Exit Sub
            End If
        Loop
        mRow = 0
    End With
End Sub

【问题讨论】:

    标签: vb.net


    【解决方案1】:

    我并证明您的代码有效,现在问题是服务器提供最后一行数据。 我进行了更改以使其正常工作:

    Dim NewPage As Boolean 
      NewPage = True 
    
      If (NewPage) = True Then 
        e.Graphics.DrawString (FDesempeño.DataGridView1.Columns (cell.ColumnIndex) .HeaderText, .font, Brushes.Black, rc, frmt) 
     
    else 
      e.Graphics.DrawString (FDesempeño.DataGridView1.Rows (cell.RowIndex - 1) .Cells (cell.ColumnIndex) .FormattedValue.ToString, .font, Brushes.Black, rc, frmt) 
    End If 
    

    我希望你能得到服务,顺便说一句,我和你一样是新手。如果你能纠正错误,如果我 agradesericia 你可以通过电子邮件与我们联系,我的电子邮件是 pablo_buy@hotmail.com

    【讨论】:

      【解决方案2】:

      您可能需要从这段代码中删除Else 部分,

      If (newpage) Then
          e.Graphics.DrawString(DataGridView1.Columns(cell.ColumnIndex).HeaderText, .Font, Brushes.Black, rc, frmt)
      Else
          e.Graphics.DrawString(DataGridView1.Rows(cell.RowIndex - 1).Cells(cell.ColumnIndex).FormattedValue.ToString, .Font, Brushes.Black, rc, frmt)
      End If
      

      然后改成,

      If (newpage) Then
          e.Graphics.DrawString(DataGridView1.Columns(cell.ColumnIndex).HeaderText, .Font, Brushes.Black, rc, frmt)
      End If
      ' and at this point you should re-calculate your rectangle again
      e.Graphics.DrawString(DataGridView1.Rows(cell.RowIndex - 1).Cells(cell.ColumnIndex).FormattedValue.ToString, .Font, Brushes.Black, rc, frmt)
      

      重点是,在每次迭代中,您都必须打印行,因此如果 newpage 标志为真,则意味着您只需要在打印行之前先打印页眉。

      【讨论】:

      • 不过OneFineDay的做法更合适。
      【解决方案3】:

      DataGridView 打印内容的最佳方法是将每一行的集合制成List(Of String),利用String.Format 将值连接在一起。使用类变量来确定您在列表中的位置,以便下一页继续。

      Private index As Integer
      Private Sub Print(...) Handles PrintDocument1.PrintPage
         Dim row As Integer = {some point you want to start at}
        'Paint a title - since this event fires for each page
        'continue loop or start loop
        For i As Integer = index To myList.Count - 1
         If Not row = e.MarginBounds.Bottom - 12 Then
          'remember where we are in the list
          index = i
          'paint your contents
         Else
          'start new page
          e.HasMorePages = True
          Exit Sub
         End If
        Next
        'reset the index for next print job
        If Not e.HasMorePages Then index = 0 
       End Sub
      
      Dim myList As New List (Of String)
      For Each row In dgv.Rows
        'add what data you want to print
      Next
      

      【讨论】:

      • 很抱歉,您能否告诉我您的代码中的“myList”是什么...谢谢
      • 就像我说的,收集你想要打印的内容,这是我的虚构版本。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-06-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-11-11
      相关资源
      最近更新 更多