C# TabControl 上下文菜单
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/457677/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
TabControl Context Menu
提问by blu
In a Windows Forms app I set the ContextMenuStrip property on a TabControl.
在 Windows 窗体应用程序中,我在 TabControl 上设置了 ContextMenuStrip 属性。
- How can I tell the user clicked a tab other then the one that is currently selected?
- How can I restrict the context menu from showing only when the top Tab portion with the label is clicked, and not elsewhere in the tab?
- 如何告诉用户单击了当前选择的选项卡之外的选项卡?
- 如何限制上下文菜单仅在单击带有标签的顶部 Tab 部分时显示,而不是在选项卡中的其他地方显示?
采纳答案by BFree
Don't bother setting the contextMenuStrip property on the TabControl. Rather do it this way. Hook up to the tabControl's MouseClick event, and then manually show the context menu. This will only fire if the tab itself on top is clicked on, not the actual page. If you click on the page, then the tabControl doesn't receive the click event, the TabPage does. Some code:
不要费心在 TabControl 上设置 contextMenuStrip 属性。不如这样做。连接到 tabControl 的 MouseClick 事件,然后手动显示上下文菜单。这只会在点击顶部的选项卡本身而不是实际页面时触发。如果您单击页面,则 tabControl 不会收到单击事件,而 TabPage 会收到。一些代码:
public Form1()
{
InitializeComponent();
this.tabControl1.MouseClick += new MouseEventHandler(tabControl1_MouseClick);
}
private void tabControl1_MouseClick(object sender, MouseEventArgs e)
{
if (e.Button == MouseButtons.Right)
{
this.contextMenuStrip1.Show(this.tabControl1, e.Location);
}
}
回答by AJ_
A bit late, but I've found a solution for the first part of your question. You can figure out which tab was right-clicked on by sending a left mouse click to the application. This selects the tab, so now you can use the TabControl.SelectedTab property to get the tab that the user right-clicked on.
有点晚了,但我已经找到了您问题第一部分的解决方案。您可以通过向应用程序发送鼠标左键单击来确定哪个选项卡被右键单击。这将选择选项卡,因此现在您可以使用 TabControl.SelectedTab 属性来获取用户右键单击的选项卡。
[DllImport("user32.dll", CharSet = CharSet.Auto, CallingConvention = CallingConvention.StdCall)]
private static extern void mouse_event(long dwFlags, long dx, long dy, long cButtons, long dwExtraInfo);
private const int MOUSEEVENTF_LEFTDOWN = 0x02;
private const int MOUSEEVENTF_LEFTUP = 0x04;
private const int MOUSEEVENTF_RIGHTDOWN = 0x08;
private const int MOUSEEVENTF_RIGHTUP = 0x10;
private static void SendLeftMouseClick()
{
int x = Cursor.Position.X;
int y = Cursor.Position.Y;
mouse_event(MOUSEEVENTF_LEFTDOWN | MOUSEEVENTF_LEFTUP, x, y, 0, 0);
}
public Form1()
{
InitializeComponent();
tabControl1.MouseDown += new MouseEventHandler(tabControl1_MouseDown);
tabControl1.MouseUp += new MouseEventHandler(tabControl1_MouseUp);
}
void tabControl1_MouseDown(object sender, MouseEventArgs e)
{
if (e.Button == MouseButtons.Right)
{
// Send a left mouse click to select the tab that the user clicked on.
SendLeftMouseClick();
}
}
void tabControl1_MouseUp(object sender, MouseEventArgs e)
{
if (e.Button == MouseButtons.Right)
{
// To show a context menu for only the tab button but not the content of the tab,
// we must show it in the tab control's mouse up event.
contextMenuStrip1.Show((Control)sender, e.Location);
}
}
回答by nisar
Opening event of context menu can be used to solve both problems
上下文菜单的打开事件可以解决这两个问题
private void contextMenuStrip1_Opening(object sender, CancelEventArgs e)
{
Point p = this.tabControl1.PointToClient(Cursor.Position);
for (int i = 0; i < this.tabControl1.TabCount; i++)
{
Rectangle r = this.tabControl1.GetTabRect(i);
if (r.Contains(p))
{
this.tabControl1.SelectedIndex = i; // i is the index of tab under cursor
return;
}
}
e.Cancel = true;
}
回答by David Silva-Barrera
I was looking for a solution for the exact same problem.
After testing both @nisar and @BFree answers I came to this (I also had the TabControl` inside a Panel somewhere in the Form):
我正在寻找完全相同问题的解决方案。
在测试了@nisar 和@BFree 的答案后,我来到了这个问题(我还在表单的某个面板中使用了 TabControl`):
- Create tabcontrol1
- Subscribe to the MouseClick event
- Create contextMenuTabs, ContextMenuStrip
- 创建 tabcontrol1
- 订阅鼠标点击事件
- 创建 contextMenuTabs、ContextMenuStrip
private void tabControl1_MouseClick(object sender, MouseEventArgs e)
{
if (e.Button == MouseButtons.Right)
{
Point ee = new Point(e.Location.X - panel1.Left, e.Location.Y - panel1.Top);
for (int i = 0; i < this.tabControl1.TabCount; i++)
{
Rectangle r = this.tabControl1.GetTabRect(i);
if (r.Contains(ee))
{
if (this.tabControl1.SelectedIndex == i)
this.contextMenuTabs.Show(this.tabControl1, e.Location);
else
{
//if a non seelcted page was clicked we detected it here!!
}
break;
}
}
}
}