WPF MVVM模式下如何将MouseButtonEventArgs传递给MultiConverter
问题解决:WPF MVVM中通过MultiConverter传递集合项与MouseDown事件参数
问题背景
使用MVVM模式开发无代码后置的WPF应用,拥有可动态添加对象的ObservableCollection<MyClass>集合myCol,集合内的MyClass对象包含用于绘制图像的WritableBitmap类型属性mySource。需要捕获集合项的MouseDown事件,同时获取触发事件的集合项实例和MouseButtonEventArgs(包含事件位置等参数),尝试用MultiConverter传递这两个参数,但不知道如何将MouseButtonEventArgs传入转换器。
原代码问题
原XAML中第二个Binding错误绑定到了ItemsControl,无法获取事件参数;转换器期望接收MouseButtonEventArgs但实际传入的是ItemsControl实例。
原XAML代码
<ItemsControl ItemsSource="{Binding myCol}"> <ItemsControl.ItemTemplate> <DataTemplate> <Grid> <Image Source="{Binding mySource}"> <b:Interaction.Triggers> <b:EventTrigger EventName="MouseDown"> <b:InvokeCommandAction Command="{Binding DataContext.MouseDownCommand, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"> <b:InvokeCommandAction.CommandParameter> <MultiBinding Converter="{StaticResource MyConverter}"> <Binding /> <!-- 需要修改的行 --> <Binding RelativeSource="{RelativeSource Mode=FindAncestor, AncestorType={x:Type ItemsControl}}"/> </MultiBinding> </b:InvokeCommandAction.CommandParameter> </b:InvokeCommandAction> </b:EventTrigger> </b:Interaction.Triggers> </Image> </Grid> </DataTemplate> </ItemsControl.ItemTemplate> </ItemsControl>
原转换器代码
public object Convert(object[] values, Type target_Type, object parameter, CultureInfo culture) { var myClass = (MyClass)values[0]; var args = (MouseButtonEventArgs)values[1]; // 期望获取的事件参数 return new Tuple<MyClass, MouseButtonEventArgs>(myClass, args); }
解决方案
关键修改点
- 开启
InvokeCommandAction的PassEventArgsToCommand属性,允许事件参数被绑定 - 将第二个Binding指向父级
EventTrigger的EventArgs属性,获取MouseButtonEventArgs
修改后的XAML代码
<ItemsControl ItemsSource="{Binding myCol}"> <ItemsControl.ItemTemplate> <DataTemplate> <Grid> <Image Source="{Binding mySource}"> <b:Interaction.Triggers> <b:EventTrigger EventName="MouseDown"> <b:InvokeCommandAction Command="{Binding DataContext.MouseDownCommand, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}" PassEventArgsToCommand="True"> <b:InvokeCommandAction.CommandParameter> <MultiBinding Converter="{StaticResource MyConverter}"> <Binding /> <!-- 绑定到EventTrigger的EventArgs属性,获取MouseButtonEventArgs --> <Binding RelativeSource="{RelativeSource AncestorType=b:EventTrigger}" Path="EventArgs"/> </MultiBinding> </b:InvokeCommandAction.CommandParameter> </b:InvokeCommandAction> </b:EventTrigger> </b:Interaction.Triggers> </Image> </Grid> </DataTemplate> </ItemsControl.ItemTemplate> </ItemsControl>
转换器代码无需修改
保持原转换器代码即可,此时values[1]将正确传入MouseButtonEventArgs实例。
注意事项
- 确保XAML的命名空间引用正确:
- .NET Core/.NET 5+版本:
xmlns:b="http://schemas.microsoft.com/xaml/behaviors" - .NET Framework版本(旧版Blend交互库):
xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity",同时需将XAML中所有b:替换为i:,包括RelativeSource的AncestorType
- .NET Core/.NET 5+版本:
内容的提问来源于stack exchange,提问作者vela18
相关产品推荐
相关产品推荐

