WPF DataGrid列,具有可变数量的按钮/形状

WPF DataGrid列,具有可变数量的按钮/形状,wpf,data-binding,mvvm,datagrid,Wpf,Data Binding,Mvvm,Datagrid,我有一个要求,在一个DataGrid列上,我需要并排显示x个可单击按钮(水平堆叠)。要显示的实际数量或按钮取决于该列中的绑定值 下图显示了这一点。左边的网格是我当前的网格,右边的网格是我正在寻找的 栅格绑定到ViewModel,如下所示: <DataGrid ItemsSource="{Binding employees}" AutoGenerateColumns="False" > <DataGrid.Columns> <

我有一个要求,在一个DataGrid列上,我需要并排显示x个可单击按钮(水平堆叠)。要显示的实际数量或按钮取决于该列中的绑定值

下图显示了这一点。左边的网格是我当前的网格,右边的网格是我正在寻找的

栅格绑定到ViewModel,如下所示:

<DataGrid ItemsSource="{Binding employees}" AutoGenerateColumns="False"  >
        <DataGrid.Columns>
            <DataGridTextColumn Binding="{Binding Path=id}" Header="Id" />
            <DataGridTextColumn Binding="{Binding Path=numberofplatforms}" Header="No" Width="50" IsReadOnly="True" />
        </DataGrid.Columns>
    </DataGrid>
雇员是:

Public Class employee
    Public Property id As String
    Public Property numberofplatforms As Integer
    Public Property selectedplatform As Integer
End Class
除了显示按钮外,按钮本身的作用必须与单选按钮类似,即在任何数据网格行上,只有一个按钮“按下”(图像中的蓝色背景按钮),其他按钮不按下(灰色背景)。按钮(或形状)必须可单击,以便更改选择

按下哪个按钮由ViewModel根据selectedplatform属性确定。本例中的属性1表示ABC,1表示DEF,2表示GHI。如果NumberOfPlatform属性为零,则不显示任何按钮(JKL)


如何设置此机制?

代码的某些部分是用C#编写的,我希望这不是问题。Wpf代码:

<Window.Resources>
    <ResourceDictionary>
        <local:PositiveIntegersConverter x:Key="PositiveIntegersConverter" />
        <local:EmployeePlatformOptionConverter x:Key="EmployeePlatformOptionConverter"/>
    </ResourceDictionary>
</Window.Resources>

<DataGrid ItemsSource="{Binding employees}" AutoGenerateColumns="False" x:Name="DataGrid1">
    <DataGrid.Columns>
        <DataGridTextColumn Binding="{Binding Path=id}" Header="Id" />
        <DataGridTemplateColumn Header="No" IsReadOnly="True">
            <DataGridTemplateColumn.CellTemplate>
                <DataTemplate>
                        <ListBox ItemsSource="{Binding numberofplatforms, Converter={StaticResource PositiveIntegersConverter}}" SelectedItem="{Binding selectedplatform}"
                                    x:Name="ListBox1">
                            <ListBox.ItemTemplate>
                                <DataTemplate>
                                    <Button Content="{Binding}" Command="{Binding Source={x:Reference DataGrid1}, Path=DataContext.SelectOptionCommand}">
                                        <Button.CommandParameter>
                                            <MultiBinding Converter="{StaticResource EmployeePlatformOptionConverter}">
                                                <Binding ElementName="ListBox1" Path="DataContext"/>
                                                <Binding Path="."/>
                                            </MultiBinding>
                                        </Button.CommandParameter>
                                        <Button.Style>
                                            <Style TargetType="Button">
                                                <Setter Property="Background" Value="Gray" />
                                                <Setter Property="Foreground" Value="White" />
                                                <Style.Triggers>
                                                    <DataTrigger Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=ListBoxItem}, Path=IsSelected}"
                                                                    Value="True">
                                                        <Setter Property="Background" Value="Blue" />
                                                    </DataTrigger>
                                                </Style.Triggers>
                                            </Style>
                                        </Button.Style>
                                    </Button>
                                </DataTemplate>
                            </ListBox.ItemTemplate>
                            <ListBox.ItemsPanel>
                                <ItemsPanelTemplate>
                                    <StackPanel Orientation="Horizontal" />
                                </ItemsPanelTemplate>
                            </ListBox.ItemsPanel>
                        </ListBox>
                </DataTemplate>
            </DataGridTemplateColumn.CellTemplate>
        </DataGridTemplateColumn>
    </DataGrid.Columns>
