Domanda

Se io mostro un MessageBox come modale di una finestra su un altro processo, funziona bene fino a quando il mio programma resta rispondere. Se è chiusa o terminata mentre la MessageBox mostra le finestre che hanno ricevuto il MessageBox verrà bloccato (ma ancora rispondere) e dovrà essere completato tramite Task Manager.

Ecco un codice di esempio per dimostrare che:

using System;
using System.Windows.Forms;
using System.Diagnostics;
using System.Threading;

namespace TestMessageBox
{
    class Program
    {
        private WindowWrapper notepad;

        Program(IntPtr handle)
        { 
            notepad = new WindowWrapper(handle); 
        }

        static void Main(string[] args)
        {
            Process[] procs = Process.GetProcessesByName("notepad");
            if (procs.Length > 0)
            {
                Console.WriteLine("Notepad detected...");
                Program program = new Program(procs[0].MainWindowHandle);
                Thread thread = new Thread(new ThreadStart(program.ShowMessage));
                thread.IsBackground = true;
                thread.Start();
                Console.Write("Press any key to end the program and lock notepad...");
                Console.ReadKey();
            }
        }

        void ShowMessage()
        { 
            MessageBox.Show(notepad, "If this is open when the program ends\nit will lock up notepad..."); 
        }
    }

    /// <summary>
    /// Wrapper class so that we can return an IWin32Window given a hwnd
    /// </summary>
    public class WindowWrapper : System.Windows.Forms.IWin32Window
    {
        public WindowWrapper(IntPtr handle)
        { 
            _hwnd = handle; 
        }
        public IntPtr Handle
        { 
            get { return _hwnd; } 
        }
        private IntPtr _hwnd;
    }

}

Come evitare questo?

È stato utile?

Soluzione

L'atto di mostrare una finestra di dialogo modale disabilita la finestra padre della finestra di dialogo (finestra del blocco note nel tuo esempio). Quando la finestra di dialogo modale viene chiusa, viene riattivata la finestra padre.

Se il programma muore prima che riabilita la finestra, quella finestra non potrà mai ottenere riattivato - spetta al thread che sta mostrando la finestra di dialogo per riattivare il genitore. (Nel tuo esempio, accade all'interno MessageBox.Show(), dopo che l'utente fa clic su OK o qualsiasi altra cosa).

L'unico modo per fare questo lavoro sarebbe quella di avere un secondo processo la cui responsabilità era di rimettere le cose come dovrebbero essere, se il processo di creazione della finestra di dialogo modale muore prematuramente, ma questo è orribile. Ed è ancora non antiproiettile -? Che cosa succede se il processo di osservatore muore troppo

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top