Search code examples
wpfdata-bindingcomboboxtextblockvalueconverter

My databinding with value converter does not work


I've got a simple Item-class, that looks like this:

public class Item : DependencyObject
{
    public int No
    {
        get { return (int)GetValue(NoProperty); }
        set { SetValue(NoProperty, value); }
    }

    public string Name
    {
        get { return (string)GetValue(NameProperty); }
        set { SetValue(NameProperty, value); }
    }

    public static readonly DependencyProperty NoProperty = DependencyProperty.Register("No", typeof(int), typeof(Item));
    public static readonly DependencyProperty NameProperty = DependencyProperty.Register("Name", typeof(string), typeof(Item));
}

And a ValueConverter, that looks like this:

[ValueConversion(typeof(Item), typeof(string))]
internal class ItemToStringConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if (value == null)
        {
            return null;
        }

        var item = ((Item)value);

        var sb = new StringBuilder();
        sb.AppendFormat("Item # {0}", item.No);

        if (string.IsNullOrEmpty(item.Name) == false)
        {
            sb.AppendFormat(" - [{0}]", item.Name);
        }

        return sb.ToString();
    }


    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

On my WPF Window, I declare a DependencyProperty (called Items) that holds a list of Item objects (List< Item >) and creates a ComboBox that binds to this DependencyProperty using this XAML-code:

<ComboBox ItemsSource="{Binding ElementName=mainWindow, Path=Items}">
    <ComboBox.ItemTemplate>
        <DataTemplate>
            <TextBlock Text="{Binding Converter={StaticResource itemToStringConverter}}"/>
        </DataTemplate>
    </ComboBox.ItemTemplate>
</ComboBox>

If I execute the code below once, the databinding works fine, howevery the value convertion fails if I execute it again:

var item1 = new Item {Name = "Item A", No = 1};
var item2 = new Item {Name = "Item B", No = 2};
var item3 = new Item {Name = "Item C", No = 3};
Items = new List<Item> {item1, item2, item3};

The problem is, that the ItemToStringConverter.Convert method is now passed a string-object as the first parameter instead of an Item-object?

What am I doing wrong?

Regards, Kenneth


Solution

  • Simple workaround would be to check the type passed to your ValueConverter. Change Convert method as follows:

    public object Convert(object value, Type targetType, object parameter, CultureInfo culture) {
            var item = value as Item;
            if(item == null) { return null; }
            var sb = new StringBuilder();
            sb.AppendFormat("Item # {0}", item.No);
            if(string.IsNullOrEmpty(item.Name) == false) {
                sb.AppendFormat(" - [{0}]", item.Name);
            }
            return sb.ToString();
        }