2011-08-27 30 views
9

Soy nuevo en C#, pero he hecho un montón de Java. Aquí está mi problema: estoy tratando de abrir un "SaveFileDialog" de un hilo que no es el hilo de UI.C#: Mostrar cuadro de diálogo en el hilo de la interfaz de usuario de otro hilo

Esto es exactamente lo que trato de hacer:

public partial class Form1: Form 
{ 
    public string AskSaveFile() 
    { 
     var sfd = new SaveFileDialog(); 
     sfd.Filter = "Fichiers txt (*.txt)|*.txt|Tous les fichiers (*.*)|*.*"; 
     sfd.FilterIndex = 1; 
     sfd.RestoreDirectory = true; 
     DialogResult result = (DialogResult) Invoke(new Action(() => sfd.ShowDialog(this))); 
     if(result == DialogResult.OK) 
     { 
      return sfd.FileName; 
     } 

     return null; 
    } 
} 

Este método siempre se llamará a partir de un hilo diferente de la que posee el formulario. El problema es que cuando ejecuto este código, el congelamiento "Form1" y el "SaveFileDialog" no aparecen.

¿Tiene alguna pista para ayudarme a mostrar el diálogo desde un hilo independiente?

Respuesta

6

Prueba esto:

public partial class Form1: Form 
{ 
    public string AskSaveFile() 
    { 
     if (this.InvokeRequired) 
     { 
      Invoke(new MethodInvoker(delegate() { AskSaveFile(); })); 
     } 
     else 
     { 
      var sfd = new SaveFileDialog(); 
      sfd.Filter = "Fichiers txt (*.txt)|*.txt|Tous les fichiers (*.*)|*.*"; 
      sfd.FilterIndex = 1; 
      sfd.RestoreDirectory = true; 
      if(sfd.ShowDialog() == DialogResult.OK) return sfd.FileName; 
     }    
     return null; 
    } 
} 
+0

No funciona: "AskSaveFile" debe devolver una cadena. Y si espero el resultado con "EndInvoke", tengo el mismo problema ("Form1" congelamiento). – Moinonime

+0

La primera parte del nuevo código hace que Dialog se ejecute en el hilo principal ... así que esto podría funcionar ... Oh, sí, el hilo principal ejecutará esto ... pero ¿quieres decir que tu hilo principal está haciendo algo diferente y no podría usarse? ? Créanme, utilizo este código en diferentes subprocesos en mis aplicaciones y funciona ... entonces debe haber algo que no entiendo ahora ... – Marco

+0

Una pregunta: ¿sus hilos son hilos o trabajadores en el fondo? – Marco

11

que se vea como esto:

public string AskSaveFile() { 
     if (this.InvokeRequired) { 
      return (string)Invoke(new Func<string>(() => AskSaveFile())); 
     } 
     else { 
      var sfd = new SaveFileDialog(); 
      sfd.Filter = "Fichiers txt (*.txt)|*.txt|Tous les fichiers (*.*)|*.*"; 
      sfd.FilterIndex = 1; 
      sfd.RestoreDirectory = true; 
      return sfd.ShowDialog() == DialogResult.OK ? sfd.FileName : null; 
     } 
    } 

Si, a pesar estancamiento continuación, asegúrese de usar ventana depuración + de Windows + Hilos del depurador y mirar a lo que el El hilo de la interfaz de usuario está funcionando. Control.Invoke() no puede completarse a menos que el subproceso UI esté inactivo y bombee el bucle de mensajes. Esperar a que termine el hilo de trabajo siempre provocará un punto muerto.

Además, tenga en cuenta que este tipo de código es arriesgado, es posible que el usuario no espere que este diálogo aparezca repentinamente y lo cierre accidentalmente al pasar el mouse o el teclado por la (s) ventana (s) propiedad del subproceso de la interfaz de usuario.

Cuestiones relacionadas