15
votes

In my WPF application, I have a ComboBox that is filled with a static list of ComboBoxItems because its contents will never change. However, because I want to databind the SelectedItem to my underlying ViewModel, I want each ComboBoxItem to also have a separate value that is to be assigned to my ViewModel property. And I'm having a bit of trouble to get this working.

My ComboBox declaration looks like:

    <ComboBox Height="23" HorizontalAlignment="Stretch" Margin="2" Name="comboBox1" VerticalAlignment="Top"
              SelectedItem="{Binding Path=Amount, Mode=TwoWay}" SelectedValuePath="Tag" >
        <ComboBoxItem Content="None" Tag="0" />
        <ComboBoxItem Content="Few" Tag="1" />
        <ComboBoxItem Content="Some" Tag="2" />
        <ComboBoxItem Content="Enough" Tag="3" />
        <ComboBoxItem Content="Lots" Tag="4" />
        <ComboBoxItem Content="Too much" Tag="5" />
    </ComboBox>

The SelectedItem of this ComboBox is bound to the ViewModel's Amount property, which is declared as an integer:

public class MyViewModel : INotifyPropertyChanged
{
    private int _amount = 3;

    public int Amount
    {
        get { return _amount; }
        set
        {
            _amount = value;
            OnPropertyChanged("Amount");
        }
    }

    //...
}

I was hoping that SelectedValuePath="Tag" would tell WPF that it should use the Tag value to bind to the ViewModel's Amount property, but when I run this application and change the ComboBox's selected item, the debug trace tells me:

System.Windows.Data Error: 23 : Cannot convert 'System.Windows.Controls.ComboBoxItem: Some' from type 'ComboBoxItem' to type 'System.Int32' for 'en-US' culture ...
System.Windows.Data Error: 7 : ConvertBack cannot convert value 'System.Windows.Controls.ComboBoxItem: Some' (type 'ComboBoxItem'). (...) System.NotSupportedException: Int32Converter cannot convert from System.Windows.Controls.ComboBoxItem.

Apparently, it tries to bind the entire ComboBoxItem to my ViewModel, not just its Tag value. What am I doing wrong?

1

1 Answers

18
votes

If you use SelectedValuePath then you need to bind to the SelectedValue property which is

Gets or sets the value of the SelectedItem, obtained by using SelectedValuePath

So modify your binding to

SelectedValue="{Binding Path=Amount, Mode=TwoWay}" 

because as you experienced the SelectedItem will always contain the actually selected item (in your case the ComboBoxItem) not the value.