-1

我正在用 C# 编写一个 WinForm 应用程序。有一个点击Form A打开Form CButton现在,我想Form B在打开之前添加一个密码输入屏幕Form C。只有输入的密码正确才会Form C打开,否则显示错误消息。Form B只有一个TextBox控件和一个验证 Button控件。

/*Form A*/
FormB fb;
private void BtnClick(object sender, EventArgs e) {
    DialogResult result;
    //fb can open once at a time
    if(fb == null){
        fb = new FormB();
        fb.FormClosed += new FormClosedEventHandler(FormB_FormClosed);

        //This seems to be not working
        result = fb.ShowDialog();
    }
    else //FormB already open. Do nothing
        return;

    //Only if password entered is correct, proceed
    if(result == DialogResult.Yes){    //result == cancel 
        //Code to open Form C          //Program never reaches here
    }
}

//Upon closing FormB, reset it to null
private void FormB_FormClosed(object sender, FormClosedEventArgs e){
    if(fb != null)
        fb = null;
}

/* Form B */
private const string password = "xxxyyyzzz";
private void BtnPW_Click(object sender, EventArgs e){
    bool result = Verify();
    if(result){
        BtnPW.DialogResult = DialogResult.Yes;
    }
    else{
        MessageBox.Show("Error: Incorrect password");
        BtnPW.DialogResult = DialogResult.No;
    }
    this.Close();             //Added
}

private bool Verify(){
    if(TxtBox.Text == password)
        return true;
    else
        return false;
}

有人能告诉我这段代码有什么问题吗?if它永远不会到达Form A.

编辑:即使我输入正确的密码并点击按钮Form B,也会result得到Form A“DialogResult.Cancel`。

4

1 回答 1

1

如果您调用 Form.Close 方法,则该表单的 DialogResult 属性将设置为 DialogResult.Cancel,即使您已将其设置为其他值。要隐藏以模态方式打开的表单,您只需将表单的 DialogResult 属性设置为 DialogResult.None 以外的任何值。

说您的代码似乎不是通常用于处理模态对话框的代码。
ShowDialog 正在阻止您的代码,直到被调用的表单关闭或隐藏时您才退出此调用,因此您不需要保留 FormB 的全局变量并在 FormA 中处理 FormB 的 FormClosed 事件处理程序。

private void BtnClick(object sender, EventArgs e) 
{
    using(FormB fb = new FormB())
    {
        // Here the code returns only when the fb instance is hidden
        result = fb.ShowDialog();
        if(result == DialogResult.Yes)
        {  
            //open Form C          
        }    
   }     
}

现在您应该在 FormB 代码中删除对 Form.Close 的调用并直接设置 FormB 的 DialogResult 属性,此时不要尝试更改按钮的 DialogResult 属性,这将不起作用,您需要再次单击隐藏表单,而是直接设置表单的 DialogResult 属性。

private const string password = "xxxyyyzzz";
private void BtnPW_Click(object sender, EventArgs e)
{
     if(Verify())
         this.DialogResult = DialogResult.Yes;
     else
     {
         MessageBox.Show("Error: Incorrect password");
         this.DialogResult = DialogResult.No;
     }
}

通过这种方式,表单被隐藏(未关闭),并且您的代码从 FormA 中的 ShowDialog 调用中退出。在 using 块中,您仍然可以使用 FormB 实例来读取其属性并采用适当的路径。当您的代码从 using 块中退出时,fb 实例将自动关闭并不再存在。

于 2017-11-13T18:17:08.957 回答