在VS 2008(.Net 3.5)中使用C#WinForms
我正在尝试将可能为空的列表绑定到数据网格.
如果列表包含元素,并且启用了AutoGenerateColumns,则数据将绑定到列表,并且一切正常.
但是,如果列表为空,或者列表变为空(通过删除最后一个元素),则什么也没有显示,只有灰色背景.
如果我手动创建列,例如:
if (m_DataGrid.AutoGenerateColumns == false)
{
foreach (var pair in objData.PropertyDataTable
.Where(pair => pair.Value.IsNative == true
&& pair.Value.IsList == false))
{
string propertyName = pair.Key;
PropertyData propertyData = pair.Value;
if (propertyData.Type == typeof(bool))
{
var column = new DataGridViewCheckBoxColumn()
{
Name = propertyName,
HeaderText = propertyName,
DataPropertyName = propertyName,
ValueType = propertyData.Type,
};
m_DataGrid.Columns.Add(column);
}
else
{
var column = new DataGridViewTextBoxColumn()
{
Name = propertyName,
HeaderText = propertyName,
DataPropertyName = propertyName,
ValueType = propertyData.Type,
};
m_DataGrid.Columns.Add(column);
}
}
}
出现列,并且我能够添加新行,但是实际上并没有绑定数据,并且没有像自动生成列时一样填充行的默认值.
当我离开视图并返回时,添加的行将保留,但数据不会保留.
将自动生成的列与调试器中的手动创建的列进行比较,两者之间唯一不同的属性是DataGridViewColumn基类上的IsDataBound属性.
启用AutoGenerateColumns时,列表中有一个或多个元素时,IsDataBound设置为true,但是即使正确设置了列的DataPropertyName属性,该列表的初始元素为零也为false.
是否有任何方法可以将空列表绑定到数据网格,并允许用户将行添加到空白列表,并且所有内容都已正确绑定?
我什至尝试在绑定之前将元素添加到空列表中,以使其自动生成并绑定列…但是一旦删除该行,列就会消失,并且绑定也将丢失.
其他实施细节:
我试图绑定一个数据源,该数据源是从以下项继承的自定义列表/集合类型:
- ICustomTypeDescriptor
- IBindingList
- ICancelAddNew
- IList<T>
- ICollection<T>
- IEnumerable<T>
- IList
- ICollection
- IEnumerable
列表中的对象是动态对象,它们继承自ICustomTypeDescriptor,并将属性映射到字典中的值.这些类型在ObjectDefinition类中定义,该类知道动态类型的可用属性信息(属性名称,类型,属性等).
每个列表都有一个分配的定义,因此列表中的每个对象都具有相同的定义.
我认为这并不重要,因为只要列表中至少有一个元素,所有内容都将正确绑定,并且可以正常工作.
解决方法:
对于列表,规则不是ICustomTypeDescriptor而是ITypedList.在列表级别实现此功能,然后可以在运行时提供合适的属性.因为这不依赖于任何行,所以即使对于零行它也应该起作用.