在 Xaml 中将 TreeView 与 ContextMenu 绑定

发布于 2024-08-26 07:49:18 字数 1203 浏览 5 评论 0原文

我对 Xaml 还很陌生,需要一些建议。

TreeView 应绑定到分层对象结构。 TreeView 应该有一个上下文菜单,该菜单特定于每种对象类型。

我尝试过以下方法:

<TreeView>
  <TreeView.Resources>
    <DataTemplate x:Key="RoomTemplate">
      <TreeViewItem Header="{Binding Name}">
        <TreeViewItem.ContextMenu>
          <ContextMenu>
            <MenuItem Header="Open" />
            <MenuItem Header="Remove" />
          </ContextMenu>
        </TreeViewItem.ContextMenu>
      </TreeViewItem>
    </DataTemplate>
  </TreeView.Resources>

  <TreeViewItem Header="{Binding Name}" Name="tviRoot" IsExpanded="True" >

  <TreeViewItem Header="Rooms"  
                ItemsSource="{Binding Rooms}"
                ItemTemplate="{StaticResource RoomTemplate}">
    <TreeViewItem.ContextMenu>
      <ContextMenu>
        <MenuItem Header="Add room"></MenuItem>
      </ContextMenu>
    </TreeViewItem.ContextMenu>
  </TreeViewItem>
</TreeViewItem>

但通过此标记,行为符合预期,但子项目(房间)缩进太多。

无论如何,我能找到的所有合并示例都在 DataTemplate 中使用 TextBlock 而不是 TreeViewItem,但想知道如何在那里集成 ContextMenu。

I'm pretty new to Xaml and need some advise.

A TreeView should be bound to a hierarchical object structure. The TreeView should have a context menu, which is specific for each object type.

I've tried the following:

<TreeView>
  <TreeView.Resources>
    <DataTemplate x:Key="RoomTemplate">
      <TreeViewItem Header="{Binding Name}">
        <TreeViewItem.ContextMenu>
          <ContextMenu>
            <MenuItem Header="Open" />
            <MenuItem Header="Remove" />
          </ContextMenu>
        </TreeViewItem.ContextMenu>
      </TreeViewItem>
    </DataTemplate>
  </TreeView.Resources>

  <TreeViewItem Header="{Binding Name}" Name="tviRoot" IsExpanded="True" >

  <TreeViewItem Header="Rooms"  
                ItemsSource="{Binding Rooms}"
                ItemTemplate="{StaticResource RoomTemplate}">
    <TreeViewItem.ContextMenu>
      <ContextMenu>
        <MenuItem Header="Add room"></MenuItem>
      </ContextMenu>
    </TreeViewItem.ContextMenu>
  </TreeViewItem>
</TreeViewItem>

But with this markup the behavior is as intended, but the child items (the rooms) are indented too much.

Anyway all the bining samples I could find use TextBlock instead of TreeViewItem in the DataTemplate, but wonder how to integrate the ContextMenu there.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

岁月流歌 2024-09-02 07:49:18

您通常不会创建包含 TreeViewItem 的 DataTemplate,因为绑定基础结构将为您创建 TreeViewItem - 您的 DataTemplate 需要做的就是指定应显示为 TreeViewItem 的内容。这就是您找到的示例在 DataTemplate 中使用 TextBlocks 而不是 TreeViewItems 的原因。

我怀疑使用 TreeViewItem 而不是 TextBlock 会导致过度缩进,因为您的 DataTemplate 中有一个(手动创建的)TreeViewItem(会产生一级缩进),而另一个(自动)TreeViewItem (会产生另一级缩进)。因此,使用 TextBlock 而不是 TreeViewItem 应该可以解决这个问题。集成 ContextMenu 应该不是问题,因为 TextBlock 也有 ContextMenu 属性。

因此,您应该能够按如下方式更改 DataTemplate:

<DataTemplate x:Key="RoomTemplate">
  <TextBlock Text="{Binding Name}">
    <TextBlock.ContextMenu>
      <ContextMenu>
        <MenuItem Header="Open" />
        <MenuItem Header="Remove" />
      </ContextMenu>
    </TextBlock.ContextMenu>
  </TextBlock>
</DataTemplate>

顺便说一句,对于 TreeViews,通常使用 HierarchicalDataTemplate 而不是普通 DataTemplate,因为这允许通过 HierarchicalDataTemplate.ItemsSource 属性实现多个级别的项目。不过,在您的场景中可能不需要这样做。

You would not normally create a DataTemplate containing a TreeViewItem, because the binding infrastructure will be creating the TreeViewItem for you -- all your DataTemplate needs to do is specify what should be displayed as the content of the TreeViewItem. That's why the samples you've found use TextBlocks instead of TreeViewItems in the DataTemplate.

I suspect the use of TreeViewItem rather than TextBlock causes the excessive indenting because you have a (manually created) TreeViewItem in your DataTemplate (which incurs one level of indent) inside another (automatic) TreeViewItem (which incurs another level of indent). Therefore, using a TextBlock instead of a TreeViewItem should cure this. Integrating the ContextMenu shouldn't be an issue because TextBlock has a ContextMenu property too.

So you should be able to just change your DataTemplate as follows:

<DataTemplate x:Key="RoomTemplate">
  <TextBlock Text="{Binding Name}">
    <TextBlock.ContextMenu>
      <ContextMenu>
        <MenuItem Header="Open" />
        <MenuItem Header="Remove" />
      </ContextMenu>
    </TextBlock.ContextMenu>
  </TextBlock>
</DataTemplate>

Incidentally for TreeViews it is common to use a HierarchicalDataTemplate rather than a plain DataTemplate because this allows for multiple levels of items via the HierarchicalDataTemplate.ItemsSource property. This may not be required in your scenario though.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文