George Barbulescu
George Barbulescu

Reputation: 131

ObservableCollection along with a repository

I am having trouble with grasping the concept of a ObservableCollection inside MVVM. For start I would like to point out that I am doing this in a Windows 8/Metro App, not WPF or Silverlight.

According to microsoft documentation, this collection has the following usefulness: "Represents a dynamic data collection that provides notifications when items get added, removed, or when the whole list is refreshed." From what I understand this helps you a lot when binding is involved. On the net I found a lot of simple examples, by creating a ObservableCollection on runtime and then working on it, but I didn't find out what is the proper way of using this collection with a repository.

Let' say I have the following repository interface that is an implementation for a ORM database backend, or a raw ADO.NET implementation

public interface IRepository<T>
{
   ObservableCollection<T> GetAll();
   void Create();
   void Update();
   void Delete();
   T GetByKey(object key);
}

and a simple ViewModel that use the repository as a model

public class ViewModel
{
   private ObservableCollection<Dummy> _obsListDummy;
   private RelayCommand _addCommand,_deleteCommand,_updateCommand;
   private IRepository<Dummy> _repositoryDummy;

   public class ViewModel()
   {
     _repositoryDummy=Factory.GetRepository<Dummy>();

   }  

   public ObservableCollection<Dummy> ObsListDummy
   {
     get
       {
          return _repositoryDummy.GetAll();
       }
   }

   public RelayCommand AddCommand
   {
     get
        {
           if (_addCommand == null)
       {
        _addCommand = new RelayCommand(p => DoAdd(); 
        //DoAdd method shows a popup for input dummy and then closes;
         );
       }
       return _myCommand;
        }

   }
   ........
}

My view would be a simple XAML with a grid, also Dummy object has INotifyPropertyChanged implemented.

Right now with this implementation after adding or updating or deleting, the ObservableCollection isn't refreshing, I know I could have put IEnumerable instead, but I dont'see an elegant solution of how would make repository to sync with the ObservableCollection that is in the model, other than subscrbing to CollectionChanged and there you treat all the states, but to it seems that I would repeat myself along with the logic that I do in the repository. And to make matters even worse, let's say I would like to get some push notification from my repository, towards the ObservableCollection.

I hope I was understand about my problem.

Thanks in advance.

Upvotes: 2

Views: 1314

Answers (2)

Mert Akcakaya
Mert Akcakaya

Reputation: 3129

You should implement INotifyPropertyChanged on your ViewModel and your ObsListDummy property should inform the ViewModel about changes applied to the collection. So it should look like this:

public class ViewModel: INotifyPropertyChanged
{
    // Declare the event 
    public event PropertyChangedEventHandler PropertyChanged;

    // Create the OnPropertyChanged method to raise the event 
    protected void OnPropertyChanged(string name)
    {
        PropertyChangedEventHandler handler = PropertyChanged;
        if (handler != null)
        {
            handler(this, new PropertyChangedEventArgs(name));
        }
    }

    private ObservableCollection<Dummy> _dummyCollection;

    public ObservableCollection<Dummy> DummyCollection 
    {
        get { return _dummyCollection; }
        set
        {
            // Set the value and then inform the ViewModel about change with OnPropertyChanged
            _dummyCollection = value;
            OnPropertyChanged("DummyCollection");
        }
    }
}

This whole INotifyPropertyChanged interface and implementation includes some dirty work like declaring event and creating a helper method to raise the event so I would suggest you to use some libraries for that like MVVM Light.

Upvotes: 1

Mare Infinitus
Mare Infinitus

Reputation: 8172

You should use a member of type ObservableCollection to store your Dummy ViewModels. In your Initialize method you read the dummies from the repository, create Dummy ViewModels and put those in the ObservableCollection. Now your view will get updated, when you use Binding to ObsListDummy (and add / remove from that collection, also note that Binding only works with public properties).

Right now, you just have a new ObservableCollection on each read, no events involved, so your View will never know about a change.

Further your ViewModel shall implement INotifyPropertyChanged.

Upvotes: 0

Related Questions