3

I'm trying to implement a bindable collection - a specialized stack - which needs to be displayed on one page of my Windows 8 app along with any updates made to it as they happen. For this, I've implemented INotifyCollectionChanged and IEnumerable<>:

public class Stack : INotifyCollectionChanged, IEnumerable<Number>
{

...

public void Push(Number push)
{
    lock (this)
    {
        this.impl.Add(push);
    }

    if (this.CollectionChanged != null)
        this.CollectionChanged(this, new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Add, push));
}

...and the equivalents for other methods...

#region INotifyCollectionChanged implementation

public event NotifyCollectionChangedEventHandler CollectionChanged;

#endregion

public IEnumerator<Number> GetEnumerator()
{
    List<Number> copy;

    lock (this)
    {
        copy = new List<Number>(impl);
    }
    copy.Reverse();

    foreach (Number num in copy)
    {
        yield return num;
    }
}

System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
{
    return this.GetEnumerator();
}

This collection class is used to define a property of an underlying class instance owned by the page, which is set as its DataContext (the Calculator property of the Page), and is then bound to a GridView:

<GridView x:Name="StackGrid" ItemsSource="{Binding Stack, Mode=OneWay}" ItemContainerStyle="{StaticResource StackTileStyle}" SelectionMode="None">

... ItemTemplate omitted for length ...

The binding works initially when the page is navigated to - existing items in the Stack are displayed just fine, but items added to/removed from the Stack are not reflected in the GridView until the page is navigated away from and back to. Debugging reveals that the CollectionChanged event in the Stack is always null, and thus it never gets called on update.

What am I missing?

Cerebrate
  • 1,391
  • 11
  • 26
  • How are you adding new objects? You'll need to add them on the UI thread. Also, how are you initializing the data context. Could you post more code? – Richard Cook Feb 26 '13 at 07:05
  • Had the same problem? WTF is with Microsoft. We've been sold this vision of MVVM, then they take away one of the most critical pillars of the architecture: the ICollectionView. – Quark Soup Dec 27 '14 at 18:15

1 Answers1

0

Just now I'm facing this same problem with custom collection that I want to be bindable. I discovered that only classes derived form Collection<> can be bound to.

Why? For now I do not know. So if you really want it to work then derive form Collection<> but this will mess with your design.

Rafal
  • 12,391
  • 32
  • 54
  • This suggestion, I think, is on the right track. I tried to change my vote, but can't because it's locked. You'll also need to provide an implementation of INotifyCollectionChanged in order to get the view to update when the view model is updated. – Quark Soup Dec 27 '14 at 21:49