32

What is the best way to bind a WPF event in the View to the ViewModel?

I have a drop event in my View but I want to replace it to the ViewModel due binding.

Found several solutions but none of them did what I expected.

View code:

    <TextBox 
    AllowDrop="True" 
    PreviewDrop="email_Drop" />
Fütemire
  • 1,705
  • 1
  • 26
  • 21
jefsmi
  • 721
  • 2
  • 9
  • 19
  • 8
    Imo binding an Event to a viewmodel is never a good idea. Well of course it depends on how you want MVVM to work for you, but we strictly separate Events, which are ui logic, and commands which is business logic. Just wanted to add this :) in the end it depends alot of how and what you want to achieve. – dowhilefor Oct 24 '11 at 14:58
  • Thanks, nice comment i'll keep this in mind. For now I just want the code behind files to be empty. But from all things I've read you are right ;) – jefsmi Oct 24 '11 at 15:42
  • @dowhilefor that is an answer by itself - and a good one. I suggest you write something up. :) – ANeves Nov 06 '15 at 16:41

4 Answers4

69

One way to handle events in MVVM and XAML is to use the Blend Interactivity features. This namespace contains the InvokeCommandAction and the CallMethodAction classes.

InvokeCommandAction lets you bind any event to a view-model command while CallMethodAction lets you bind any event to a view-model method.

For example if you want to bind the DoubleClick event of a Button to a view-model command you would do like this:

<Button>
    <i:Interaction.Triggers>
        <i:EventTrigger EventName="MouseDoubleClick">
            <i:InvokeCommandAction Command="{Binding Path=DoSomethingCommand}"/>
        </i:EventTrigger>
    </i:Interaction.Triggers>
</Button>

And declaring this namespace:

xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"

All you need to reference it in your projects is to install Expression Blend or the Expression Blend SDK.

Ucodia
  • 7,410
  • 11
  • 47
  • 81
  • Using dotnet 6 I had to add a different namespace: xmlns:i="http://schemas.microsoft.com/xaml/behaviors" – Dbloom Mar 30 '23 at 23:15
6

Well one way to do is to convert that event into a command and then bind it to presenter command, i.e. by defining event behaviour.

See this, WPF Event Binding to ViewModel (for non-Command classes)

Community
  • 1
  • 1
Bhupendra
  • 1,725
  • 22
  • 30
  • I found the EventToCommand solution but I'm not huge fan of it so wanted to know if there were better ways to solve this but thanks ;) – jefsmi Oct 24 '11 at 14:58
  • 1
    :) you can try the attached property solution if that suits you – Bhupendra Oct 24 '11 at 15:20
2
<Button MouseDoubleClick="{eb:EventBinding Command=DoSomethingCommand}">

</Button>

Command

{eb:EventBinding} (Simple naming pattern to find Command)

{eb:EventBinding Command=CommandName}

CommandParameter

$e (EventAgrs)

$this or $this.Property

string

https://github.com/JonghoL/EventBindingMarkup

jongho
  • 79
  • 2
1

I get the viewmodel from the bindingcontext and activate my viewmodel method from there

    public partial class ParentView : ContentPage
    {
            public ParentView()
            {            
                InitializeComponent();
            }

            private void LanguagePicker_SelectedIndexChanged(object sender, System.EventArgs e)
            {
                var parentViewModel = (ParentViewModel)this.BindingContext;
                parentViewModel.SelectedLanguageChanged(sender,e);
            }
    }
Sjors Miltenburg
  • 2,540
  • 4
  • 33
  • 60