Question

I'm struggling with one point of MVVM and I hope someone can enlighten me.

My scenario is this: A model something like this:

public class Codes
{
    public string Code { get; set; }
    public string Value { get; set; }
    public ObservableCollection<SubCoddes> SubCodes { get; set; }
}

A ViewModel that has this:

public ObservableCollection<Codes> Codes { get; set; }

The Codes collection are bound to a ListView in the View.

My big doubt is if there should be ObservableCollection in the model. If not, what is a better approach?

Both Codes and SubCodes are filled by a query in a MS SQLServer database when the application is initialized...and there's no option to create new ones. They can only be reused.

I can have in Codes multiple equal codes with different values - ex:

Code a = new Code { value="test1", Code ="100" }
Code b = new Code { value="test2", Code ="100" }

These values should be bound to TestBoxes in the view.

====EDIT=====

Maybe I have wrongly exposed the problem. When I say cannot create more, I may have lead to a wrong preposution. What I meant is that the initial structure is created with the DB query, but in the UI there will be buttons to replicate a Code and a Subcode...and that will add those to the corresponding lists.

Ex: in the UI:

Code A - duplicate button

-> Subcode A - duplicate button

-> Subcode B - duplicate button

Code B - duplicate button

Everytime I click on a duplicate button it duplicates the structure (either subcodes or codes with subcodes).

These changes must be done in the bservableCollection Codes.

I hope I'm making myself clear...and sorry for my English.

Regards

Was it helpful?

Solution

You do not need an ObservableCollection<T> that is only useful when you add or remove items from the collection after assigning it - which you say you do not. A List<T> would be fine and well within MVVM. However you still have to remember to implement INotifyPropertyChanged and raise the PropertyChanged when the List<T> is assigned - or anything you assign you want the binding to re-read the source.

e.g. you should have:

private List<Code> codes;
public List<Codes> Codes 
{ 
    get {return codes;}
    set 
    {
        codes = value;
        NotifyPropertyChanged("Codes");
    }
}

private void NotifyPropertyChanged(string propertyName)
{
    if (PropertyChanged != null)
    {
        PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }
}

The same applies to your nested collection SubCodes, i.e. Codes should also implement the interface and the setter for SubCodes should raise the event. Furthermore if you were to modify a Code's property at runtime and you want that reflected in the UI the properties on Code should raise the event too. Also any class you bind to should always implement the interface even if the individual properties do not raise the event, because binding to a class that does not implement the interface creates memory leaks. (unless the Property is a DependencyProperty, which it shouldn't be unless you are authoring you own control, or the Binding Mode is OneTime).

OTHER TIPS

I think the MVVM way is to have the entities/data model in the Model, and to do all the tweeks and modifications to it in the ViewModel so it can then bind it to the View. Assuming you are using observable collections to check if the user modifies some textbox maybe they should be in the ViewModel.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top