模拟 ShowDialog 功能
-
11-09-2019 - |
题
我正在编写一个应用程序(c# + wpf),其中所有模式样式对话框都实现为 UserControl
在覆盖主要内容的半透明网格顶部 Window
. 。这意味着只有一个 Window
它保持了所有公司应用程序的外观和风格。
要显示一个 MessageBox
, ,语法如下:
CustomMessageBox b = new CustomMessageBox("hello world");
c.DialogClosed += ()=>
{
// the rest of the function
}
// this raises an event listened for by the main window view model,
// displaying the message box and greying out the rest of the program.
base.ShowMessageBox(b);
正如您所看到的,与经典的 .NET 版本相比,不仅执行流程实际上是相反的,而且还极其冗长:
MessageBox.Show("hello world");
// the rest of the function
我真正寻找的是一种不再返回的方法 base.ShowMessageBox
直到它引发了对话框关闭事件,但我看不出如何在不挂起 GUI 线程的情况下等待此事件,从而阻止用户单击“确定”。我知道我可以将委托函数作为参数 ShowMessageBox
函数可以防止执行反转,但仍然会导致一些疯狂的语法/缩进。
我是否遗漏了一些明显的东西,或者是否有标准方法可以做到这一点?
其他提示
要做到这一点的方式是通过使用一个 DispatcherFrame 对象。
var frame = new DispatcherFrame();
CustomMessageBox b = new CustomMessageBox("hello world");
c.DialogClosed += ()=>
{
frame.Continue = false; // stops the frame
}
// this raises an event listened for by the main window view model,
// displaying the message box and greying out the rest of the program.
base.ShowMessageBox(b);
// This will "block" execution of the current dispatcher frame
// and run our frame until the dialog is closed.
Dispatcher.PushFrame(frame);
您可以让你的函数成返回IEnumerator<CustomMessageBox>
的迭代器,然后把它写这样的:
//some code
yield return new CustomMessageBox("hello world");
//some more code
您会然后写一个包装函数,它枚举器,并调用MoveNext
(其将执行所有的功能,直到下一个yield return
)在DialogClosed
处理程序。
请注意的是,包装函数将不会是一个阻塞调用。
设置在消息框中类另一个消息循环。是这样的:
public DialogResult ShowModal()
{
this.Show();
while (!this.isDisposed)
{
Application.DoEvents();
}
return dialogResult;
}
如果您在反光看Windows.Form你会看到它确实是这样的..
不隶属于 StackOverflow