由于您想要的格式是非标准的,您必须帮助提供解析和显示它的逻辑。一种方法是在CellFormatting 和CellParsing 事件中编写一些代码。
另一种方法是指定一个IFormatProvider 对象。 通常这些只是进行格式化,您可能仍需要代码进行解析,但只需多几行代码,FormatProvider 也可以做到这一点:
Imports System.Globalization
Public Class DGVOddDateFormatter
Implements IFormatProvider, ICustomFormatter
Private myFmt As String = "dd/MM/yyyy HHmm"
Private mydgv As DataGridView
Private myNDX As Int32 = -1
Public Sub New(ctl As DataGridView, fmt As String, colNdx As Int32)
mydgv = ctl
myFmt = fmt
myNDX = colNdx
AddHandler mydgv.CellParsing, AddressOf dgv_CellParsing
mydgv.Columns(colNdx).DefaultCellStyle.Format = fmt
End Sub
Private Sub dgv_CellParsing(sender As Object, e As DataGridViewCellParsingEventArgs)
If e.ColumnIndex = myNDX Then
Dim dt As DateTime
If DateTime.TryParseExact(e.Value.ToString(),
myFmt, Nothing,
DateTimeStyles.None, dt) Then
e.Value = dt
e.ParsingApplied = True
End If
End If
End Sub
Public Function Format(format1 As String,
arg As Object,
formatProvider As IFormatProvider) As String _
Implements ICustomFormatter.Format
Dim dt As DateTime
If TypeOf (arg) Is DateTime Then
dt = CType(arg, DateTime)
Return dt.ToString(myFmt)
Else
Return "" ' or other default value
End If
End Function
Public Function GetFormat(formatType As Type) As Object Implements IFormatProvider.GetFormat
If TypeOf formatType Is ICustomFormatter Then
Return Me
End If
Return Nothing
End Function
End Class
创建格式化程序后,它会挂接到CellParsing 事件以提供补充逻辑,将内容转换回有效的DateTime。
用法
dgv1.DataSource = dtSample
dgv1.Columns(4).DefaultCellStyle.FormatProvider = New DGVOddDateFormatter(dgv1,
"dd/MM/yyyy HHmm", 4)
如果没有IFormatProvider,您将在CellParsing 和CellFormatting 事件中使用相同的代码,但您必须在其他可能也使用奇怪格式的网格上复制它。由于格式化程序传递了要使用的格式,因此它是可重用的。
在这种情况下,DGV 可以自己进行解析和格式化,因为它所需要的只是它拥有的格式字符串。但在其他情况下,例如转换纪元类型日期(自某个任意日期以来的秒数),它不会有任何线索。因此,他们为您提供了创建和使用自己的IFormatProvider 的方法。这些可以与Enum 转换、TimeSpan 格式化等其他内容一起使用。