I have a List<List<string>> where the outer list will be the rows for a grid and the inner list the column values.
How can I wrap the List<List<string>> so it’s a suitable DataSource for the grid, which accepts IList or IBindingList?
Effectively I want it to be seen as a List<MyObject> with the MyObject class having exposing the strings as public properties for binding.
I can’t change the list and it can have a very big number of rows so copying the data wouldn’t be ideal.
A simple example of the difference is the following code with a DataGridView dropped on a WinForm:
public class SupplierEntry
{
public string SupplierCode
{
get
{
return "SUPPLIERCODE";
}
}
public string SupplierTitle
{
get
{
return "SUPPLIERTITLE";
}
}
}
private void Test()
{
List<string> supplierEntryString = new List<string>();
supplierEntryString.Add("SUPPLIERCODE");
supplierEntryString.Add("SUPPLIERTITLE");
List<List<string>> supplierListStrings = new List<List<string>>();
supplierListStrings.Add(supplierEntryString);
List<SupplierEntry> supplierListObjects = new List<SupplierEntry>();
SupplierEntry supplierEntryObject = new SupplierEntry();
supplierListObjects.Add(supplierEntryObject);
//this can't handle the nested collections, instead showing a Capacity and Count column
dataGridView1.DataSource = supplierListStrings;
//this works giving you a supplier code and title column
//dataGridView1.DataSource = supplierListObjects;
}
When setting the DataSource of a DataGridView, the DataGridView will treat the supplied object as an
IList<something>, where for eachsomethingit will use reflection to find all the public readable properties. The public readable properties of aList<string>are Capacity and Count.In order to get your strings to appear in the DataGridView they must be presented as properties. You can do this at least three ways: Make your own class (as you have already done with
SupplierEntry), use aTuple, or use an anonymous type.A compromise that would allow you to use your source
List<List<string>>without copying any data would be to provide a wrapper class which just presents the data as properties: