views:

168

answers:

1

Background:

I have a List<T> in my ViewModel defined as...

private List<FooBar> _fooBars;

public List<FooBar> FooBars
{
    get { return _fooBars; }
    set
    {
        if (value == _fooBars) return;
        _fooBars = value;
        OnPropertyChanged("FooBars");
    }
}

FooBar is defined as...

public class FooBar
{
    public string FooBarProperty { get; set; }
    // more properties here
}

Meanwhile, I have a GridView that binds to this list.

<ListView
    ItemsSource="{Binding FooBars}">
    <ListView.View>
        <GridView
            <GridViewColumn
                Header="Foo Bar Prop"
                DisplayMemberBinding={Binding FooBarProperty} />
            <!--more columns here-->
        </GridView>
    </ListView.View>
</ListView>

I run my app and all this works great. My FooBarProperties fill as expected.

The Problem:

In response to some user action. I edit one of the FooBar objects in FooBars, and call OnPropertyChanged() to let WPF know I want the bindings to update.

FooBars[2].FooBarProperty = "Some new text here";
OnProperChanged("FooBars"); // WPF is not listening to this :(

Only one problem: this completely doesn't work. The GridView never udpates.

A Workaround:

After much head scratching (and table banging and swearing), I came up with this replacement for the above:

FooBars[2].FooBarProperty = "Some new text here";
FooBars = FooBars.Select(fb => fb).ToList(); // this works but why is it necessary?

Works like a charm, but why do I need to do this?

NOTE: I tried switching from List<FooBar> to ObservableCollection<FooBar>, but that made absolutely no difference.

My Questions:

Very simply, why do I need this crazy code that basically copies the list into itself to get my bindings to update?

Is there a better way to force an update?

Thanks.

EDIT -- The Final Solution:

Thanks to @Botz3000's answer below, I switched FooBars back to ObservableCollection<FooBar>, and I modified FooBar so it implements INotifyChanged. Everything works as it's supposed to and no weird list copying required.

+3  A: 

If you are not changing the object that is stored in the ObservableCollection itself, but rather a property of it, then the CollectionChanged event won't be triggered.

Your FooBarProperty needs a PropertyChanged("FooBarProperty"), too. Since the list items bind to this property, they'll need notifications for that.

Botz3000
Indeed use the edit...
Zenuka
That's it! Thank you!
DanM