C# 如何在执行命令之前转换命令参数?
我的视图中有一个DataGrid,DataGrid有带按钮的单元格,这些单元格分配了命令。现在我希望将当前行对象(位于DataGrid.CurrentItem中)传递给命令执行逻辑 我最初的想法是将CommandParameter与值转换器一起使用,转换器将DataGrid作为参数,并将所需信息从DataGrid提取到我自己的类中——这样我就可以避免从视图模型中引用DataGrid 问题是,显示网格时会执行CommandParameter绑定/值转换,这意味着还并没有选定的项 我是否可以避免将DataGrid引用引入到命令执行逻辑中,比如在执行命令之前解析deffer CommandParameter之类的内容 更新:我需要CurrentItem和CurrentColumn,我已经意识到,CurrentItem可能可以通过绑定SelectedItem来访问,以避免使用SelectedItem属性收到答案。C# 如何在执行命令之前转换命令参数?,c#,wpf,c#-4.0,datagrid,wpfdatagrid,C#,Wpf,C# 4.0,Datagrid,Wpfdatagrid,我的视图中有一个DataGrid,DataGrid有带按钮的单元格,这些单元格分配了命令。现在我希望将当前行对象(位于DataGrid.CurrentItem中)传递给命令执行逻辑 我最初的想法是将CommandParameter与值转换器一起使用,转换器将DataGrid作为参数,并将所需信息从DataGrid提取到我自己的类中——这样我就可以避免从视图模型中引用DataGrid 问题是,显示网格时会执行CommandParameter绑定/值转换,这意味着还并没有选定的项 我是否可以避免将D
- 您的命令参数应该是
这样,参数将是单击按钮的行CommandParameter=“{Binding}”
,该按钮是模型的一个实例DataContext
- 将参数强制转换到命令中的模型
方法Execute
- 例如,假设您希望阻止该命令执行
如果SelectedItem为空或必须选择该项,则
您只需从基于方法的
返回bool即可 你想买什么就买什么CanExecute
- 您的命令参数应该是
这样,参数将是单击按钮的行CommandParameter=“{Binding}”
,该按钮是模型的一个实例DataContext
- 将参数强制转换到命令中的模型
方法Execute
- 例如,假设您希望阻止该命令执行
如果SelectedItem为空或必须选择该项,则
您只需从基于方法的
返回bool即可 你想买什么就买什么CanExecute
- 所以我最初的想法非常接近
当我将CommandParameter绑定到DataGrid时,问题是,当绑定解析时,DataGrid还不知道什么是CurrentColumn、CurrentCell或CurrentItem,所以它解析为空值
所以我将绑定改为绑定到DataGridCell——问题解决了——Cell能够在绑定解析时分辨出它所属的列和项,所以当命令被触发时,它已经拥有了所有正确的数据
Style看起来像这样:
<Button Command="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}},
Path=DataContext[RowActionFeature].RowActionCommand}"
CommandParameter="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type DataGridCell}},
Converter={StaticResource DataGridCellToRowActionParametersConverter}}">
...
</Button>
public class DataGridCellToRowActionParametersConverter : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
var dataGridCell = value as DataGridCell;
if (dataGridCell == null)
{
return null;
}
var dataRowView = dataGridCell.DataContext as DataRowView;
var columnIndex = dataGridCell.Column.DisplayIndex;
return new RowActionParameters
{
Item = dataGridCell.DataContext,
ColumnPropertyName = dataGridCell.Column.SafeAccess(x => x.SortMemberPath),
DataRowView = dataRowView,
ColumnIndex = columnIndex
};
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
所以我最初的想法很接近 当我将CommandParameter绑定到DataGrid时,问题是,当绑定解析时,DataGrid还不知道什么是CurrentColumn、CurrentCell或CurrentItem,所以它解析为空值 所以我将绑定改为绑定到DataGridCell——问题解决了——Cell能够在绑定解析时分辨出它所属的列和项,所以当命令被触发时,它已经拥有了所有正确的数据 Style看起来像这样:
<Button Command="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type UserControl}},
Path=DataContext[RowActionFeature].RowActionCommand}"
CommandParameter="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type DataGridCell}},
Converter={StaticResource DataGridCellToRowActionParametersConverter}}">
...
</Button>
public class DataGridCellToRowActionParametersConverter : IValueConverter
{
public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
{
var dataGridCell = value as DataGridCell;
if (dataGridCell == null)
{
return null;
}
var dataRowView = dataGridCell.DataContext as DataRowView;
var columnIndex = dataGridCell.Column.DisplayIndex;
return new RowActionParameters
{
Item = dataGridCell.DataContext,
ColumnPropertyName = dataGridCell.Column.SafeAccess(x => x.SortMemberPath),
DataRowView = dataRowView,
ColumnIndex = columnIndex
};
}
public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
{
throw new NotImplementedException();
}
}
你试过了吗,我想绑定是在你触发命令时执行的。@Bolu-是的,我试过了,绑定是在呈现数据网格时执行的,而不是在单击按钮时执行的。你想发送什么命令参数,我想大部分都可以通过按钮的命令绑定来完成。我不知道这是WPF,还有一个C标记。你试过了吗,我认为绑定是在您触发命令时执行的。@Bolu-是的,我已经尝试过了,绑定是在呈现数据网格时执行的,而不是在单击按钮时执行的。您要发送什么命令参数,我想大部分都可以通过按钮的命令绑定来完成。我不知道这是WPF。还有一个C#标记。它解决了CurrentItem问题,但没有回答如何获取CurrentColumn。@Giedrius您在同一行中有多个按钮使用同一命令?是的,我使用DataGridCell样式,所以样式是按钮,它的命令被描述-所以是的,我需要以某种方式识别它是什么按钮。@Giedrius确定您可以使用
IMultiValueConverter
向您的命令传递多个参数,例如,您可以将列索引作为附加参数传递,我不确定在没有看到XAML的情况下你到底想做什么,所以请用其中的相关部分更新问题,同时ViewModel必须对你的视图一无所知,使用XAML和Converters一切都是可行的我明白你的意思,我想我还没有很好地表达我的问题-主要的想法是,如果可以将CommandParameter解析推迟到command即将执行的时刻,而不是在渲染时进行解析。这解决了CurrentItem问题,但不回答如何获取CurrentColumn。@Giedrius您在同一行中有多个按钮,使用同一命令?是的,我使用DataGridCell样式,因此样式中是button,并且描述了它的命令-是的,我需要以某种方式识别按钮。@Giedrius确定您可以使用IMultiValueConverter
向命令传递多个参数。例如,您可以将列索引作为附加参数传递,我不确定您在没有看到XAML的情况下到底想做什么,因此请使用问题的相关部分更新问题,另外,ViewModel对您的视图一无所知,使用XAML和Converters一切都是可行的。我明白您的意思,我想我还没有很好地阐述我的问题——主要的想法是,是否可以将命令参数解析推迟到命令即将执行时,而不是在渲染时进行解析。