由于用户点击Tab键而离开文本框之前,我想启用一个跟随它的控件,以便它成为焦点控件。
相反,似乎Winforms已经决定焦点会在哪里,所以它会跳过控制。
我已尝试使用Validating
和Validated
事件启用后续控件,但似乎这太晚了,即使我知道如果验证表明失败,焦点也不会离开控件如此清晰,标签行为可能会在验证时受到影响。
因此,示例特定场景(代码如下):
观察到的行为是焦点移动到第二个文本框,跳过复选框,并且复选框已启用,可能不是按此顺序(即,我描述观察到的最终结果,不一定是事情发生的顺序) )。
有可能得到我想要的东西吗?
这是一个演示问题的LINQPad程序
void Main()
{
var fm = new Form();
var e1 = new TextBox();
e1.Location = new Point(8, 8);
e1.CausesValidation = true;
e1.TabIndex = 0;
e1.TabStop = true;
var chk = new CheckBox();
chk.Text = "Checkbox";
chk.Location = new Point(8, e1.Bottom + 8);
chk.Enabled = false;
chk.TabIndex = 1;
chk.TabStop = true;
var e2 = new TextBox();
e2.Location = new Point(8, chk.Bottom + 8);
e2.TabIndex = 2;
e2.TabStop = true;
fm.Controls.Add(e1);
fm.Controls.Add(chk);
fm.Controls.Add(e2);
e1.Validating += (s, e) =>
{
Debug.WriteLine("e1 validating");
chk.Enabled = true;
};
e1.Validated += (s, e) =>
{
Debug.WriteLine("e1 validated");
chk.Enabled = true;
};
chk.Enter += (s, e) => Debug.WriteLine("chk entered");
e2.Enter += (s, e) => Debug.WriteLine("e2 entered");
fm.ShowDialog();
}
答案 0 :(得分:0)
一个黑客的排序。但是工作..
e1.Leave += (s, e) =>
{
Debug.WriteLine("e1 Leave");
chk.Enabled = true;
fm.SelectNextControl( e1,true,true,true,true);
};
答案 1 :(得分:0)
您最好在TextChanged
事件中验证输入,例如:
e1.TextChanged += (s, e) =>
{
chk.Enabled = (e1.Text.Length > 2);
};
Control.Validating
event的MSDN文档包含此警告:
请勿尝试从Enter,GotFocus,Leave,LostFocus,Validating或Validated事件处理程序中设置焦点。这样做可能会导致您的应用程序或操作系统停止响应。有关更多信息,请参阅"键盘输入参考"中的WM_KILLFOCUS主题。部分,以及"消息死锁" "关于消息和消息队列" MSDN库中http://msdn.microsoft.com/library的主题。
我不记得Windows使用处理消息的具体顺序,但我怀疑启用chk
复选框的消息会在 Windows处理Tab键后发送。在TextChanged
事件中进行验证意味着您不必担心这种奇怪的竞争状况。