2009-04-25 8 views
0

Je ne peux pas le croire, cela fonctionne dans mon autre application, mais dans celui-ci, qui a une structure similaire - ce n'est pas!Invoquer à partir de thread différent

public string ListAdd 
    { 
     set 
     { 
      if (listView1.InvokeRequired) 
      { 
       this.Invoke((MethodInvoker)delegate 
       { 
        listView1.Items.Add(value); 
       }); 
      } 
      else 
      { 
       listView1.Items.Add(value); 
      } 
     } 
    } 

La façon dont je l'appelle:

 var formz = Form.ActiveForm as Form1; 
     if (formz != null) 
      formz.ListAdd = "asdasdasdasd"; 

Si je l'appelle de la fonction où je reçois paquet (je veux le mettre sur le listView) sur TCP - Rien ne se passe, mais si je appelez-le dans cette même classe où j'initialise WinSock - cela fonctionne.

Où le problème pourrait-il être? Je viens de déboguer l'application, formz est nulle à l'endroit où je l'appelle (fonction de réception). Pourquoi est-il nul là-bas, mais pas dans un autre endroit?

+0

Vous ne devriez pas travailler comme cela dans un setter de propriété, pensez à le changer en méthode. –

Répondre

2

Je ne pense pas, cela va résoudre votre problème, mais avez-vous pensé à utiliser le modèle suivant pour faire l'appel? Je le considère beaucoup plus lisible. Créez cette méthode d'extension.

public static class ControlExtension 
{ 
    public static void ThreadSafeInvoke(this Control control, MethodInvoker method) 
    { 
     if (control != null) 
     { 
     if (control.InvokeRequired) 
     { 
      control.Invoke(method); 
     } 
     else 
     { 
      method.Invoke(); 
     } 
     } 
    } 
} 

Et puis vous pouvez effectuer des appels de méthode thread-safe comme ceci.

Form form = new Form(); 

form.ThreadSafeInvoke(() => form.Text = "ThreadSafeInvoke"); 

Ou plusieurs appels à la fois.

form.ThreadSafeInvoke(() =>     
{ 
    form.Text = "ThreadSafeInvoke"; 
    form.Visible = true; 
    form.WindowState = FormWindowState.Maximized; 
}); 

MISE À JOUR

Le problème est clairement Form.ActiveForm retour null.

  1. Il n'existe aucune forme active au moment de l'appel.
  2. Le thread n'a pas l'autorisation d'obtenir le formulaire actif - MSDN indique que UIPermission est requis.
1

Si ActiveForm renvoie null alors vous ne pouvez pas avoir un formulaire actif ou il n'est pas de type Form1. Vous utilisez "comme Form1", donc si vous avez un Form2 qui est actif alors formz sera mis à null.

Pouvez-vous passer formz dans la fonction au lieu d'appeler ActiveForm?

+0

J'ai un seul formulaire, et j'utilise async (WSAAsyncSelect()) pour faire mes connexions. Non, je ne peux pas affecter Form1 à une variable qui n'a pas encore été initialisée. –

+0

Alors, que retourne Form.ActiveForm? Null ou une forme d'un type autre que Form1? –

+0

null //Comment.length = 15; –

0

Vérifiez si vous êtes en mode débogage; Si c'est le cas, la valeur du formulaire actif retournée sera nulle.

Questions connexes