madlan madlan - 6 months ago 39
Vb.net Question

Slow DataGridView Drawing\Rendering

I'm using a DataGridView to load data from a DataTable. This DataGridView is located on a tab (Forms.TabPage). When clicking this tab the datagrid takes a second or two to draw from the top down, regardless of wheather data is being loaded or not.

Is there anything I can do to speed up the Drawing\Rendering when clicking the Tab?

I Don't think the actual population of the DGV is causing this, as it's filled during form load so by the time the tabs click it would have loaded the few rows (20 - 30) it displays.

Using cn As New SqlConnection(connectionString)
Using cmd As SqlCommand = cn.CreateCommand()

cmd.CommandType = System.Data.CommandType.Text
cmd.CommandText = _
" SELECT [finish_time], [file_name], [transfer_status]" & _
" FROM dbo.[transfer_log]"

cmd.Notification = Nothing

cn.Open()


Dim columnSpec = New DataColumn()
With columnSpec
.DataType = GetType(System.String)
.ColumnName = "ClmFinishTime"
End With
Datatable1.Columns.Add(columnSpec)

Dim columnSpec2 = New DataColumn()
With columnSpec2
.DataType = GetType(System.String)
.ColumnName = "ClmFilename"
End With
Datatable1.Columns.Add(columnSpec2)

Dim columnSpec3 = New DataColumn()
With columnSpec3
.DataType = GetType(System.Byte())
.ColumnName = "ClmStatus"
End With
Datatable1.Columns.Add(columnSpec3)

Using dr As SqlDataReader = cmd.ExecuteReader()
While dr.Read()

Dim row As DataRow = Datatable1.NewRow
row("ClmFinishTime") = dr.Item("finish_time")
row("ClmFilename") = dr.Item("file_name")

Select Case dr.Item("transfer_status")
Case 0
row("ClmStatus") = ConvertToByte(My.Resources.accept)
Case 1
row("ClmStatus") = ConvertToByte(My.Resources.remove)
End Select

Datatable1.Rows.Add(row)

End While
End Using
End Using
DataGridView2.AutoGenerateColumns = False
DataGridView2.DataSource = Datatable1

Answer

I fixed this by double buffering the control:

Public Shared Sub SetDoubleBuffered(ByVal control As Control)
    GetType(Control).InvokeMember("DoubleBuffered", BindingFlags.SetProperty Or BindingFlags.Instance Or BindingFlags.NonPublic, Nothing, control, New Object() {True})
End Sub