Update
After a bit of investigating. What seems to be the issue is that the SelectedValue/SelectedItem is occurring before the Item source is finished loading. If I sit in a break point and wait a few seconds it works as expected. Don't know how I'm going to get around this one.
End Update
I have an application using in WPF using MVVM with a ComboBox. Below is the ViewModel Example. The issue I'm having is when we leave our page and migrate back the ComboBox is not selecting the current Value that is selected.
View Model
public class MyViewModel
{
private MyObject _selectedObject;
private Collection<Object2> _objects;
private IModel _model;
public MyViewModel(IModel model)
{
_model = model;
_objects = _model.GetObjects();
}
public Collection<MyObject> Objects
{
get
{
return _objects;
}
private set
{
_objects = value;
}
}
public MyObject SelectedObject
{
get
{
return _selectedObject;
}
set
{
_selectedObject = value;
}
}
}
For the sake of this example lets say MyObject has two properties (Text and Id). My XAML for the ComboBox looks like this.
XAML
<ComboBox Name="MyComboBox" Height="23" Width="auto"
SelectedItem="{Binding Path=SelectedObject,Mode=TwoWay}"
ItemsSource="{Binding Objects}"
DisplayMemberPath="Text"
SelectedValuePath="Id">
No matter which way I configure this when I come back to the page and the object is reassembled the ComboBox will not select the value. The object is returning the correct object via the get in the property though.
I'm not sure if this is just an issue with the way the ComboBox and MVVM pattern works. The text box binding we are doing works correctly.
It could be the way you are applying the DataContext to the Page. In WPF, everytime you navigate to a Page everything gets re-initialized, constructor gets called, loaded methods, everything. so if you are setting your DataContext inside your View you will no doubt be blowing away that SelectedItem that the user selected. In order to avoid that use the KeepAlive property of your pages.
This will result in only the Loaded event being fired when navigating back to a page you have already visited. So you will need to ensure that you are setting the DataContext on Initialize (either externally or within the constructor) rather than Load.
However, this will only work for that instance of the Page. If you navigate to a new instance of that page it constructor will be called again.
You need to put the ItemsSource property BEFORE the SelectedItem property. I came across a blog a few days ago mentioning the issue.
I had this problem with a ComboBox displaying a list of colors ( List<Brush> ).
Selecting a color was possible but it wasnt displayed when the selection closed (although the property was changed!)
The fix was overwriting the Equals(object obj) method for the type selected in the ComboBox (Brush), which wasnt simple because Brush is sealed. So i wrote a class EqualityBrush containing a Brush and implementing Equals:
Using a List of my new EqualityBrush class instead of normal Brush class fixed the problem!
My Combobox XAML looks like this:
Remember that my "Brush"-Property in the ViewModel now has to be of Type EqualityBrush!
I have noticed this behavior before as well. I have noticed that the SelectedIndex property doesn't cause the same bug. If you can restructure your ViewModel to expose the index of the selected item, and bind to that, you should be good to go.
The type of the
SelectedValuePath
and theSelectedValue
must be EXACTLY the same.If for example the type of
SelectedValuePath
isInt16
and the type of the property that binds toSelectedValue
isint
it will not work.I spend hours to find that, and that's why I am answering here after so much time the question was asked. Maybe another poor guy like me with the same problem can see it.