我正在使用WPF Toolkit的DataGrid。我已经启用了DataGrid上的属性以允许多行选择。我如何获得SelectedItems?我正在使用MVVM框架将我的ViewModel绑定到我的视图。WPF Toolkit DataGrid多选:如何获取SelectedItems?
谢谢!
我正在使用WPF Toolkit的DataGrid。我已经启用了DataGrid上的属性以允许多行选择。我如何获得SelectedItems?我正在使用MVVM框架将我的ViewModel绑定到我的视图。WPF Toolkit DataGrid多选:如何获取SelectedItems?
谢谢!
我一直在寻找这个问题的答案。我找到的答案是
1)在代码隐藏中将工作委托给ViewModel中的方法,从DataGrid传递SelectedItems
列表。该集合将包含所选的所有项目。
或者
2)使用MVVM工具包光,使您可以使用事件来指挥并直接传递一个对象作为参数传递给视图模型。
private void DataGrid_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
IList lst = this.myDataGrid.SelectedItems;
ViewModel.RowsSelected(lst);
}
在这种情况下,你需要绑定你在你的XAML SelectionChanged
您selectionchanged
在后面的代码。然后在你的代码后面,你可以保存这个列表,并用它来删除选定的行等。
如果有更好的方法来做到这一点,我很想知道是否是好的。
HTH
比尔
我设法使用命令中继比尔提到的来解决这个问题。这部分内容有点肮脏,但我避免将任何代码放在后面的文件中。首先,在你的XAML中 - 将你的命令绑定到一个按钮上,或者任何触发你的RelayCommand的东西。
<Button Content="Select"
cmd:ButtonBaseExtensions.Command="{Binding CommandSelect}"
cmd:ButtonBaseExtensions.CommandParameter="{Binding ElementName=Results, Path=SelectedItems}" />
您会注意到命令参数绑定到另一个UI元素 - 您希望获得所选项目的DataGrid或ListView。此语法将在Silverlight 3以及WPF中起作用,因为它现在支持元素到元素的绑定。
在您的视图模型的命令会是这个样子
Private _CommandSelect As RelayCommand(Of IEnumerable)
Public ReadOnly Property CommandSelect() As RelayCommand(Of IEnumerable)
Get
If _CommandSelect Is Nothing Then
_CommandSelect = New RelayCommand(Of IEnumerable)(AddressOf CommandSelectExecuted, AddressOf CommandSelectCanExecute)
End If
Return _CommandSelect
End Get
End Property
Private Function CommandSelectExecuted(ByVal parameter As IEnumerable) As Boolean
For Each Item As IElectoralAreaNode In parameter
Next
Return True
End Function
Private Function CommandSelectCanExecute() As Boolean
Return True
End Function
选定的项目将返回一个SelectedItemCollection,但你可能不希望此扶养您的视图模型。因此,将它作为IEnumerable键入并做一点点投射是你唯一的选择,而不是“肮脏”。但它使您的代码保持清洁和MVVM模式!
考虑到比尔的答案,合并选项1和2,添加一个附加属性作为替代书写代码隐藏的泛滥,我想出了一个行为。
首先,我们具有以下行为:
Public Class SelectedItemsBehavior
Public Shared ReadOnly SelectedItemsChangedHandlerProperty As DependencyProperty =
DependencyProperty.RegisterAttached("SelectedItemsChangedHandler",
GetType(mvvm.RelayCommand), GetType(SelectedItemsBehavior),
New FrameworkPropertyMetadata(New PropertyChangedCallback(AddressOf OnSelectedItemsChangedHandlerChanged)))
Public Shared Function GetSelectedItemsChangedHandler(ByVal element As DependencyObject) As mvvm.RelayCommand
If element Is Nothing Then Throw New ArgumentNullException("element")
Return element.GetValue(SelectedItemsChangedHandlerProperty)
End Function
Public Shared Sub SetSelectedItemsChangedHandler(ByVal element As DependencyObject, ByVal value As mvvm.RelayCommand)
If element Is Nothing Then Throw New ArgumentNullException("element")
element.SetValue(SelectedItemsChangedHandlerProperty, value)
End Sub
Private Shared Sub OnSelectedItemsChangedHandlerChanged(d As DependencyObject,
e As DependencyPropertyChangedEventArgs)
Dim dataGrid As DataGrid = DirectCast(d, DataGrid)
If e.OldValue Is Nothing AndAlso e.NewValue IsNot Nothing Then
AddHandler dataGrid.SelectionChanged, AddressOf ItemsControl_SelectionChanged
End If
If e.OldValue IsNot Nothing AndAlso e.NewValue Is Nothing Then
RemoveHandler dataGrid.SelectionChanged, AddressOf ItemsControl_SelectionChanged
End If
End Sub
Public Shared Sub ItemsControl_SelectionChanged(sender As Object,
e As SelectionChangedEventArgs)
Dim dataGrid As DataGrid = DirectCast(sender, DataGrid)
Dim itemsChangedHandler As RelayCommand = GetSelectedItemsChangedHandler(dataGrid)
itemsChangedHandler.Execute(dataGrid.SelectedItems)
End Sub
End Class
C#:
using Microsoft.VisualBasic;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Data;
using System.Diagnostics;
public class SelectedItemsBehavior
{
public static readonly DependencyProperty SelectedItemsChangedHandlerProperty = DependencyProperty.RegisterAttached("SelectedItemsChangedHandler", typeof(mvvm.RelayCommand), typeof(SelectedItemsBehavior), new FrameworkPropertyMetadata(new PropertyChangedCallback(OnSelectedItemsChangedHandlerChanged)));
public static mvvm.RelayCommand GetSelectedItemsChangedHandler(DependencyObject element)
{
if (element == null)
throw new ArgumentNullException("element");
return element.GetValue(SelectedItemsChangedHandlerProperty);
}
public static void SetSelectedItemsChangedHandler(DependencyObject element, mvvm.RelayCommand value)
{
if (element == null)
throw new ArgumentNullException("element");
element.SetValue(SelectedItemsChangedHandlerProperty, value);
}
private static void OnSelectedItemsChangedHandlerChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
DataGrid dataGrid = (DataGrid)d;
if (e.OldValue == null && e.NewValue != null) {
dataGrid.SelectionChanged += ItemsControl_SelectionChanged;
}
if (e.OldValue != null && e.NewValue == null) {
dataGrid.SelectionChanged -= ItemsControl_SelectionChanged;
}
}
public static void ItemsControl_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
DataGrid dataGrid = (DataGrid)sender;
RelayCommand itemsChangedHandler = GetSelectedItemsChangedHandler(dataGrid);
itemsChangedHandler.Execute(dataGrid.SelectedItems);
}
}
然后我们把它添加到数据网格在XAML:
<DataGrid AutoGenerateColumns="False" FontFamily="Tahoma" FontSize="9"
ItemsSource="{Binding Path=ResultsVM}"
mvvm:SelectedItemsBehavior.SelectedItemsChangedHandler="{Binding Path=ResultsSelectionChangedCommand}" />
然后我们在代码中RelayCommand ViewModel:
Public ReadOnly Property ResultsSelectionChangedCommand() As mvvm.RelayCommand
Get
If _resultsSelectionChangedCommand Is Nothing Then
_resultsSelectionChangedCommand = New mvvm.RelayCommand(AddressOf ResultsSelectionChanged)
End If
Return _resultsSelectionChangedCommand
End Get
End Property
Public Sub ResultsSelectionChanged(ByVal selectedItems As Object)
_resultsSelectedItems.Clear()
For Each item In selectedItems
_resultsSelectedItems.Add(item)
Next
End Sub
C#:
public mvvm.RelayCommand ResultsSelectionChangedCommand {
get {
if (_resultsSelectionChangedCommand == null) {
_resultsSelectionChangedCommand = new mvvm.RelayCommand(ResultsSelectionChanged);
}
return _resultsSelectionChangedCommand;
}
}
public void ResultsSelectionChanged(object selectedItems)
{
_resultsSelectedItems.Clear();
foreach (item in selectedItems) {
_resultsSelectedItems.Add(item);
}
}
的_resultsSelectedItems简直是在DataGrid中显示的项目清单:
Private _resultsSelectedItems As New List(Of WorkOrderMatchViewModel)
C#:
private List<WorkOrderMatchViewModel> _resultsSelectedItems = new List<WorkOrderMatchViewModel>();
希望这有助于有点同时使用的Bill的方法无需参考MVVM-Light。
C#版本SelectedItemsBehavior类。可能会帮助某人。
public static class SelectedItemsBehavior
{
public static readonly DependencyProperty SelectedItemsChangedHandlerProperty =
DependencyProperty.RegisterAttached("SelectedItemsChangedHandler",
typeof(RelayCommand),
typeof(SelectedItemsBehavior),
new FrameworkPropertyMetadata(new PropertyChangedCallback(OnSelectedItemsChangedHandlerChanged)));
public static RelayCommand GetSelectedItemsChangedHandler(DependencyObject element)
{
if (element == null)
{
throw new ArgumentNullException("element");
}
return element.GetValue(SelectedItemsChangedHandlerProperty) as RelayCommand;
}
public static void SetSelectedItemsChangedHandler(DependencyObject element, RelayCommand value)
{
if (element == null)
{
throw new ArgumentNullException("element");
}
element.SetValue(SelectedItemsChangedHandlerProperty, value);
}
public static void OnSelectedItemsChangedHandlerChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
DataGrid dataGrid = (DataGrid)d;
if (e.OldValue == null && e.NewValue != null)
{
dataGrid.SelectionChanged += new SelectionChangedEventHandler(ItemsControl_SelectionChanged);
}
if (e.OldValue != null && e.NewValue == null)
{
dataGrid.SelectionChanged -= new SelectionChangedEventHandler(ItemsControl_SelectionChanged);
}
}
public static void ItemsControl_SelectionChanged(Object sender, SelectionChangedEventArgs e)
{
DataGrid dataGrid = (DataGrid)sender;
RelayCommand itemsChangedHandler = GetSelectedItemsChangedHandler(dataGrid);
itemsChangedHandler.Execute(dataGrid.SelectedItems);
}
}
通过http://stackoverflow.com/a/2615487/284795 – 2012-11-21 14:49:23