prism 5.0 InvokeCommandAction SelectionMode =" Multiple"

时间:2017-03-01 12:26:23

标签: wpf mvvm prism prism-5

我想通过InvokeCommandAction prism 5.0检测列表框中的所有选定项目。

XAML

<Window x:Class="Selection.Prism5._0.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
    xmlns:local="clr-namespace:Selection.Prism5"
    xmlns:prism="http://www.codeplex.com/prism"
    mc:Ignorable="d"
    Title="MainWindow"
    Height="350"
    Width="525">
<FrameworkElement.DataContext>
    <local:MainViewModel />
</FrameworkElement.DataContext>
<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="2*" />
        <ColumnDefinition Width="5" />
        <ColumnDefinition Width="3*" />
    </Grid.ColumnDefinitions>
    <ListBox SelectedItem="{Binding SelectedItem}"
             ItemsSource="{Binding Items}"
             SelectionMode="Multiple">
        <i:Interaction.Triggers>
            <i:EventTrigger EventName="SelectionChanged">
                <prism:InvokeCommandAction Command="{Binding SelectItemsCommand}"
                                           TriggerParameterPath="AddedItems" />
            </i:EventTrigger>
        </i:Interaction.Triggers>

        <ListBox.ItemTemplate>
            <DataTemplate>
                <TextBlock Text="{Binding Name}" />
            </DataTemplate>
        </ListBox.ItemTemplate>
    </ListBox>

</Grid>

查看模型

  public class MainViewModel : BindableBase
{
    public MainViewModel()
    {
        this.Items = new List<Model>
        {
           new Model {Id=1,Name="Name 1" },
           new Model {Id=2,Name="Name 2" },
           new Model {Id=3,Name="Name 3" },
           new Model {Id=4,Name="Name 4" },
           new Model {Id=5,Name="Name 5" },
           new Model {Id=6,Name="Name 6" }
        };
        SelectItemsCommand = new DelegateCommand<object[]>((items) =>
        {
            if (items != null && items.Count() > 0)
            {
                SelectedItems = items.Select(i => (Model)i);
            }
        });

    }



    public ICommand SelectItemsCommand { get; private set; }

    private IEnumerable<Model> _items;
    public IEnumerable<Model> Items
    {
        get { return _items; }
        set
        {
            _items = value; base.OnPropertyChanged("Items");
        }
    }


    private IEnumerable<Model> _selectedItems;
    public IEnumerable<Model> SelectedItems
    {
        get { return _selectedItems; }
        set
        {
            _selectedItems = value; base.OnPropertyChanged("SelectedItems");
        }
    }
    private Model _selectedItem;
    public Model SelectedItem
    {
        get { return _selectedItem; }
        set
        {
            _selectedItem = value; base.OnPropertyChanged("SelectedItem");
        }
    }
}

它应该有效,但它没有。当我在GUI中选择多个项目时:

enter image description here

查看型号代码只能识别一个项目:

enter image description here

我在布莱恩·拉古纳斯的"What's New in Prism 5.0"中看到了这个例子,据我所知,这项技术也可以用于多选。 我在这做错了什么?

2 个答案:

答案 0 :(得分:1)

SelectionChangedEventArgs.AddedItems 为您提供特定操作的选择列表。如果列表框SelectionMode"Multiple""Single",则不能单击一次选择多个项目。如果ListBox SelectionMode"Extended",则可以使用Shift键选择多个项目。

SelectionChangedEventArgs.AddedItems 不会为特定操作提供列表框中的所有选定项。

您的需要

在视图中,

TriggerParameterPath="AddedItems"更改为TriggerParameterPath="Source.SelectedItems"

在ViewModel中

DelegateCommand<object[]>更改为DelegateCommand<System.Collections.ICollection>

参考: http://frststart.blogspot.com/2016/10/selectionchangedselecteditemstutorial.html

答案 1 :(得分:0)

您一次选择一个项目,并且每次选择项目时都会调用该命令。

这是预期的行为。

如果要跟踪当前选定的项目,可以向IsSelected类添加Model属性,并使用ItemContainerStyle将此属性绑定到IsSelected ListBoxItem容器的属性:

<ListBox SelectedItem="{Binding SelectedItem}"
             ItemsSource="{Binding Items}"
             SelectionMode="Multiple">
    <i:Interaction.Triggers>
        <i:EventTrigger EventName="SelectionChanged">
            <prism:InvokeCommandAction Command="{Binding SelectItemsCommand}"
                                           TriggerParameterPath="AddedItems" />
        </i:EventTrigger>
    </i:Interaction.Triggers>
    <ListBox.ItemContainerStyle>
        <Style TargetType="ListBoxItem">
            <Setter Property="IsSelected" Value="{Binding IsSelected}" />
        </Style>
    </ListBox.ItemContainerStyle>
    <ListBox.ItemTemplate>
        <DataTemplate>
            <TextBlock Text="{Binding Name}" />
        </DataTemplate>
    </ListBox.ItemTemplate>
</ListBox>
SelectItemsCommand = new DelegateCommand<System.Collections.IList>((items) =>
{
    SelectedItems = Items.Where(x => x.IsSelected).ToList();
});