我编写了一个小应用程序,展示了我将如何处理您描述的行为。
我用四个控件设置了我的主窗体(此示例中只是按钮,可以是您想要的任何控件)。然后我设置了另一个表单作为选择器。对于此示例,它仅包含一个 ListBox,其中包含控件名称。你可以做一些更花哨的东西。您还可以传入当前聚焦的控件,以使该控件已在列表中被选中。我默认为列表中的第一个控件。
我在 MainForm 上设置了一个名为 NextControl 的公共属性来保存从选择器表单中选择的控件。我还设置了一个 List 属性来保存对您希望能够从中选择的所有控件的引用。使用此方法,ShowDialog 应该可以正常工作,因为焦点不会设置在 Next 控件上,直到该 Dialog 退出之后。
主窗体:
using System.Collections.Generic;
using System.Windows.Forms;
namespace Tabber
{
public partial class MainForm : Form
{
public MainForm()
{
InitializeComponent();
ControlList = new List<Control>(new Control[] {button1, button2, button3, button4});
}
private List<Control> ControlList { get; set; }
public Control NextControl { get; set; }
private void MainForm_KeyDown(object sender, KeyEventArgs e)
{
if (e.Modifiers == Keys.Control && e.KeyCode == Keys.Tab)
{
using (var chooseDialog = new Chooser(this, ControlList))
{
if (chooseDialog.ShowDialog() == DialogResult.OK)
{
if (NextControl != null)
{
NextControl.Focus();
}
}
}
}
}
}
}
选择者:
using System.Collections.Generic;
using System.Windows.Forms;
namespace Tabber
{
public partial class Chooser : Form
{
public Chooser(MainForm sender, List<Control> controls)
{
Sender = sender;
InitializeComponent();
foreach (Control control in controls)
{
listBox1.Items.Add(control);
}
listBox1.DisplayMember = "Name";
listBox1.SetSelected(0, true);
}
private MainForm Sender { get; set; }
private void Chooser_KeyDown(object sender, KeyEventArgs e)
{
if (e.Modifiers == Keys.Control && e.KeyCode == Keys.Tab)
{
if (listBox1.SelectedIndex == listBox1.Items.Count - 1)
{
listBox1.SetSelected(0, true);
}
else
{
listBox1.SetSelected(listBox1.SelectedIndex + 1, true);
}
e.Handled = true;
}
}
private void listBox1_KeyUp(object sender, KeyEventArgs e)
{
if (e.KeyCode == Keys.ControlKey)
{
Sender.NextControl = (Control) listBox1.SelectedItem;
DialogResult = DialogResult.OK;
Close();
}
}
}
}
您可以修改它以满足您的需要。它为我正确地改变了焦点。