如何从 ListBox.ItemTemplate DataTemplate 内部调用 Button 命令,以在不选择 ListBox 项目的情况下传递参数?

How do I call Button command from inside of ListBox.ItemTemplate DataTemplate, to pass parameter without selecting ListBox item?

我有一个问题,我已经面临几个小时了。在我的 xaml 视图中,我有一个 ListBox,它定义 DataTemplate 如下:

<DataTemplate>
                    <Grid>
                        <Grid.RowDefinitions>
                            <RowDefinition Height ="30"/>
                            <RowDefinition Height ="30"/>
                        </Grid.RowDefinitions>
                        <Grid.ColumnDefinitions>
                            <ColumnDefinition Width="*" />
                            <ColumnDefinition Width="*" />
                            <ColumnDefinition Width="*" />
                            <ColumnDefinition Width="*" />
                            <ColumnDefinition Width="*" />
                            <ColumnDefinition Width="*" />
                            <ColumnDefinition Width="*" />
                        </Grid.ColumnDefinitions>

                        <!--Row 0-->
                        <TextBlock Grid.Column="0"
                                       Grid.Row="0"
                                       Style="{StaticResource racetblk}">
                                    Horse name
                        </TextBlock>
                        <TextBlock Grid.Column="1"
                                       Grid.Row="0"
                                       Style="{StaticResource racetblk}">
                                    Horse DOB
                        </TextBlock>

                        <!--Row 1-->
                        <StackPanel Orientation="Horizontal"
                                    Grid.Row="1"
                                    Grid.Column="0">
                            <TextBox Text="{Binding Path=HorseName, Mode=TwoWay, UpdateSourceTrigger=LostFocus}"
                                 Style="{StaticResource tableItem}"
                                 Height="20"
                                     Width="150"/>
                            <Button Width="50"
                                Margin="5"
                                Height="20"
                                Content="Pick"
                                Background=" #a1c883 "
                                Foreground="White"
                                Command="{Binding PickHorseDataCommand}"
                                CommandParameter="{Binding ElementName=lbHorseList, Path=SelectedIndex}"/>
                        </StackPanel>
                        <TextBox Text="{Binding Path=Birth, Mode=TwoWay, UpdateSourceTrigger=LostFocus}"
                                 Grid.Row="1"
                                 Grid.Column="1"
                                 Style="{StaticResource tableItem}"
                                 Height="20"/>
                    </Grid>

                </DataTemplate>

在模板内部 <!--Row 1--> 我有一个按钮,应该触发我的 ViewModel 命令内部的命令应该在 TextBox:

中键入文本后触发
private ICommand pickHorseDataCommand;
        public ICommand PickHorseDataCommand
        {
            get
            {
                if (pickHorseDataCommand == null)
                    pickHorseDataCommand = new RelayCommand(
                    o =>
                    {
                        int horseIndex = (int)o;
                        HorseDataWrapper horse = Horses[horseIndex];
                        LoadedHorse horseFromList = allHorses.Where(i => i.Name == horse.HorseName).FirstOrDefault();
                        horse.Birth = horseFromList.Birth.ToString();
                        var dupa = horse;
                    });
                return pickHorseDataCommand;
            }
        }

这有两个问题。首先,命令根本没有触发,我相信,我应该使用 RelativeSource 以某种方式绑定命令,但直到现在我还没有设法做到这一点。

另外,CommandParameter绑定了SelectedIndex,所以在按下按钮的时候必须选中ListBox项,才能实现绑定。如果不选择项目,我找不到任何其他解决方案来进行绑定。也许您有其他选择?

非常感谢您抽出时间提供帮助。

你可以这样做 需要指定 AncestorType

Command="{Binding DataContext.pickHorseDataCommand,RelativeSource={RelativeSource AncestorType=,Mode=FindAncestor}}"

如果命令是在视图模型中定义的,您可以像这样绑定到它:

Command="{Binding DataContext.PickHorseDataCommand, RelativeSource={RelativeSource AncestorType=ListBox}}"

如果你需要视图模型中的SelectedIndex,你应该定义一个源属性并将ListBoxSelectedIndex绑定到属性这个而不是使用 CommandParameter:

<ListBox SelectedIndex="{Binding YourIndexProperty}" ... />

命令的Execute方法可以直接访问索引属性:

int index = this.YourIndexProperty;

另一个选项可能是传递对当前项目本身的引用,而不是使用索引,作为命令的参数:

CommandParameter="{Binding}"