EnL*_*cha 5 .net wpf xaml listview mvvm
我有一个绑定到ObservableCollection的ListView ItemsSource.我通过MVVM添加了一个属性来跟踪ListView.SelectedItem.我的ListView中添加了一个按钮(通过GridViewColumn.CellTemplate)来创建一个按钮命令,该命令显示有关我的ObservableCollection中每个对象的数据.因此,我的ObservableCollection(ListView列1)中的对象列表显示在ListView中,带有相应的按钮(ListView列2).
守则很棒!唯一的问题是:在单击列表中的相应按钮之前,用户必须单击ListView行.(如果用户单击按钮而不先单击ListView行,我的"SelectedFromQueue"属性会出现空引用异常.)
我想添加代码,单击按钮时设置ListView.SelectedItem属性.因此,如果用户单击按钮,则代码应在执行关联的MVVM命令之前更新ListView.SelectedItem属性绑定.
有人有任何示例代码吗?谢谢你的帮助.
我的XAML:
<UserControl xmlns:local="clr-namespace:MyApp"
x:Class="MyApp.QueueObjectList"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
mc:Ignorable="d" Height="290" Width="320">
<Grid Width="319">
<GroupBox Header="Queue Class List" HorizontalAlignment="Left" Width="319" BorderBrush="Black" BorderThickness="2">
<ListView ItemsSource="{Binding Path=QueueList}" Name="QueueListView">
<ListView.SelectedItem>
<Binding Path="SelectedFromQueue" Mode="TwoWay" UpdateSourceTrigger="PropertyChanged">
</Binding>
</ListView.SelectedItem>
<ListView.View>
<GridView>
<GridViewColumn Width="140" Header="Queue Name" DisplayMemberBinding="{Binding Name}" />
<GridViewColumn Width="179" Header="Property Information">
<GridViewColumn.CellTemplate>
<DataTemplate>
<Button Content="Get Property Info" Command="{Binding Path=GetQueueObjProperties}"
DataContext="{Binding DataContext, RelativeSource={RelativeSource FindAncestor, AncestorType=ListView}}" />
</DataTemplate>
</GridViewColumn.CellTemplate>
</GridViewColumn>
</GridView>
</ListView.View>
</ListView>
</GroupBox>
</Grid>
</UserControl>
Run Code Online (Sandbox Code Playgroud)
我的MainWindowViewModel C#代码:
private ObservableCollection<Queue> _QueueList;
private Queue _selectedFromQueue;
public ObservableCollection<Queue> QueueList
{
get { return _QueueList; }
set
{
_QueueList = value;
RaisePropertyChanged("QueueList");
}
}
public Queue SelectedFromQueue
{
get { return _selectedFromQueue; }
set
{
_selectedFromQueue= value;
RaisePropertyChanged("SelectedFromQueue");
}
}
// Constructor
public MainWindowViewModel()
{
QueueList = new ObservableCollection<Queue>();
_selectedFromQueue= null;
}
public ICommand GetQueueObjProperties
{
get { return new RelayCommand(GetQueueProperties, CanGetQueueProperties); }
}
private bool CanGetQueueProperties()
{
if (_QueueList.Count > 0)
{
return true;
}
return false;
}
private void GetQueueProperties()
{
if (CanGetQueueProperties())
{
ResponseMessage.Add("Queue name: " +SelectedFromQueue.Name);
}
}
Run Code Online (Sandbox Code Playgroud)
更新:谢谢你!
我在XAML代码中添加了以下内容:
<ListView.Resources>
<Style TargetType="{x:Type ListViewItem}">
<EventSetter Event="PreviewGotKeyboardFocus" Handler="SelectCurrentItem"/>
</Style>
</ListView.Resources>
Run Code Online (Sandbox Code Playgroud)
我在后面的代码中添加了以下c#方法:
protected void SelectCurrentItem(Object sender, KeyboardFocusChangedEventArgs e)
{
ListViewItem item = (ListViewItem)sender;
item.IsSelected = true;
}
Run Code Online (Sandbox Code Playgroud)
效果很好!再次感谢参考sll!
我不确定它的GetQueueProperties作用是什么,但听起来您用来SelectedFromQueue
知道在哪个项目上执行您的逻辑,而 GUI 中的选择是次要的。
如果是这种情况,请不要使用SelectedFromQueue,而是将其添加到Button:
CommandParameter="{Binding DataContext, RelativeSource={RelativeSource FindAncestor, AncestorType=ListViewItem}}"
Run Code Online (Sandbox Code Playgroud)
这将为您提供一个Queue与按下的按钮所在行关联的对象,如图e.Parameter所示SelectedFromQueue。
如果您确实需要为 GUI 设置所选项目,请在开始时SelectedFromQueue添加:
SelectedFromQueue = (e.Parameter is Queue) ? e.Parameter : null
Run Code Online (Sandbox Code Playgroud)