取消选择wpf树视图(MVVM)中的所选项目
本文关键字:选项 项目 MVVM wpf 选择 视图 取消 | 更新日期: 2023-09-27 18:27:01
我使用的是WPF树视图,当我选中一个节点''项目时,单击它。当用户第二次点击所选节点时,我希望取消选择该节点''项目,即我应该能够获得该事件。如果单击已选定的节点''项目,则不会调用IsSelected。我该如何让它工作?
<TreeView Grid.Column="0" Grid.Row="1" ItemsSource="{Binding source}" Name="mytreeview">
<TreeView.ItemContainerStyle>
<Style TargetType="{x:Type TreeViewItem}">
<Setter Property="IsExpanded" Value="{Binding IsExpanded, Mode=TwoWay}" />
<Setter Property="IsSelected" Value="{Binding IsSelected, Mode=TwoWay}" />
<Setter Property="FontWeight" Value="Normal" />
<Style.Triggers>
<Trigger Property="IsSelected" Value="True">
<Setter Property="FontWeight" Value="Bold" />
</Trigger>
</Style.Triggers>
</Style>
</TreeView.ItemContainerStyle>
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding Children}">
<TextBlock Text="{Binding displaytext}"/>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
</TreeView>
在我的视图模型中,我有
public bool IsSelected
{
get
{
return _isSelected;
}
set
{
if (value != _isSelected)
{
_isSelected = value;
if (_isSelected)
{
//my logic
}
this.OnPropertyChanged("IsSelected");
}
}
}
我知道这有点晚了,但我最近也有同样的要求(即在第二次单击时取消选择选定的TreeViewItem),我通过在TreeView的ItemContainerStyle的"Style"条目中声明"MouseLeftButtonUp"事件的事件处理程序来解决它,如下所示:
<TreeView.ItemContainerStyle>
<Style TargetType="{x:Type TreeViewItem}">
<EventSetter Event="MouseLeftButtonUp" Handler="TreeViewItem_MouseLeftButtonUp"/>
</Style>
</TreeView.ItemContainerStyle>
代码后面的事件处理程序如下:
private TreeViewItem prevTVI;
private void TreeViewItem_MouseLeftButtonUp(object sender, MouseButtonEventArgs e)
{
TreeViewItem tvi = (TreeViewItem)sender;
if (tvi == this.prevTVI)
{
this.prevTVI = null;
if (tvi.IsSelected)
tvi.IsSelected = false;
}
else
this.prevTVI = tvi;
e.Handled = true;
}
现在,我想问一下,是否有人认为这种方法打破了MVVM模式?我个人不这么认为,因为事件处理程序只关心视图及其对象,而不关心其他任何事情,但我想听听其他人的意见,尤其是如果有人有其他选择的话。
if (value != _isSelected)
假设UI甚至试图设置一些内容,那么这一行就阻塞了切换逻辑。像这样的东西至少可以修复那个部分。
set
{
if (value != _isSelected)
{
_isSelected = value;
this.OnPropertyChanged("IsSelected");
}
else if(_isSelected)
{
IsSelected = false;
}
}
否则,UI在设置值之前会检查选择,您需要通过其他一些用户交互来处理它,比如在单击时处理取消选择。
IsSelected属性只有在选择新项目时才会更改。在同一项目上单击两次通常不会产生任何效果。您需要在TreeView上注册MouseDown事件,然后在代码后面强制取消选择该项。