MVVM Interaction with CLR Events

How are you going to bind to the CLR event using the mvvm template?

For routed events, I use EventToCommandTrigger from the Cinch framework and it works fine.

I checked the Behaviors and Effects from the Expression Blend examples, and it looks like a DataEventTrigger is what I should use, but the sample is a bit confusing.

I want the IsVisibleChanged event to fire my IsVisibleChangedCommand. I'm also not sure which code to use in the ViewModel to support this.

<i:Interaction.Triggers> <i:EventTrigger EventName="SelectedItemChanged"> <framework:EventToCommandTrigger Command="{Binding SelectedMenuItemChangedCommand}" CommandParameter="{Binding SelectedValue, ElementName=lstClusters}" /> </i:EventTrigger> <framework:DataEventTrigger EventName="IsVisibleChanged" Source="{Binding IsVisibleChangedCommand}"> </framework:DataEventTrigger> </i:Interaction.Triggers> 
+4
source share
1 answer

You can use the Expression Blend SDK to invoke commands in response to events in general, however, in my experience, not all events are supported by EventTrigger.

For example, this works:

 <Label Content="LabelText"> <i:Interaction.Triggers> <i:EventTrigger EventName="MouseMove"> <i:InvokeCommandAction Command="{Binding IsVisibleChangedCommand, Mode=OneWay}"/> </i:EventTrigger> </i:Interaction.Triggers> </Label> 

But this is not so:

 <Label Content="LabelText"> <i:Interaction.Triggers> <i:EventTrigger EventName="IsVisibleChanged"> <i:InvokeCommandAction Command="{Binding IsVisibleChangedCommand, Mode=OneWay}"/> </i:EventTrigger> </i:Interaction.Triggers> </Label> 

I'm not sure why, but the Blend SDK is not like the IsVisible property. You can do something similar, but using visibility (instead of IsVisible) with PropertyChangedTrigger as follows:

 <Label x:Name="label1" Content="LabelText"> <i:Interaction.Triggers> <ei:PropertyChangedTrigger Binding="{Binding Visibility, ElementName=label1}"> <i:InvokeCommandAction Command="{Binding IsVisibleChangedCommand, Mode=OneWay}"/> </ei:PropertyChangedTrigger> </i:Interaction.Triggers> </Label> 

BTW - Here are the namespaces:

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

In addition, here is another solution to your specific problem that does not require the Blend SDK:

Instead of directly binding the event to the command, you can bind the visibility property of your object to the viewmodel property and execute the command from the property settings tool as follows:

View:

 <UserControl x:Class="SampleApp.Views.EventBindingDemoView" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Height="200" Width="200"> <UserControl.Resources> <BooleanToVisibilityConverter x:Key="BooleanToVisibilityConverter" /> </UserControl.Resources> <Grid> <Label Content="LabelText" Visibility="{Binding Path=ElementIsVisible, Mode=TwoWay, Converter={StaticResource BooleanToVisibilityConverter}}"/> <!-- The rest of your view here --> </Grid> </UserControl> 

ViewModel (ViewModelBase should implement INotifyPropertyChanged and OnPropertyChanged (string propertyName)):

 public class EventBindingDemoViewModel : ViewModelBase { private bool ElementIsVisibleField = true; // or false if it should initially be hidden public bool ElementIsVisible { get { return this.ElementIsVisibleField; } set { if (this.ElementIsVisibleField != value) { this.ElementIsVisibleField = value; this.OnPropertyChanged("ElementIsVisible"); // Execute command this.IsVisibleChangedCommand.Execute(null); } } } public ICommand IsVisibleChangedCommand; // The rest of your viewmodel here } 

In any case, this should work.

+7
source

All Articles