为什么 ToolStripMenuItem.Click 个事件处理程序显示相同的内容?
Why ToolStripMenuItem.Click event handlers show the same content?
我有一个树视图,其中有一个名为 "FTPServerListNode" 的节点。
"FTPServerListNode"有2个FTPServerNode,1个是"serverId1",另外1个是"serverId2"。
FTPServerListNode 和 FTPServerNode 都是从 TreeNode 扩展而来。
每个子节点都有一个 ToolStripMenuItem。
每个 ToolStripMenuItem 都有自己的点击事件处理程序。
这 2 个点击事件处理程序只显示节点名称。
但是,我发现两个事件处理程序显示相同的内容(即 "serverId2")。
这是我的源代码。
using System;
using System.Windows.Forms;
namespace ToolStripMenuItemTest
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
treeView1.Nodes.Add(new FtpServerListNode());
}
}
internal class FtpServerNode : TreeNode
{
internal FtpServerNode(string serverDesc, string serverId)
{
this.Text = serverDesc;
this.Name = serverId;
}
}
internal class FtpServerListNode : TreeNode
{
internal FtpServerListNode()
{
FtpServerNode ftpServerNode = new FtpServerNode("serverDesc1", "serverId1");
var nN= ftpServerNode.Name;
ToolStripMenuItem removeServerToolStrip = new ToolStripMenuItem();
removeServerToolStrip.Text = "Remove This FTP Server";
removeServerToolStrip.Click += (sender, e) => MessageBox.Show(nN);
ftpServerNode.ContextMenuStrip = new ContextMenuStrip();
ftpServerNode.ContextMenuStrip.Items.Add(removeServerToolStrip);
this.Nodes.Add(ftpServerNode);
ftpServerNode = new FtpServerNode("serverDesc2", "serverId2");
nN= ftpServerNode.Name;
removeServerToolStrip = new ToolStripMenuItem();
removeServerToolStrip.Text = "Remove This FTP Server";
removeServerToolStrip.Click += (sender, e) => MessageBox.Show(nN);
ftpServerNode.ContextMenuStrip = new ContextMenuStrip();
ftpServerNode.ContextMenuStrip.Items.Add(removeServerToolStrip);
this.Nodes.Add(ftpServerNode);
this.Text = "Root Node";
this.Expand();
}
}
}
我附上我的项目屏幕供您参考。
请将您的事件处理程序更改为
var mName = ftpServerNode.Name;
removeServerToolStrip.Click += (sender, e) => MessageBox.Show(mName);
您 运行 陷入修改闭包问题:
https://www.jetbrains.com/help/resharper/AccessToModifiedClosure.html
经过多次试验,以下代码有效:
internal class FtpServerListNode : TreeNode
{
internal FtpServerListNode()
{
SortedDictionary<string, FtpServerNode> ftpServerList = new SortedDictionary<string, FtpServerNode>();
FtpServerNode ftpServerNode = new FtpServerNode("serverDesc1", "serverId1");
ftpServerList.Add("serverId1", ftpServerNode);
ftpServerNode = new FtpServerNode("serverDesc2", "serverId2");
ftpServerList.Add("serverId2", ftpServerNode);
foreach (FtpServerNode fn in ftpServerList.Values)
{
ToolStripMenuItem removeServerToolStrip = new ToolStripMenuItem();
removeServerToolStrip.Text = "Remove This FTP Server " + fn.Name;
removeServerToolStrip.Click += (sender, e) => MessageBox.Show(fn.Name);
fn.ContextMenuStrip = new ContextMenuStrip();
fn.ContextMenuStrip.Items.Add(removeServerToolStrip);
this.Nodes.Add(fn);
}
this.Text = "Root Node";
this.Expand();
}
}
我有一个树视图,其中有一个名为 "FTPServerListNode" 的节点。
"FTPServerListNode"有2个FTPServerNode,1个是"serverId1",另外1个是"serverId2"。
FTPServerListNode 和 FTPServerNode 都是从 TreeNode 扩展而来。
每个子节点都有一个 ToolStripMenuItem。
每个 ToolStripMenuItem 都有自己的点击事件处理程序。
这 2 个点击事件处理程序只显示节点名称。
但是,我发现两个事件处理程序显示相同的内容(即 "serverId2")。
这是我的源代码。
using System;
using System.Windows.Forms;
namespace ToolStripMenuItemTest
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
treeView1.Nodes.Add(new FtpServerListNode());
}
}
internal class FtpServerNode : TreeNode
{
internal FtpServerNode(string serverDesc, string serverId)
{
this.Text = serverDesc;
this.Name = serverId;
}
}
internal class FtpServerListNode : TreeNode
{
internal FtpServerListNode()
{
FtpServerNode ftpServerNode = new FtpServerNode("serverDesc1", "serverId1");
var nN= ftpServerNode.Name;
ToolStripMenuItem removeServerToolStrip = new ToolStripMenuItem();
removeServerToolStrip.Text = "Remove This FTP Server";
removeServerToolStrip.Click += (sender, e) => MessageBox.Show(nN);
ftpServerNode.ContextMenuStrip = new ContextMenuStrip();
ftpServerNode.ContextMenuStrip.Items.Add(removeServerToolStrip);
this.Nodes.Add(ftpServerNode);
ftpServerNode = new FtpServerNode("serverDesc2", "serverId2");
nN= ftpServerNode.Name;
removeServerToolStrip = new ToolStripMenuItem();
removeServerToolStrip.Text = "Remove This FTP Server";
removeServerToolStrip.Click += (sender, e) => MessageBox.Show(nN);
ftpServerNode.ContextMenuStrip = new ContextMenuStrip();
ftpServerNode.ContextMenuStrip.Items.Add(removeServerToolStrip);
this.Nodes.Add(ftpServerNode);
this.Text = "Root Node";
this.Expand();
}
}
}
我附上我的项目屏幕供您参考。
请将您的事件处理程序更改为
var mName = ftpServerNode.Name;
removeServerToolStrip.Click += (sender, e) => MessageBox.Show(mName);
您 运行 陷入修改闭包问题: https://www.jetbrains.com/help/resharper/AccessToModifiedClosure.html
经过多次试验,以下代码有效:
internal class FtpServerListNode : TreeNode
{
internal FtpServerListNode()
{
SortedDictionary<string, FtpServerNode> ftpServerList = new SortedDictionary<string, FtpServerNode>();
FtpServerNode ftpServerNode = new FtpServerNode("serverDesc1", "serverId1");
ftpServerList.Add("serverId1", ftpServerNode);
ftpServerNode = new FtpServerNode("serverDesc2", "serverId2");
ftpServerList.Add("serverId2", ftpServerNode);
foreach (FtpServerNode fn in ftpServerList.Values)
{
ToolStripMenuItem removeServerToolStrip = new ToolStripMenuItem();
removeServerToolStrip.Text = "Remove This FTP Server " + fn.Name;
removeServerToolStrip.Click += (sender, e) => MessageBox.Show(fn.Name);
fn.ContextMenuStrip = new ContextMenuStrip();
fn.ContextMenuStrip.Items.Add(removeServerToolStrip);
this.Nodes.Add(fn);
}
this.Text = "Root Node";
this.Expand();
}
}