Models and View-Models
The definition of a model is often hotly debated, and the line between a model and a view-model can be blurred. Some prefer not to "pollute" their models with the INotifyPropertyChanged
interface, and instead duplicate the model properties in the view-model, which does implement this interface. Like many things in software development, there is no right or wrong answer. Be pragmatic and do whatever feels right.
View Separation
The intention of MVVM is to separate those three distinct areas - Model, view-model, and View. While it's acceptable for the view to access the view-model (VM) and (indirectly) the model, the most important rule with MVVM is that the VM should have no access to the view or its controls. The VM should expose everything that the view needs, via public properties. The VM should not directly expose or manipulate UI controls such as TextBox
, Button
, etc.
In some cases, this strict separation can be difficult to work with, especially if you need to get some complex UI functionality up and running. Here, it's perfectly acceptable to resort to using events and event handlers in the view's "code-behind" file. If it's purely UI functionality then by all means utilise events in the view. It's also acceptable for these event handlers to call public methods on the VM instance - just don't go passing it references to UI controls or anything like that.
RelayCommand
Unfortunately the RelayCommand
class used in this example isn't part of the WPF framework (it should have been!), but you'll find it in almost every WPF developer's tool box. A quick search online will reveal plenty of code snippets that you can lift, to create your own.
A useful alternative to RelayCommand
is ActionCommand
which is provided as part of Microsoft.Expression.Interactivity.Core
which provides comparable functionality.