Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>In Windows Forms, or WPF without MVVM, you could just say <strong>MessageBox.Show()</strong> and that was it! Wouldn't it be nice if you could do the same in MVVM?</p> <p>Here is one way to do this - and it is as close as I can get to MessageBox.Show().</p> <p>Here is the MVVM friendly <strong>MessageBox_Show()</strong>!</p> <pre><code>public class MyViewModel: ViewModelBase { protected void AskTheQuestion() { MessageBox_Show(ProcessTheAnswer, "Are you sure you want to do this?", "Alert", System.Windows.MessageBoxButton.YesNo); } public void ProcessTheAnswer(MessageBoxResult result) { if (result == MessageBoxResult.Yes) { // Do something } } } </code></pre> <p>Tada!</p> <p>Here is how it works:</p> <p>All that MessageBox_Show actually does is fire an event, so it is perfectly MVVM friendly. The ViewModel knows nothing about any view that may or may not be consuming it, and it doesn't perform the showing of a Windows MessageBox on it's own, so it can also be safely unit tested.</p> <p>To use it in a View, which will cause it to actually show a MessageBox, you just subscribe to the event and call e.Show() in the event handler, like this:</p> <pre><code>public partial class MyView : UserControl { public MyView() { InitializeComponent(); this.DataContext = new MyViewModel(); (this.DataContext as MyViewModel).MessageBoxRequest += new EventHandler&lt;MvvmMessageBoxEventArgs&gt;(MyView_MessageBoxRequest); } void MyView_MessageBoxRequest(object sender, MvvmMessageBoxEventArgs e) { e.Show(); } } </code></pre> <p>And that is all you need to do to show MVVM friendly Windows MessageBoxes.</p> <p>The code below only needs to be implemented once in your project, or you can put it in a reusable shared library.</p> <p>Add this to your ViewModel base class so it can be used from any ViewModel:</p> <pre><code>public class ViewModelBase : INotifyPropertyChanged { //... public event EventHandler&lt;MvvmMessageBoxEventArgs&gt; MessageBoxRequest; protected void MessageBox_Show(Action&lt;MessageBoxResult&gt; resultAction, string messageBoxText, string caption = "", MessageBoxButton button = MessageBoxButton.OK, MessageBoxImage icon = MessageBoxImage.None, MessageBoxResult defaultResult = MessageBoxResult.None, MessageBoxOptions options = MessageBoxOptions.None) { if (this.MessageBoxRequest != null) { this.MessageBoxRequest(this, new MvvmMessageBoxEventArgs(resultAction, messageBoxText, caption, button, icon, defaultResult, options)); } } } </code></pre> <p>And then add the EventArgs class for the event handler:</p> <pre><code>public class MvvmMessageBoxEventArgs : EventArgs { public MvvmMessageBoxEventArgs(Action&lt;MessageBoxResult&gt; resultAction, string messageBoxText, string caption = "", MessageBoxButton button = MessageBoxButton.OK, MessageBoxImage icon = MessageBoxImage.None, MessageBoxResult defaultResult = MessageBoxResult.None, MessageBoxOptions options = MessageBoxOptions.None) { this.resultAction = resultAction; this.messageBoxText = messageBoxText; this.caption = caption; this.button = button; this.icon = icon; this.defaultResult = defaultResult; this.options = options; } Action&lt;MessageBoxResult&gt; resultAction; string messageBoxText; string caption; MessageBoxButton button; MessageBoxImage icon; MessageBoxResult defaultResult; MessageBoxOptions options; public void Show(Window owner) { MessageBoxResult messageBoxResult = MessageBox.Show(owner, messageBoxText, caption, button, icon, defaultResult, options); if (resultAction != null)resultAction(messageBoxResult); } public void Show() { MessageBoxResult messageBoxResult = MessageBox.Show(messageBoxText, caption, button, icon, defaultResult, options); if (resultAction != null) resultAction(messageBoxResult); } } </code></pre> <p>Unit testing is easy:</p> <pre><code>target.AskTheQuestion(); target.ProcessTheAnswer(System.Windows.MessageBoxResult.Yes); </code></pre> <p>Happy Coding!</p>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload