0

MDI メインフォームがあります。その上でフォームをホストし、閉じる前にメッセージボックスを表示したい(変更を保存するかどうかをユーザーに尋ねる)。

ここまでは順調ですが、MDI メイン フォームを閉じても MDI 子の FormClosing イベントが発生しないことがわかりました。MDI メインの FormClosing イベント (発生します) でMdiChild .Close() を呼び出すだけだと考えました。この継ぎ目は機能しますが、問題が発生します...

私が表示するメッセージボックスで、変更を保存して閉じるのをキャンセルするのではなく、変更を保存するようにユーザーに提案します。通常はこれで問題なく動作しますが、MDI メインの FormClosing イベントをキャンセルする方法が見つからないようです。これを行うエレガントな方法はありますか?

編集:MDIメインのFormClosingイベントでキャッチされる例外をスローすることでこれを解決しました(ユーザーが閉じる手順をキャンセルすることを決定したとき)。このようにして、いつ MDI メインの FormClosing イベントをキャンセルしなければならないかがわかります。この継ぎ目は正常に機能します...しかし、この「hax」がこれを行う唯一の方法であるとは信じられません。きっともっと良い方法がありますか?

4

3 に答える 3

3

ユーザーがクローズのキャンセルに投票したときに、子フォームのクローズをキャンセルすると思いますか?

その場合、私はこのメインフォームを閉じて行きます

private void Form1_FormClosing(object sender, FormClosingEventArgs e)
{
    if (e.CloseReason == CloseReason.UserClosing)
    {
        foreach (Form frm in this.MdiChildren)
        {
            frm.Close();
        }
    }
    e.Cancel = (this.MdiChildren.Length > 0);
}
于 2010-05-10T09:04:50.410 に答える
1

子フォームを呼び出す代わりに、子フォームのCloseようなメソッドを作成しReadyToClose、メインフォームがループして子フォームごとにそれを呼び出すことをお勧めします。ユーザーに質問をして、必要に応じて保存し、続行してもよい場合は最後に true を返します。

そして、すべての子フォームがクローズに「投票」した場合は、すべてクローズします。それ以外の場合は、何もクローズしません。

于 2010-05-10T08:54:48.093 に答える
1

MDI メイン フォームを閉じると、すべての子の Close イベントが最初に呼び出されるため、foreach ループで frm.Close() を呼び出すと、子の Close イベントが再度呼び出されます (既に閉じている必要があるかどうかはわかりません)。 .

ho1の提案は私にとってはうまくいきました。これが私の変更された foreach ループです (ClosableMDIChildForm は IsOkToClose() メソッドを含むインターフェイスです):

foreach (ClosableMDIChildForm cmdif in this.MdiChildren)
{
    if (!cmdif.IsOkToClose())
    {
        e.Cancel = true;
        ((Form)mdifc).Focus();
        break;
    }
}

明らかに、this.MdiChildren フォームは ClosableMDIChildForm インターフェイスを実装する必要があります。ウィンドウを閉じてもよいかどうかを判断するロジックは、IsOkToClose() の実装にあります。

于 2010-08-02T23:14:51.613 に答える