2009-12-01 23 views
5

すべてのモーダルスタイルのダイアログが、として実装されていて、メインWindowをカバーする半透明グリッドの上にアプリケーション(c#+ wpf)を書いています。つまり、Windowが1つしかなく、すべての企業アプリケーションのルックアンドフィールを維持しています。 エミュレートShowDialog機能

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スレッドをぶら下げとせず、この待つことが可能であるかを確認カント私たちを防ぐそれでもOKをクリックしてください。私はShowMessageBox関数の引数としてデリゲート関数を取ることができることを知っています。この種の関数は実行の逆転を防ぎますが、依然として狂った構文/インデントを引き起こします。

明らかなものがないか、これを行う標準的な方法がありますか?

答えて

5

CodeProjectのthisの記事とMSDNのthisの記事をご覧ください。最初の記事では、手動でブロッキングモーダルダイアログを作成する方法を説明し、2番目の記事でカスタムダイアログを作成する方法を示します。

+0

リンクされた最初の記事は、これを行う方法の完全な例を示しています。 – Guy

0

あなたは、このようにそれを書き、IEnumerator<CustomMessageBox>を返すイテレータにあなたの関数を作ることができ:

//some code 
yield return new CustomMessageBox("hello world"); 
//some more code 

あなたは、その後のすべてを実行しますどの列挙子を取り、(MoveNextを呼び出すラッパー関数を記述します機能は、次のyield returnDialogClosedハンドラで。

ラッパー関数はブロッキング呼び出しではないことに注意してください。

0

メッセージボックスクラスに別のメッセージループを設定します。ような何か:

public DialogResult ShowModal() 
{ 
    this.Show(); 

    while (!this.isDisposed) 
    { 
    Application.DoEvents(); 
    } 

    return dialogResult; 
} 

あなたはリフレクターでWindows.Formを見れば、あなたはそれがこのような何かをして表示されます。..

+0

彼はWinFormsではなくWPFを使用しています。 – SLaks

+0

ああ、私はそれを逃した。 WPFは完全に異なっていますか?ウィンドウにメッセージループがなくなりますか? –

4

これを行う方法は、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); 
関連する問題