While off reading random blog posts on the tubes, I stumbled upon a post that describes a 101-level scenario of using lookup data in the DataGrid and DataForm with RIA Services. The author was struggling to find a solution for the problem and was clearly frustrated.
The scenario is very common; let’s use the Cars example where every Model refers to its Make.
We want a DataGrid that includes the make name as a column:
And we want a DataForm with a ComboBox for the Make:
Let’s tackle this in two steps: first we’ll make the DataGrid show the Make Name and second we’ll make the DataForm show the ComboBox of Makes.
In the metadata class for the Model, annotate the properties as such:
This will lead to auto-generated fields in this order:
- Base Price
The only problem this leaves for DataGrid is that we don’t want to display the Make, but instead, we want to display the Make.Name. One solution for this would be to override the ToString() method on Make and have it return the Name. But let’s handle this in the UI; here’s our XAML:
Our DomainDataSource is loading our Models and the DataGrid is bound to the results. We are auto-generating the columns for the grid, but we’re also doing two extra things:
- Handling the AutoGeneratingColumn event
- Adding a read-only column to display the Make.Name
The code for the AutoGeneratingColumn event handler will prevent the auto-generation of the Make column, since we’re replacing it with a Make Name column:
In order to get the DataForm to display the ComboBox, we need to customize the Make column’s auto-generation for that control too. Here’s the XAML for the DataForm:
And our handler for AutoGeneratingField will create a ComboBox for the editing:
The ComboBox has two bindings: ItemsSource is bound to the “Makes” property on the DomainContext, and SelectedItem is two-way bound to the “Make” property on the model.
There’s only one thing left missing from this solution—we need to load all of the Makes into the DomainContext. We can do this easily from within the page’s constructor:
When adding a new model, we can see the Make field shows us the fully-populated list.
I would expect this pattern to be followed pretty regularly when dealing with lookup data. There might be some ways in your applications to condense this effort so that it can be reused across screens and types of lookup data.