WPF-ContextMenu模板绑定数据失败;
一、原代码:
XAML:
<TreeView x:Name="trvwProjectList" Margin="0,0,0,0" VerticalAlignment="Stretch" VerticalContentAlignment="Stretch" BorderBrush="DarkGray" BorderThickness="0.7">
<TreeView.Resources>
<HierarchicalDataTemplate DataType="{x:Type vModelLocal:Project_TreeNodes}" ItemsSource="{Binding ChildNodes}">
<!-- MouseRightButtonDown="ProjectListMenu_MouseRightButtonDown" -->
<StackPanel Orientation="Horizontal" Tag="{Binding NodeName}" MouseLeftButtonDown="ProjectListMenu_MouseLeftButtonDown" VerticalAlignment="Stretch" Margin="0">
<Label Content="{Binding NodeName}" Tag="{Binding NodeID}" ToolTip="{Binding NodeDescribe}" Style="{DynamicResource LabelStyle1}" BorderThickness="0" VerticalContentAlignment="Top">
<!-- 右键菜单 -->
<Label.ContextMenu>
<ContextMenu StaysOpen="true" ItemsSource="{Binding Path = Menus}"/>
</Label.ContextMenu>
</Label>
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.Resources>
</TreeView>
C#:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
namespace ProjectViewModel
{
/// <summary>
/// Tree列表
/// </summary>
public class Project_TreeNodes
{
/// <summary>
/// 节点Id
/// </summary>
public int NodeID { get; set; }
/// <summary>
/// 节点名
/// </summary>
public string NodeName { get; set; } = string.Empty;
/// <summary>
/// 节点描述
/// </summary>
public string NodeDescribe { get; set; } = string.Empty;
/// <summary>
/// 父节点Id
/// </summary>
public int ParentID { get; set; }
/// <summary>
/// 图标
/// </summary>
public string Img { get; set; };
/// <summary>
/// 右键菜单
/// </summary>
public ContextMenu Menus=new();
/// <summary>
/// 子元素
/// </summary>
public List<Project_TreeNodes> ChildNodes { get; set; } = new();
}
public 页面代码(){
trvwProjectList.ItemsSource = new Project_TreeNodes(){...};
}
}
错误信息:“在类型为 Project_TreeNodes 的对象上找不到 Menus 属性。 ”
二、分析:
1、原因:
HierarchicalDataTemplate模板问题,ContextMenu可以放在TreeView中,用鼠标事件选择展开内容
2、修改方式一:
使用别人模板,但是不能对展开内容加以控制;连接:https://blog.51cto.com/u_15693505/5409852。
3、修改方式二:
XML:
<TreeView x:Name="trvwProjectList" MouseDown="TrvwProjectList_MouseDown" PreviewMouseRightButtonDown="TrvwProjectList_PreviewMouseRightButtonDown" Margin="0,0,0,0" VerticalAlignment="Stretch" VerticalContentAlignment="Stretch" BorderBrush="DarkGray" BorderThickness="0.7">
<TreeView.Resources>
<HierarchicalDataTemplate DataType="{x:Type vModelLocal:Project_TreeNodes}" ItemsSource="{Binding ChildNodes}">
<!-- MouseRightButtonDown="ProjectListMenu_MouseRightButtonDown" -->
<StackPanel Orientation="Horizontal" Tag="{Binding NodeName}" MouseLeftButtonDown="ProjectListMenu_MouseLeftButtonDown" VerticalAlignment="Stretch" Margin="0">
<Image Margin="0" Width="18" Height="16" Source="{Binding Img}"/>
<Label Content="{Binding NodeName}" Tag="{Binding NodeID}" ToolTip="{Binding NodeDescribe}" Style="{DynamicResource LabelStyle1}" BorderThickness="0" VerticalContentAlignment="Top"/>
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.Resources>
</TreeView>
C#:
/// <summary>
/// 右键菜单
/// </summary>
private void TrvwProjectList_PreviewMouseRightButtonDown(object sender, MouseButtonEventArgs e)
{
if (e.OriginalSource is DependencyObject source)
{
while (source != null && source.GetType() != typeof(StackPanel))
{
source = System.Windows.Media.VisualTreeHelper.GetParent(source);
} // 找到节点名
if (source is StackPanel item)
{
CreateContextMenu(item.Tag?.ToString() ?? string.Empty);
}
}
}
/// <summary>
/// 显示右键菜单
/// </summary>
/// <param name="positionItem">功能节点名</param>
private void CreateContextMenu(string nodeName)
{
trvwProjectList.ContextMenu = null;
ContextMenu contextMenu = new(); // 右键菜单对象
MenuItem menuItem = new();
MenuItem menuItem1 = new();
bool isDone = false; // 是否已处理
// 根节点
switch (nodeName)
{
case "菜单1":
menuItem = new();
menuItem.Header = "添加";
{
menuItem1 = new();
menuItem1.Header = "添加组";
menuItem1.Click += new RoutedEventHandler((sender, e) => { MessageBox.Show("添加了组"); });
menuItem.Items.Add(menuItem1);
menuItem1 = new();
menuItem1.Header = "添加文件";
menuItem1.Click += new RoutedEventHandler((sender, e) => { MessageBox.Show("添加了文件"); });
menuItem.Items.Add(menuItem1);
}
contextMenu.Items.Add(menuItem);
contextMenu.Items.Add(new Separator());
menuItem = new();
menuItem.Header = "剪切";
menuItem.Click += new RoutedEventHandler((sender, e) => { MessageBox.Show("剪切"); });
contextMenu.Items.Add(menuItem);
menuItem = new();
menuItem.Header = "复制";
menuItem.Click += new RoutedEventHandler((sender, e) => { MessageBox.Show("复制"); });
contextMenu.Items.Add(menuItem);
trvwProjectList.ContextMenu = contextMenu;
isDone = true;
break;
default:
break;
}
// 组节点名
if (isDone) { }
else if (nodeName.Contains("组"))
{
}
else
{
}
}
本文来自博客园,作者:꧁执笔小白꧂,转载请注明原文链接:https://www.cnblogs.com/qq2806933146xiaobai/p/17039678.html
分类:
.Net-WPF
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· SQL Server 2025 AI相关能力初探
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南