关闭所有打开的模态对话框窗口。

4
我有一个WPF应用程序,其中有几个模态窗口用于不同的目的。这可以通过使用ShowDialog函数轻松实现。然而,在我的应用程序中,我有一个计时器来测量空闲时间(即没有鼠标移动或按键),这将导致用户注销。当此计时器触发时,是否有一种方法可以查找并关闭所有打开的模态窗口,而无需明确跟踪每个窗口?
更新:我还想关闭任何MessageBox.Show实例。这可能吗?
谢谢, 马特
2个回答

6

你尝试过迭代Application.Current.Windows集合并关闭所有不是Application.Current.MainWindow的窗口吗?

Jogy


我刚刚根据我在MSDN论坛上找到的一个帖子做了这个,http://social.msdn.microsoft.com/Forums/en/wpf/thread/86e4806f-8f95-49a8-811e-e01514518e16 - Matt Ruwe
我更新了我的问题,包括 MessageBoxes。你知道如何以类似的方式关闭它们吗? - Matt Ruwe

4
当计时器触发时,有没有一种方法可以找到并关闭所有打开的模态窗口而不需要显式跟踪每个窗口?
您可以使用ComponentDispatcher.IsThreadModal来检查UI线程是否处于模态状态。如果是, Application.Current.Windows属性将给出已打开窗口的列表。
如果您只有一个MainWindow,则可以关闭任何其他窗口(因为它们将是您的模态对话框),但如果您有多个窗口,则必须检查每个窗口。
不幸的是,没有直接的API可以确定特定窗口是否为模态 - 但是Window类中有一个私有变量,您可以使用它来实现此功能。例如,以下方法使用反射来确定窗口是否为模态:
  public static bool IsModal(Window window)
  {
       Type type = typeof(Window);
       var field = type.GetField("_showingAsDialog", BindingFlags.Instance | BindingFlags.NonPublic);
       return field.GetValue(window);
  }

很遗憾,这可能会改变(因为它使用了未记录的私有成员)。


谢谢你的回答。我之前不知道Application.Current.Windows属性。另外,感谢你提供关于_showingAsDialog字段的信息。看起来这就是解决方法。我更新了我的问题以包括MessageBox实例。你知道如何以类似的方式关闭它们吗? - Matt Ruwe
@Matt:不幸的是,MessageBox.Show可能需要进行P/Invoke调用,因为它们没有可以访问的窗口...如果你也要处理这个问题,你可能需要重新考虑你的设计,或者查看使用EnumWindows和类似方法调用PInvoke来跟踪所有打开的窗口... - Reed Copsey
谢谢。我想我们会尝试将所有的MessageBox调用转换为Windows,这样再加上你的答案应该就能解决这个问题了。 - Matt Ruwe

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接