2010-03-23 46 views
2

我为这个问题做了一个简单的测试应用程序,每个包含一个按钮的两个winforms。 单击第一个窗体上的按钮打开另一个窗体。它还订阅了关键事件。KeyUp处理错误控制

第二种形式有其按钮设置为“的AcceptButton”在我们为1S睡觉被点击的事件,然后设置的DialogResult为true(睡眠是模拟做了一些处理)

时输入用于关闭第二种形式是第一种形式的按钮的KeyUp事件被触发,即使在第二种形式通过之前键被释放,第二种形式仍然显示并聚焦。

如果在第二种形式下按下其他任何输入按键,则第一种形式的按钮不会触发事件。

第一种形式:

public Form1() 
    { 
     InitializeComponent(); 
     buttonForm2.KeyUp += new KeyEventHandler(cntKeyUp); 
    } 

    void cntKeyUp(object sender, KeyEventArgs e) 
    { 
     MessageBox.Show(e.KeyCode.ToString()); 
    } 

    private void buttonForm2_Click(object sender, EventArgs e) 
    { 
     using (Form2 f = new Form2()) 
     { 
      f.ShowDialog(); 
     } 
    } 

第二种形式:

private void button1_Click(object sender, EventArgs e) 
    { 
     Thread.Sleep(1000); 
     this.DialogResult = DialogResult.OK; 
    } 

有谁知道为什么该事件被触发的非活性形式的按钮,可以做些什么来阻止这种情况发生?

+0

该问题已通过向Form1添加KeyDown处理程序解决,然后keyup事件验证EventArgs的KeyValue是否匹配由KeyDown设置的KeyValue,然后清除该KeyValue。 如果KeyUp事件被另一个对话触发,KeyDown值永远不会被设置,我们知道不应该采取任何行动。 按照SLak建议的第二种形式调用是小型测试案例中的一个潜在解决方案,但在实际应用中,在一个或多个对话框中很容易忘记这么做。 – Mikael 2010-03-23 14:52:08

回答

3

在发送WM_KEYUP消息之前,您正在进行阻止呼叫,然后关闭表单。

在发送消息时,第二个表单不见了,所以当前的重点控制是在第一个表单上。

可以在cntKeyUp如果验证:

您可以通过在第二种形式的点击处理程序调用BeginInvoke只隐藏在接下来的消息循环的形式(在KEYUP之后)各地

0

一种方法解决这个问题发件人是您期望的表单,然后您处理它,否则忽略。

+0

发件人是Form1上的按钮,也就是我有兴趣收听的人。所以这是行不通的。 – Mikael 2010-03-23 13:50:24