Is it possible for the View to subscribe to the CLM event of the ViewModel?
Sometimes the view model needs to raise notifications that the view should process and do something in response, especially. when they cannot be modeled as property and property change notifications.
Anything in MVVM Light that can allow a view to listen for events and broadcast model model notifications to UI actions using declarative Xaml markup?
a source to share
Personally, I find a technique for picking up events from a VM and capturing them in a representation that is acceptable in certain circumstances. I usually prefer to work with Messenger for such cases, especially if you need special event arguments (because it is quite a lot of work to declare a new args argument class and a new delegate).
Also, the event handler is a tight connection between the view and the viewmodel, while you usually prefer a loose connection, but if you know about this fact and the consequences, then why not ...
Another method (for example, for navigation, dialogs, etc.) is to declare the interface using the required methods (for example, IDialogService with AskConfirmation and ShowMessage methods). Then implement that class interface (which could be MainWindow / MainPage itself) and pass it to the ViewModel (for example, in the View's constructor right after the call to InitializeComponent). In the VM, call these methods as needed. This has the advantage of being easy enough to test (just mock the IDialogService and make sure the methods are called).
I usually move between Messenger and IDialogService depending on various factors. Lately, I prefer the interface based approach because it's a little easier to test (but Messenger is quite testable, so YMMV).
Cheers, Laurent
a source to share
In a "pure" MVVM solution, the only thing that needs to connect the View to the ViewModel is Bindings. There is nothing to stop you from passing your DataContext to your ViewModel and attaching an event to the View, but that kind of defeats the purpose of using the MVVM approach. Alternatively, try to rethink why you think you need to raise the event to view:
- Do you need to display a popup? A number of related "toast" lists can be used with an appropriate template to create popups in a view because the viewmodel "inserts" notification objects into the associated collection.
- Do you need to disable the dropdown menu or some similar UI action? Bind the appropriate property in the UI to the property of the view model, set the mode to bidirectional, and set the view model accordingly.
etc. etc.
a source to share
You are correct that sometimes the ViewModel needs to interact with the View. One way to do this is for the ViewModel to raise the CLR event that the View is viewing. This can be done in code for the view.
MVVM is not about eliminating coding views! Its separation of concerns and better testability with unit tests.
Another way to enable communication between the ViewModel and the View is by introducing an interface (IView). More information on this approach can be found on the WPF Application Framework (WAF) website .
a source to share
MVVMLight does have tech support for handling sending messages from the ViewModel to your view. Review the namespace GalaSoft.MvvmLight.Messaging. There is a better way to send messages using dialod, then the example below, however this is just a quick example.
Example
ViewModel
public MainPageViewModel()
{
Messenger.Default.Send("Payment");
}
View
public MainPage()
{
Messenger.Default.Register<string>(this, DialogRequested);
}
private DialogRequested(string message)
{
MessageBox.Show(message);
}
a source to share