首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >KeyBinding in HierarchicalDataTemplate of TreeView

KeyBinding in HierarchicalDataTemplate of TreeView
EN

Stack Overflow用户
提问于 2016-04-26 12:38:51
回答 2查看 714关注 0票数 2

我有一个TreeView。我想通过单击EditLeafCommand F2来启用。

模型:

代码语言:javascript
复制
public class Leaf
{
    public string LeafName { get; set; }
    public bool HasChildren { get; set; }        
}

窗口的ViewModel:

代码语言:javascript
复制
public MainWindowViewModel{

  public ReadOnlyCollection<LeafViewModel> Leafs
  {
        get { return leafs; }
  }
}

ViewModel of TreeView:

代码语言:javascript
复制
public class LeafViewModel : TreeViewItemViewModel
{
    public ObservableCollection<TreeViewItemViewModel> Children
    {
        get { return _children; }
    }
    public string LeafName { get; set; }   
    public RelayCommand EditLeafCommand { get; set; }     

}

XAML:

代码语言:javascript
复制
<TreeView  ItemsSource="{Binding Leafs}">               
   <TreeView.InputBindings>
      <KeyBinding Key="F2" Command="{Binding SelectedItem.EditLeafCommand, 
                           diag:PresentationTraceSources.TraceLevel=High}"/>
   </TreeView.InputBindings>
   <TreeView.Resources>
      <HierarchicalDataTemplate DataType="{x:Type vm:LeafViewModel}" 
                                     ItemsSource="{Binding Children}">
         <StackPanel Orientation="Horizontal">               
            <TextBox Text="{Binding LeafName}" IsReadOnly="{Binding IsReadOnlyItem}" 
            Tag="{Binding DataContext, RelativeSource={RelativeSource Self}}">
               <TextBox.ContextMenu>
                  <ContextMenu DataContext="{Binding PlacementTarget.Tag, RelativeSource={RelativeSource Self}}">
                     <MenuItem Command="{Binding EditLeafCommand}" CommandParameter="{Binding ALeaf}" Header="Edit" />
                  </ContextMenu>
               </TextBox.ContextMenu>
            </TextBox>
         </StackPanel>
      </HierarchicalDataTemplate>
   </TreeView.Resources>
</TreeView>

输出窗口

System.Windows.Data警告: 56 :创建绑定的BindingExpression (hash=2683661) (hash=47044325) System.Windows.Data警告: 58 :路径:'EditLeafCommand‘ System.Windows.Data警告: 60 : BindingExpression (hash=2683661):默认模式解析为OneWay System.Windows.Data警告: 61 : BindingExpression (hash=2683661):默认更新触发器解析为PropertyChanged System.Windows.Data警告: 62 : BindingExpression (hash=2683661):附加到System.Windows.Input.KeyBinding.Command (hash=29578451) System.Windows.Data警告: 64 : BindingExpression (hash=2683661):Use System.Windows.Data警告: 67 : BindingExpression (hash=2683661):解析源 System.Windows.Data警告: 69 : BindingExpression (hash=2683661):找不到框架导师 System.Windows.Data警告: 65 : BindingExpression (hash=2683661):解决延迟源 System.Windows.Data警告: 95 : BindingExpression (hash=2683661):Got KeyBinding (hash=29578451) System.Windows.Data警告: 67 : BindingExpression (hash=2683661):解析源 System.Windows.Data警告: 70 : BindingExpression (hash=2683661):Found元素: TreeView (hash=11903911) (确定) System.Windows.Data警告: 78 : BindingExpression (hash=2683661):使用根项MainWindowViewModel (hash=44115416)激活 System.Windows.Data警告: 108 : BindingExpression (hash=2683661):在0级-对于MainWindowViewModel.EditLeafCommand找到访问器 System.Windows.Data错误: 40 : BindingExpression路径错误:在'object‘MainWindowViewModel’(HashCode=44115416)‘上找不到'EditLeafCommand’属性。BindingExpression:Path=EditLeafCommand;DataItem='MainWindowViewModel‘(HashCode=44115416);目标元素为'KeyBinding’(HashCode=29578451);目标属性为'Command‘(键入'ICommand') System.Windows.Data警告: 80 : BindingExpression (hash=2683661):TransferValue -获取原始值{DependencyProperty.UnsetValue} System.Windows.Data警告: 88 : BindingExpression (hash=2683661):TransferValue -使用回退/默认值 System.Windows.Data警告: 89 : BindingExpression (hash=2683661):TransferValue -使用最后值

