我有一个填充了枚举值的WinForms RadioGroup。我的问题是当控件获得焦点时,它会尝试使用System.DBNull
更新所选项,这不是枚举的有效值,我最终得到异常:
类型的对象' System.DBNull'无法转换为' MyNamespace.MyEnumType'
我有一个自定义的RadioGroup类,其中包含以下用于添加项目和获取/设置所选值的代码:
/// <summary>
/// sets the items, using reflection to get the display member and value
/// </summary>
public void SetItems<T>(IEnumerable<T> values, string valueMember, string displayMember)
{
Type t = typeof(T);
PropertyInfo displayProperty = t.GetProperty(displayMember);
PropertyInfo valueProperty = t.GetProperty(valueMember);
if (displayProperty == null)
throw new ArgumentException(string.Format("Property {0} is not found on class {1}", displayMember, t.FullName), "displayMember");
if (valueMember == null)
throw new ArgumentException(string.Format("Property {0} is not found on class {1}", valueMember, t.FullName), "valueMember");
Properties.Items.Clear();
foreach (var val in values)
{
object desc = displayProperty.GetValue(val, null);
Properties.Items.Add(new RadioGroupItem(valueProperty.GetValue(val, null), desc == null ? string.Empty : desc.ToString()));
}
}
/// <summary>
/// accessor for the selected value
/// </summary>
public object SelectedValue
{
get { return GetSelectedValue(); }
set { SetSelectedValue(value); }
}
private object GetSelectedValue()
{
if (SelectedIndex < 0 || SelectedIndex >= Properties.Items.Count)
{
if (DataBindings.Count > 0 && DataBindings["SelectedValue"] != null)
return DataBindings["SelectedValue"].DataSourceNullValue;
else
return null;
}
return Properties.Items[SelectedIndex].Value;
}
private void SetSelectedValue(object selectedItem)
{
SelectedIndex = FindSelectedValue(selectedItem);
}
private int FindSelectedValue(object value)
{
for (int i = 0; i < Properties.Items.Count; i++)
{
object val = Properties.Items[i].Value;
if ((val != null && val.Equals(value)) || (val == null && value == null))
{
return i;
}
}
return -1;
}
以下是从文件后面的代码初始化的方法:
myRadioGroup.SetItems<KeyValuePair<MyEnum, string>>(
new List<KeyValuePair<MyEnum, string>>()
{
new KeyValuePair<MyEnum, string>(MyEnum.VALUE_A, "Value A"),
new KeyValuePair<MyEnum, string>(MyEnum.VALUE_B, "Value B")
},
"Key", "Value");
// adds the binding
myRadioGroup.DataBindings.Add(new Binding("MyPropertyName", myDataSource, "SelectedValue", true, DataSourceUpdateMode.OnValidation, MyEnum.NONE));
当我打电话
时,我不清楚为什么我会收到此异常myRadioGroup.Focus();
GotFocus事件被命中,SetSelectedValue方法被调用并返回正常的null
值。我唯一能想到的是GetSelectedValue
显示DataSourceNullValue
作为System.DBNull,尽管在构造函数中将其设置为MyEnum.NONE
,但即使我在调试模式下更正它仍然给了我同样的例外。
同样根据MSDN page about this binding constructor
[null value parameter]在从数据源返回DBNull时将属性设置为指定的值。
这是我可以看到对DBNull的引用的唯一地方。
有没有办法修复此异常,或阻止RadioGroup在获得焦点时尝试更新数据源?
答案 0 :(得分:0)
我想我找到了一个解决方案... Binding
构造函数设置.NullValue
,而我需要设置.DataSourceNullValue
// adds the binding
Binding b = new Binding("MyPropertyName", myDataSource, "SelectedValue", true, DataSourceUpdateMode.OnValidation, MyEnum.NONE);
b.DataSourceNullValue = MyEnum.NONE;
myRadioGroup.DataBindings.Add(b);
DataSourceNullValue
指定数据源的哪个值被视为空值,指定应将哪个值写回数据源以获取空值。
默认值为System.DBNull
,因此它似乎尝试将空值写为System.DBNull
,这对于枚举无效。