DataGridView 单元格合并问题——无法释放动作
前情:
最近,从网上下载一段代码(类),功能是DataGridView 的单元格合并,调用成功,可以对任意相邻的一些单元格进行合并;
问题:
在一个窗体中,只有一个DataGridView ,数据是动态加载的,也就是能通过按扭切换,加载不同的数据 。
当表格显示一组数据,第一次调用这个合并单元格类后,在这一个表格中能按要求合并单元格,但是,当按下按扭,加载新的数据时(同一个DataGridView ,显示完全不同的数据),虽然没有在切换时加入合并单元格动作,但这些合并动作还在,也就是在新的显示表格中,依然还在进行合并。
查看源码,并没有释放资源取消动作的功能,也不知道怎么实现这功能,请高手指教;
合并类及调用代码如下(网上下载的):
‘=====================================
'·合并单元格类
'***********************************************************************
Public Class CmbDatagridbiew
Private data As New List(Of MyRect)
Private Dgv As DataGridView
Public Sub New(_dgv As DataGridView)
Me.Dgv = _dgv
AddHandler _dgv.CellPainting, AddressOf DGV_CellPainting
End Sub
Public Sub Close()
data.Clear()
End Sub
Public Sub Add(_rect As MyRect)
Me.data.Add(_rect)
Me.SetCellEnabled(_rect)
End Sub
Public Sub Add(_top As Integer, _left As Integer, _bottom As Integer, _right As Integer)
Me.data.Add(New MyRect(_top, _left, _bottom, _right))
Me.SetCellEnabled(New MyRect(_top, _left, _bottom, _right))
End Sub
Private Sub SetCellEnabled(_rect As MyRect)
For i = _rect.Top To _rect.Bottom
For j = _rect.Left To _rect.Right
Me.Dgv.Rows(i).Cells(j).ReadOnly = True
Next
Next
End Sub
Private Function InRects(rowIndex As Integer, colIndex As Integer) As Integer
For i = 0 To Me.data.Count - 1
If Me.data(i).InRect(rowIndex, colIndex) Then Return i
Next
Return -1
End Function
Private Sub DGV_CellPainting(sender As Object, e As DataGridViewCellPaintingEventArgs)
Using gridBrush As Brush = New SolidBrush(Me.Dgv.GridColor),
backColorBrush As SolidBrush = New SolidBrush(e.CellStyle.BackColor)
Using gridLinePen = New Pen(gridBrush)
If Me.data.Count = 0 Then Return
Dim index As Integer = Me.InRects(e.RowIndex, e.ColumnIndex)
If index = -1 Then Return
e.Graphics.FillRectangle(backColorBrush, e.CellBounds)
If e.RowIndex = Me.data(index).Bottom Then e.Graphics.DrawLine(gridLinePen,
e.CellBounds.Left, e.CellBounds.Bottom - 1,
e.CellBounds.Right - 1, e.CellBounds.Bottom - 1)
If e.ColumnIndex = Me.data(index).Right Then e.Graphics.DrawLine(gridLinePen,
e.CellBounds.Right - 1, e.CellBounds.Top,
e.CellBounds.Right - 1, e.CellBounds.Bottom - 1)
e.Handled = True
For i = 0 To Me.data.Count - 1
Dim rect1 As Rectangle = Me.Dgv.GetCellDisplayRectangle(Me.data(i).Left, Me.data(i).Top, False)
Dim rect2 As Rectangle = Me.Dgv.GetCellDisplayRectangle(Me.data(i).Right, Me.data(i).Bottom, False)
Dim rect As New Rectangle(rect1.Left, rect1.Top, rect2.Right - rect1.Left, rect2.Bottom - rect1.Top)
Dim text As String
Try
text =
Me.Dgv.Rows(Me.data(i).Top).Cells(Me.data(i).Left).Value.ToString().Trim()
Catch ex As Exception
text = ""
End Try
Dim sz As Drawing.SizeF = e.Graphics.MeasureString(text, e.CellStyle.Font)
e.Graphics.DrawString(text, e.CellStyle.Font, New SolidBrush(e.CellStyle.ForeColor),
rect.Left + (rect.Width - sz.Width) / 2,
rect.Top + (rect.Height - sz.Height) / 2,
StringFormat.GenericDefault)
Next
End Using
End Using
End Sub
End Class
Public Class MyRect
Public Top As Integer
Public Right As Integer
Public Bottom As Integer
Public Left As Integer
Public Sub New(_top As Integer, _left As Integer, _bottom As Integer, _right As Integer)
Me.Top = _top
Me.Right = _right
Me.Bottom = _bottom
Me.Left = _left
End Sub
Public Function InRect(rowIndex As Integer, colIndex As Integer) As Boolean
If rowIndex >= Me.Top And rowIndex <= Me.Bottom And colIndex >= Me.Left And colIndex <= Me.Right Then
Return True
Else
Return False
End If
End Function
End Class
'#End CmbDatagridbiew
’==========================================以下 调用代码
'·调用示例:
' 声明
' Private cmb As MergeCells
'
' 表格加载完成后
' cmb = New CmbDatagridbiew(Me.DataGridView1)
' cmb.Add(0, 0, 1, 2)
‘合并范围
’ 起点单元格中(0,0)即第一行第一列交叉位置的单元格,终点单元格(1,2)即第二行第三列交叉位置的单元格
’**************************************************************************************
**************************************************************************************
‘================================================以下实际操作演示
Public Class Form1
Private cmb As MergeCells
Private Sub Fm_data_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
‘ 窗体中只有一个固定的DataGridView,二个按扭(以显示不同的数据)
end sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
‘按扭一 加载数据到表格中
.......
’加入合并动作
cmb = New CmbDatagridbiew(Me.DataGridView1)
' cmb.Add(0, 0, 1, 2)
End Sub ’能正常加载并按要求合并单元格
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
‘按扭二,再加载全新的数据到表格中(同一个DataGridView)
.......
’没有加入合并动作
End Sub ’问题出现——上次的合并动作仍然在起作用,将同样的单元格进行了合并,但这不是我需要的
end class
请高手指教,如何解决这个问题?
最近,从网上下载一段代码(类),功能是DataGridView 的单元格合并,调用成功,可以对任意相邻的一些单元格进行合并;
问题:
在一个窗体中,只有一个DataGridView ,数据是动态加载的,也就是能通过按扭切换,加载不同的数据 。
当表格显示一组数据,第一次调用这个合并单元格类后,在这一个表格中能按要求合并单元格,但是,当按下按扭,加载新的数据时(同一个DataGridView ,显示完全不同的数据),虽然没有在切换时加入合并单元格动作,但这些合并动作还在,也就是在新的显示表格中,依然还在进行合并。
查看源码,并没有释放资源取消动作的功能,也不知道怎么实现这功能,请高手指教;
合并类及调用代码如下(网上下载的):
‘=====================================
'·合并单元格类
'***********************************************************************
Public Class CmbDatagridbiew
Private data As New List(Of MyRect)
Private Dgv As DataGridView
Public Sub New(_dgv As DataGridView)
Me.Dgv = _dgv
AddHandler _dgv.CellPainting, AddressOf DGV_CellPainting
End Sub
Public Sub Close()
data.Clear()
End Sub
Public Sub Add(_rect As MyRect)
Me.data.Add(_rect)
Me.SetCellEnabled(_rect)
End Sub
Public Sub Add(_top As Integer, _left As Integer, _bottom As Integer, _right As Integer)
Me.data.Add(New MyRect(_top, _left, _bottom, _right))
Me.SetCellEnabled(New MyRect(_top, _left, _bottom, _right))
End Sub
Private Sub SetCellEnabled(_rect As MyRect)
For i = _rect.Top To _rect.Bottom
For j = _rect.Left To _rect.Right
Me.Dgv.Rows(i).Cells(j).ReadOnly = True
Next
Next
End Sub
Private Function InRects(rowIndex As Integer, colIndex As Integer) As Integer
For i = 0 To Me.data.Count - 1
If Me.data(i).InRect(rowIndex, colIndex) Then Return i
Next
Return -1
End Function
Private Sub DGV_CellPainting(sender As Object, e As DataGridViewCellPaintingEventArgs)
Using gridBrush As Brush = New SolidBrush(Me.Dgv.GridColor),
backColorBrush As SolidBrush = New SolidBrush(e.CellStyle.BackColor)
Using gridLinePen = New Pen(gridBrush)
If Me.data.Count = 0 Then Return
Dim index As Integer = Me.InRects(e.RowIndex, e.ColumnIndex)
If index = -1 Then Return
e.Graphics.FillRectangle(backColorBrush, e.CellBounds)
If e.RowIndex = Me.data(index).Bottom Then e.Graphics.DrawLine(gridLinePen,
e.CellBounds.Left, e.CellBounds.Bottom - 1,
e.CellBounds.Right - 1, e.CellBounds.Bottom - 1)
If e.ColumnIndex = Me.data(index).Right Then e.Graphics.DrawLine(gridLinePen,
e.CellBounds.Right - 1, e.CellBounds.Top,
e.CellBounds.Right - 1, e.CellBounds.Bottom - 1)
e.Handled = True
For i = 0 To Me.data.Count - 1
Dim rect1 As Rectangle = Me.Dgv.GetCellDisplayRectangle(Me.data(i).Left, Me.data(i).Top, False)
Dim rect2 As Rectangle = Me.Dgv.GetCellDisplayRectangle(Me.data(i).Right, Me.data(i).Bottom, False)
Dim rect As New Rectangle(rect1.Left, rect1.Top, rect2.Right - rect1.Left, rect2.Bottom - rect1.Top)
Dim text As String
Try
text =
Me.Dgv.Rows(Me.data(i).Top).Cells(Me.data(i).Left).Value.ToString().Trim()
Catch ex As Exception
text = ""
End Try
Dim sz As Drawing.SizeF = e.Graphics.MeasureString(text, e.CellStyle.Font)
e.Graphics.DrawString(text, e.CellStyle.Font, New SolidBrush(e.CellStyle.ForeColor),
rect.Left + (rect.Width - sz.Width) / 2,
rect.Top + (rect.Height - sz.Height) / 2,
StringFormat.GenericDefault)
Next
End Using
End Using
End Sub
End Class
Public Class MyRect
Public Top As Integer
Public Right As Integer
Public Bottom As Integer
Public Left As Integer
Public Sub New(_top As Integer, _left As Integer, _bottom As Integer, _right As Integer)
Me.Top = _top
Me.Right = _right
Me.Bottom = _bottom
Me.Left = _left
End Sub
Public Function InRect(rowIndex As Integer, colIndex As Integer) As Boolean
If rowIndex >= Me.Top And rowIndex <= Me.Bottom And colIndex >= Me.Left And colIndex <= Me.Right Then
Return True
Else
Return False
End If
End Function
End Class
'#End CmbDatagridbiew
’==========================================以下 调用代码
'·调用示例:
' 声明
' Private cmb As MergeCells
'
' 表格加载完成后
' cmb = New CmbDatagridbiew(Me.DataGridView1)
' cmb.Add(0, 0, 1, 2)
‘合并范围
’ 起点单元格中(0,0)即第一行第一列交叉位置的单元格,终点单元格(1,2)即第二行第三列交叉位置的单元格
’**************************************************************************************
**************************************************************************************
‘================================================以下实际操作演示
Public Class Form1
Private cmb As MergeCells
Private Sub Fm_data_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
‘ 窗体中只有一个固定的DataGridView,二个按扭(以显示不同的数据)
end sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
‘按扭一 加载数据到表格中
.......
’加入合并动作
cmb = New CmbDatagridbiew(Me.DataGridView1)
' cmb.Add(0, 0, 1, 2)
End Sub ’能正常加载并按要求合并单元格
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
‘按扭二,再加载全新的数据到表格中(同一个DataGridView)
.......
’没有加入合并动作
End Sub ’问题出现——上次的合并动作仍然在起作用,将同样的单元格进行了合并,但这不是我需要的
end class
请高手指教,如何解决这个问题?
...全文
相关推荐
c# winform ===datagridview 单元格合并
c# winform ===datagridview 单元格合并 c# winform ===datagridview 单元格合并 c# winform ===datagridview 单元格合并
DataGridView合并单元格
纵向合并效果如下: 横向合并效果如下:以下是设计思路:因为代码比较简单,所以这里不多加解释.只说下遗憾,运行以下的代码时,发现在整个DATAGRID的列完全能显示的时候,绘制背景色没有问题,但,当有一部分行或列被挡住时,使用滚动条来移动,却发现有些DATAGRIDCELL的背景色被绘制窜行了,或者丢失了.而你左右多移动几下滚动条绘制又没有问题了,估计这是因为DATAGRIDVIEW
DataGridView列头与单元格合并高级技巧
本文还有配套的精品资源,点击获取 简介:在.NET框架的Windows Forms应用程序中, DataGridView 是一个强大的数据展示控件。本文将详细介绍如何在该控件中合并列头以及模拟单元格合并的效果。我们将探讨列头合并的基本方法和多级列头合并的自定义实现。同时,也会讨论单元格合并的技巧,如通过隐藏行或列以及创建自定义单元格类来实现。文章还涉及到了一个...
在Winfrom下的对DataGridView单元格合并
网络采集,精心整理,C# Winform 下的对DataGridView单元格合并,包含纵向及横向代码,有效果图。
DataGridView合并单元格(纵向合并及横向合并)
DataGridView合并单元格(纵向合并及横向合并) 京华志&精华志出品 分享资源 C# ASP.NET SQL DBA 源码


