views:

184

answers:

2

I have the following scenario, I want to create a DataGrid and then populate the contents at runtime.

The issue I am having is that because I do not know what the fields are until I am creating the grid I do not know how to set the item source correctly. As you can see in the following code I am adding the Field names as columns, I am then looping through my items and at this point I want to create an anonymous type for each item where I am setting a property (called its field name) to the field names value

foreach (string fieldName in listViewFieldCollection)
{
    DataGridTextColumn newColumn = new DataGridTextColumn
                                       {
                                           Header = fieldName,
                                           Binding = new Binding(fieldName)
                                       };

    dataGrid.Columns.Add(newColumn);
}

List<object> list = new List<object>();

foreach (ListItem listItem in listItems)
{
    foreach (string fieldName in listViewFieldCollection)
    {
        list.Add(new
                     {
                         // I want to be able to dynamically build Anonymous type properties here
                         fieldName = listItem[fieldName]
                     });
    }
}

dataGrid.ItemsSource = list;

for example. If I have the Fields called 'Title' and 'Link' then I want the list.Add(new to behave as

    list.Add(new
                 {
                     Title = listItem["Title"],
                     Link = listItem["Link"]
                 });

but if the fields are 'Manager', 'Title' and 'Salary' it should perform like

    list.Add(new
                 {
                     Manager = listItem["Manager"],
                     Title = listItem["Title"],
                     Salary = listItem["Salary"],
                 });
+1  A: 

It is impossible without reflection or codegeneration.

new
                 {
                     Manager = listItem["Manager"],
                     Title = listItem["Title"],
                     Salary = listItem["Salary"],
                 }

is converted to class with three fields and then few lines to set these fields. This is codegenerated by compiler. So in runtime you can't do that.

Andrey
A: 

It sounds like using reflection could work. The code below is something that may get you started. The snippet will loop through all Properties on the object.

        foreach (var currentPropertyInformation in source.GetType().GetProperties())
        {
            if ((currentPropertyInformation.GetGetMethod() == null) || (currentPropertyInformation.GetSetMethod() == null)) 
                continue;

            if (string.Compare(currentPropertyInformation.Name, "Item") != 0) // handle non-enumerable properties
            {
                // place this snippet in method and yield info?
            }
            else // handle enumerable properties
            {
            }
        }
greglev
Fantastic, I will give this option a go as soon as I can and report back. Thanks @greglev
Phill Duffy