我看到了这篇文章,这是同一个问题,然而,被接受的答案没有任何代码(我试图通过链接,然而,提供的方法并没有帮助我)

错误说:

System.Windows.Data错误: 40 :BindingExpression错误:在“object”‘MainWindowViewModel’上找不到'EditLeafCommand‘属性

但是我怎样才能直接到EditLeadViewModel

如何从EditLeafCommand LeafViewModel 调用并发送参数?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2016-04-28 06:55:35

安迪ONeill已经解决了这个问题。我真的为他的解决方案感到兴奋:)。我急于与大家分享这个解决方案:

绑定到LeafViewModel中的命令

代码语言:javascript
复制
<TreeView  ItemsSource="{Binding Leafs}" Name="tv">
   <TreeView.Resources>
      <HierarchicalDataTemplate DataType="{x:Type local:LeafViewModel}" 
                                      ItemsSource="{Binding Children}">
         <StackPanel Orientation="Horizontal">
            <Label VerticalAlignment="Center" FontFamily="WingDings" Content="1"/>
               <TextBox Text="{Binding LeafName}" Tag="{Binding DataContext, 
                  RelativeSource={RelativeSource Self}}" Background="Transparent">
                  <TextBox.ContextMenu>
                     <ContextMenu DataContext="{Binding PlacementTarget.Tag, 
                                     RelativeSource={RelativeSource Self}}">
                        <MenuItem Command="{Binding EditLeafCommand}" 
                         CommandParameter="{Binding ALeaf}" Header="Edit" />
                     </ContextMenu>
                  </TextBox.ContextMenu>
               </TextBox>
            </StackPanel>
         </HierarchicalDataTemplate>
      </TreeView.Resources>
    <TreeView.InputBindings>
    <KeyBinding Key="F2" Command="{Binding SelectedItem.EditLeafCommand, ElementName=tv}"/>
    </TreeView.InputBindings>
</TreeView>
票数 0
EN

Stack Overflow用户

发布于 2016-04-27 10:57:45

您的MainViewModel没有SelectedItem属性。您需要将此属性添加到视图模型中,并确保在该属性更改时触发INotifyPropertyChanged.PropertyChanged事件。

每当树视图的选定项发生更改时,还需要更新此属性。有多种方法可以做到这一点。一种方法是使用Nuget包System.Windows.Interactivity.WPF。您必须添加名称空间声明:

代码语言:javascript
复制
xmlns:i="clr-namespace:System.Windows.Interactivity;assembly=System.Windows.Interactivity"

然后,在树视图XAML元素中添加以下内容(我只显示要添加什么--将XAML的其余部分保留在TreeView元素中):

代码语言:javascript
复制
<TreeView Name="treeView" ItemsSource="{Binding Leafs}">
  <i:Interaction.Triggers>
    <i:EventTrigger EventName="SelectedItemChanged">
      <i:InvokeCommandAction Command="{Binding SetSelectedItemCommand, PresentationTraceSources.TraceLevel=High}" CommandParameter="{Binding SelectedItem, ElementName=treeView}" />
    </i:EventTrigger>
  </i:Interaction.Triggers>
</TreeView>

注意,TreeView元素有一个名称(treeView),用于InvokeCommandAction元素中的CommandParameter绑定。

另外,请注意,您必须在MainViewModel上添加一个MainViewModel。这个命令应该设置我在第一段中描述的SelectedItem属性。下面是一些使用泛型RelayCommand的代码片段

代码语言:javascript
复制
class MainWindowViewModel {

  TreeViewItemViewModel selectedItem;

  public MainWindowViewModel() {
    SetSelectedItemCommand = new RelayCommand<TreeViewItemViewModel>(SetSelectedItem);
  }

  public TreeViewItemViewModel SelectedItem {
    get { return selectedItem; }
    set {
      selectedItem = value;
      OnPropertyChanged();
    }
  }

  void SetSelectedItem(TreeViewItemViewModel viewModel) {
    SelectedItem = viewModel;
  }

}

这是使您的键绑定到SelectedItem.EditLeafCommand工作所需的基本内容。然而,你还有另一个问题。HierarchicalDataTemplate将树节点定义为TextBox。单击TextBox时,没有向TreeView发出任何单击,并且所选内容不会更改。我的建议是使用每个树节点(例如TextBlock)的非交互式表示。然后,当调用EditLeafCommand时,在顶部放置一个TextBox,允许用户编辑节点。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/36865204

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档