使用模态和非模态形式的区别

Posted

技术标签:

【中文标题】使用模态和非模态形式的区别【英文标题】:Difference in using Modal and Non-Modal forms 【发布时间】:2021-11-10 10:21:21 【问题描述】:

我有一个关于模态和非模态形式的 using 语句的问题。

当我使用 using 语句时,我想要完成的是相同的行为。

下面是一个与模态表单完美配合的示例。

Dictionary<string, string> input;
using (var window = new Form1()

    window.ShowDialog();

    if (window.DialogResult == DialogResult.Cancel)
    
        return Result.Cancelled;
    

    input = window.GetInformation();

当我将 ShowDialog() 更改为 Show() 时,整个表单不再起作用。

我试过不使用 using 语句,但我无法从上面的我那里获取信息。

有没有办法实现完全相同的结果,但使用form.Show() 而不是使用ShowDialog()

编辑: 当我使用 ShowDialog() 从外部应用程序显示表单时,单击外部应用程序时它不会被停用。但我正在使用在这种情况下不会触发的 OnDeactivated 事件。所以我尝试了 Show(),这似乎有效。

【问题讨论】:

你喜欢Show的哪一点,或者你不喜欢ShowDialog的哪一点? 这不是关于using,而是更多关于 ShowDialog() 仅在用户关闭对话框后返回,而 Show() 立即返回。您必须为 FormClosed 事件 ***.com/questions/24193049/… 显式添加侦听器 当我使用 ShowDialog() 显示来自外部应用程序的表单时,单击外部应用程序时它不会被停用。但我正在使用在这种情况下不会触发的 OnDeactivated 事件。所以我尝试了 Show(),这似乎有效。 【参考方案1】:

如果问题是为什么 Show() 在 Using 语句中不起作用,那是因为 Show() 是非模态的,因此程序流程继续(即不等待 Form 像 ShowDialog() 那样关闭将)。因此,流程继续退出 Using,它会处理在 Using 内部创建的对象,包括您创建的 Form。这就是它似乎不起作用的原因。

这是我为解决此问题所做的工作。

我将要显示的表单声明为您正在使用的类全局:

private Form1 window;

在我想显示的函数中:

if (window != null && !window.IsDisposed) window.BringToFront();
else

   var window = new Form1();
   window.Show();
   // ... rest of your code here

当然,如果您不使用 ShowDialog(),则必须以不同的方式捕获结果。我更喜欢的方式是使用 FormClosing 事件

在实例化表单时添加:

 window.FormClosing += window_FormClosing;

然后在事件处理程序中添加您想要捕获结果的任何代码:

    private void window_FormClosing(object sender, FormClosingEventArgs e)
    
        Form1 window = sender as Form1;
        // Your code here
    

【讨论】:

以上是关于使用模态和非模态形式的区别的主要内容,如果未能解决你的问题,请参考以下文章

【读书笔记4】弹框体系总结:模态弹框和非模态弹框

WinForms 编程 - 模态和非模态表单问题

如何创建一个模态的对话框

Qt的模态对话框和非模态对话框 经常使用setAttribute (Qt::WA_DeleteOnClose)

Qt 销毁模态对话框

如何直观的区分模态对话框和非模态对话框