</DataGrid>
使用封装对象:

public class EmployeePlatformOption
{
    public Employee Employee { get; set; }
    public int Platform { get; set; }
}
将选择传递到ViewModel类中的SelectOptionCommand:

public ICommand SelectOptionCommand { get; set; }
private void SelectOptionExecute(EmployeePlatformOption employeePlatformOption)
{
    if (employeePlatformOption != null && employeePlatformOption.Employee != null &&
        employeePlatformOption.Platform > 0)
    {
        employeePlatformOption.Employee.selectedplatform = employeePlatformOption.Platform;
    }
}

员工应实现INotifyPropertyChange界面,以便在屏幕上显示selectedplatform update。

部分代码是C#,我希望这不是问题。Wpf代码:

<Window.Resources>
    <ResourceDictionary>
        <local:PositiveIntegersConverter x:Key="PositiveIntegersConverter" />
        <local:EmployeePlatformOptionConverter x:Key="EmployeePlatformOptionConverter"/>
    </ResourceDictionary>
</Window.Resources>

<DataGrid ItemsSource="{Binding employees}" AutoGenerateColumns="False" x:Name="DataGrid1">
    <DataGrid.Columns>
        <DataGridTextColumn Binding="{Binding Path=id}" Header="Id" />
        <DataGridTemplateColumn Header="No" IsReadOnly="True">
            <DataGridTemplateColumn.CellTemplate>
                <DataTemplate>
                        <ListBox ItemsSource="{Binding numberofplatforms, Converter={StaticResource PositiveIntegersConverter}}" SelectedItem="{Binding selectedplatform}"
                                    x:Name="ListBox1">
                            <ListBox.ItemTemplate>
                                <DataTemplate>
                                    <Button Content="{Binding}" Command="{Binding Source={x:Reference DataGrid1}, Path=DataContext.SelectOptionCommand}">
                                        <Button.CommandParameter>
                                            <MultiBinding Converter="{StaticResource EmployeePlatformOptionConverter}">
                                                <Binding ElementName="ListBox1" Path="DataContext"/>
                                                <Binding Path="."/>
                                            </MultiBinding>
                                        </Button.CommandParameter>
                                        <Button.Style>
                                            <Style TargetType="Button">
                                                <Setter Property="Background" Value="Gray" />
                                                <Setter Property="Foreground" Value="White" />
                                                <Style.Triggers>
                                                    <DataTrigger Binding="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType=ListBoxItem}, Path=IsSelected}"
                                                                    Value="True">
                                                        <Setter Property="Background" Value="Blue" />
                                                    </DataTrigger>
                                                </Style.Triggers>
                                            </Style>
                                        </Button.Style>
                                    </Button>
                                </DataTemplate>
                            </ListBox.ItemTemplate>
                            <ListBox.ItemsPanel>
                                <ItemsPanelTemplate>
                                    <StackPanel Orientation="Horizontal" />
                                </ItemsPanelTemplate>
                            </ListBox.ItemsPanel>
                        </ListBox>
                </DataTemplate>
            </DataGridTemplateColumn.CellTemplate>
        </DataGridTemplateColumn>
    </DataGrid.Columns>
</DataGrid>
使用封装对象:

public class EmployeePlatformOption
{
    public Employee Employee { get; set; }
    public int Platform { get; set; }
}
将选择传递到ViewModel类中的SelectOptionCommand:

public ICommand SelectOptionCommand { get; set; }
private void SelectOptionExecute(EmployeePlatformOption employeePlatformOption)
{
    if (employeePlatformOption != null && employeePlatformOption.Employee != null &&
        employeePlatformOption.Platform > 0)
    {
        employeePlatformOption.Employee.selectedplatform = employeePlatformOption.Platform;
    }
}
员工应实现INotifyPropertyChange界面,以便在屏幕上显示selectedplatform update