C # - WPF / WP. Database linking the right way? MVVM

Let's say that I have this class as a Model (database created from it):

public class Customer
{
    public int Id { get; set; }
    public string Name { get; set; }
    public string City { get; set; }
}

      

In the ViewModel I have ObservableCollection clients that store all clients from the database:

ObservableCollection<Customer> Customers;

      

"Clients" are populated from the database.

In the View, the ListBox is populated by clients:

<ListBox ItemsSource="{Binding Customers}" />

      

Here's the problem. Let's say I want to insert a new customer into the database, which approach should I take to track changes using the UI:

Reset ItemsSource: (This is the worst approach currently used)

ListBoxExample.ItemsSource = null;
ListBoxExample.ItemsSource = Customers;

      

Tracking changes through ObservableCollection clients

For example, if I want to insert something into the database, insert it into Clients and the UI will be notified of the change.

What are the other options?

What is the best MVVM approach to achieve the following:

  • Parse JSON data and insert into local database
  • Get data from local database and populate ListBox / ListView
  • If new data is inserted into the database or an item is deleted / changed, update the changes in the ListBox / ListView

If I want to add an item to the database, I can just add the item to the Customers list and add it to the database. However, let me say that I am deleting an object from the database, the Observable Clients collection will not be notified of this and will not be in sync (the UI will not update either). Is there a way to go deeper into the MVVM framework and instead of adding / removing / modifying items in the observable Collection AND database, to somehow make the observable collection track changes in the database (if the change is done with another application, for example).

+3


source to share


1 answer


Hmm, I don't know if you need a solution, but as per your last comment, you are not satisfied ... I'll illustrate my approach.

public class CustomersVm : INotifyPropertyChange
{ // just to point out, that you're using a VM class here   
   private ObservableCollection _customers;
   public ObservableCollection Customers
   { // since you're binding this to your listbox, DON'T change the reference during runtime
       get { return _customers ?? (_customers = new ObservableCollection());
   }

   // here comes your loading logic
   public void RefreshCustomers()
   {
       var customers = LoadCustomersFromDb(); // contains now a result set of model classes

       Customers.Clear(); //Clear the collection instead of creating it again.
       foreach(var customer in customers)
           Customers.Add(customer);
   }
}

      



Now use the XAML, which works if DataContext

to Window

set an instance CustomersVm

. (Note: To be more general, the DataContext

parent must be set as follows.)

<Window DataContext=... >
    <ListBox ItemsSource={Binding Customers} />
</Window>

      

0


source







All Articles