将 ComboBox SelectedValue 绑定到 Nullable(Of Integer) 属性 会抛出 InvalidCastException
Binding a ComboBox SelectedValue to a Nullable(Of Integer) property throws InvalidCastException
我有一个 ViewModel class(实例化为 ilvm),上面有一个 Nullable(Of Integer)属性,称为 LinkedCompanyID,它手动绑定到 ComboBox 上的 SelectedValue。用户从列表中选择一个值会导致组合框抛出 InvalidCastException。我之前用其他 classes 做过这个,不同之处在于它们是通过 BindingSource 绑定的,而不是直接如下所示。我必须直接绑定的原因是 class 派生自 ComponentModel,它似乎使 BindingSource 不可见各个属性。
<Browsable(False), Bindable(True)>
<DesignerSerializationVisibilityAttribute(System.ComponentModel.DesignerSerializationVisibility.Hidden)>
Public Property LinkedCompanyID As Integer?
Get
If Not DesignMode AndAlso _currentEntity IsNot Nothing Then
Return _currentEntity.LinkedCompanyID
Else
Return Nothing
End If
End Get
Set(value As Integer?)
If Not DesignMode AndAlso _currentEntity IsNot Nothing Then
If Not EqualityComparer(Of Integer?).Default.Equals(_currentEntity.LinkedCompanyID, value) Then
_currentEntity.LinkedCompanyID = value
NotifyPropertyChanged("LinkedCompanyID")
End If
End If
End Set
End Property
绑定的形式为加载事件:
.
.
.
Dim linkedCompanyBinding As Binding = New Binding("SelectedValue", ilvm, "LinkedCompanyID", False, DataSourceUpdateMode.OnPropertyChanged)
AddHandler linkedCompanyBinding.Parse, AddressOf parseNullableInteger
Me.cmbLinkedCompany.DataBindings.Add(linkedCompanyBinding)
列表定义为:
IEnumerable(Of KeyValuePair(Of integer?, string))
DisplayMember 设置为 'Value',ValueMember 设置为 'Key'。
当用户从组合框列表中选择一个值时,将抛出 InvalidCastException,表明它无法从 Int32 转换为 Nullable(Of Integer)。
无奈之下我添加了parseNullableInteger方法:
Private Sub parseNullableInteger(sender As Object, e As ConvertEventArgs)
If e.Value IsNot Nothing AndAlso Not IsDBNull(e.Value) Then
e.Value = Convert.ChangeType(e.Value, e.DesiredType)
Else
e.Value = Nothing
End If
End Sub
这也不起作用,实际上当它尝试将 Integer 转换为 Nullable Integer 时会生成自己的 InvalidCastException。关于如何使这项工作有任何建议吗?
谢谢,尼尔
所以扩展我的评论。视图模型作为数据源绑定到 BindingSource,然后控件绑定到 BindingSource,ComboBox 正常工作。
例如
dim ilvmBindingSource as New BindingSource
ilvmBindingSource.DataSource = ilvm
cmbLinkedCompany.DataBindings.Add("SelectedValue", ilvmBIndingSource, "LinkedCompanyID", False, DataSourceUpdateMode.OnPropertyChanged)
这基本上完成了处理来自 ComboBox 的 'strange' 值的工作。
我有一个 ViewModel class(实例化为 ilvm),上面有一个 Nullable(Of Integer)属性,称为 LinkedCompanyID,它手动绑定到 ComboBox 上的 SelectedValue。用户从列表中选择一个值会导致组合框抛出 InvalidCastException。我之前用其他 classes 做过这个,不同之处在于它们是通过 BindingSource 绑定的,而不是直接如下所示。我必须直接绑定的原因是 class 派生自 ComponentModel,它似乎使 BindingSource 不可见各个属性。
<Browsable(False), Bindable(True)>
<DesignerSerializationVisibilityAttribute(System.ComponentModel.DesignerSerializationVisibility.Hidden)>
Public Property LinkedCompanyID As Integer?
Get
If Not DesignMode AndAlso _currentEntity IsNot Nothing Then
Return _currentEntity.LinkedCompanyID
Else
Return Nothing
End If
End Get
Set(value As Integer?)
If Not DesignMode AndAlso _currentEntity IsNot Nothing Then
If Not EqualityComparer(Of Integer?).Default.Equals(_currentEntity.LinkedCompanyID, value) Then
_currentEntity.LinkedCompanyID = value
NotifyPropertyChanged("LinkedCompanyID")
End If
End If
End Set
End Property
绑定的形式为加载事件:
.
.
.
Dim linkedCompanyBinding As Binding = New Binding("SelectedValue", ilvm, "LinkedCompanyID", False, DataSourceUpdateMode.OnPropertyChanged)
AddHandler linkedCompanyBinding.Parse, AddressOf parseNullableInteger
Me.cmbLinkedCompany.DataBindings.Add(linkedCompanyBinding)
列表定义为:
IEnumerable(Of KeyValuePair(Of integer?, string))
DisplayMember 设置为 'Value',ValueMember 设置为 'Key'。
当用户从组合框列表中选择一个值时,将抛出 InvalidCastException,表明它无法从 Int32 转换为 Nullable(Of Integer)。
无奈之下我添加了parseNullableInteger方法:
Private Sub parseNullableInteger(sender As Object, e As ConvertEventArgs)
If e.Value IsNot Nothing AndAlso Not IsDBNull(e.Value) Then
e.Value = Convert.ChangeType(e.Value, e.DesiredType)
Else
e.Value = Nothing
End If
End Sub
这也不起作用,实际上当它尝试将 Integer 转换为 Nullable Integer 时会生成自己的 InvalidCastException。关于如何使这项工作有任何建议吗?
谢谢,尼尔
所以扩展我的评论。视图模型作为数据源绑定到 BindingSource,然后控件绑定到 BindingSource,ComboBox 正常工作。
例如
dim ilvmBindingSource as New BindingSource
ilvmBindingSource.DataSource = ilvm
cmbLinkedCompany.DataBindings.Add("SelectedValue", ilvmBIndingSource, "LinkedCompanyID", False, DataSourceUpdateMode.OnPropertyChanged)
这基本上完成了处理来自 ComboBox 的 'strange' 值的工作。