[Threads] Stopper un thread via un control

Résolu
littlekenny Messages postés 43 Date d'inscription mardi 25 février 2003 Statut Membre Dernière intervention 10 septembre 2009 - 28 févr. 2008 à 17:34
littlekenny Messages postés 43 Date d'inscription mardi 25 février 2003 Statut Membre Dernière intervention 10 septembre 2009 - 4 mars 2008 à 09:51
Salut,

M'étant  basé sur l'article de MorpionMx (Opérations cross-threads - utilisation des délégations synchrones / asynchrones), j'aimerais fermer mon thread secondaire (traitement qui peut devenir long et lourd) via un bouton ou popup lié à mon thread principal. Une fois mon thread secondaire lancé, mon interface principale est cependant bloquée jusqu'à la fin de l'exécution du thread secondaire (qu'il soit asynchrone ou pas, ça ne change rien).
<hr size="2" width="100%" />// mon thread secondaire
private Thread threadLoadReport=null;
...
//je lance mon thread secondaire à partir de la forme qui contient le bouton qui devrait être utilisé pour tuer (abord) ce thread.
threadLoadReport = new Thread(new ThreadStart(ExecuteThreadReport));
threadLoadReport.Priority = ThreadPriority.Highest;
threadLoadReport.Start();
...
private void ExecuteThreadReport()
        {
            IAsyncResult iar=this.BeginInvoke(new DelExecuteReport(ExecuteReport), lastReportOpened);
            //lancement de l'exécution lourde, contenue dans la procédure ExecuteReport(string str)
            this.EndInvoke(iar);
        }
...
//le code derrière le bouton pour tuer mon thread secondaire est simple:
if (threadLoadReport != null)
            {
                threadLoadReport.Abort();
                threadLoadReport = null;
            }
<hr size="2" width="100%" />Pour résumé, je ne comprends pas pourquoi mon interface principale est bloquée lorsque je lance mon thread secondaire. J'aimerais avoir la possibilité de garder la main sur celle-ci.

Un super grand merci d'avance, ça me dépannerait beaucoup.

7 réponses

littlekenny Messages postés 43 Date d'inscription mardi 25 février 2003 Statut Membre Dernière intervention 10 septembre 2009
4 mars 2008 à 09:51
Je crois avoir trouvé une solution:

            private Thread threadLoadReport = null; //thread pour afficher mon rapport
            private Thread threadStop = null; //thread pour popup, pour arrêter threadLoadReport
...
            threadStop = new Thread(new ThreadStart(ExecuteThreadStop));
            threadStop.Name = "stop";
            threadStop.Start(); 
            threadLoadReport = new Thread(new ThreadStart(ExecuteThreadReport));
            threadLoadReport.Name= "Execute";
            threadLoadReport.Priority = ThreadPriority.Highest;
            threadLoadReport.IsBackground = true;
            threadLoadReport.Start();
...
private void ExecuteThreadStop()
        {
            frmStop = new FrmStop(); //mon popup qui va me servir à stopper le chargement de mon rapport (using to abord the thread threadLoadReport).
            frmStop.ShowDialog(); //j'utilise un showdialog et pas un show, sinon le popup disparait à la fin du thread (vu qu'ils sont liés)
        }

Comme vous pouvez le voir, je n'utilise pas d'invoke dans mon second thread (ExecuteThreadStop()), cela répond bien à ma question-réponse de mon post précédent sur la méthode invoke. Mon popup n'est ainsi pas lié au thread principal et est lancé via un autre thread. Le plus lourd du travail est fait, il ne me reste plus qu'à aborder le chargement du premier thread et c'est bon.

Merci pour vos aides.
3
lassaad83 Messages postés 148 Date d'inscription vendredi 28 avril 2006 Statut Membre Dernière intervention 1 décembre 2009
28 févr. 2008 à 18:30
Qu'est ce que tu fait exactement dans la méthode ExecuteReport(string str) ?
0
lassaad83 Messages postés 148 Date d'inscription vendredi 28 avril 2006 Statut Membre Dernière intervention 1 décembre 2009
28 févr. 2008 à 18:38
Rajoute un Thread.Sleep(0) au niveau ExecuteThreadReport()
0
MorpionMx Messages postés 3466 Date d'inscription lundi 16 octobre 2000 Statut Membre Dernière intervention 30 octobre 2008 57
28 févr. 2008 à 19:25
Salut,

Regarde les explications que je donne dans ce sujet, elles pourront peut etre t'aider

Mx
MVP C# 
0

Vous n’avez pas trouvé la réponse que vous recherchez ?

Posez votre question
littlekenny Messages postés 43 Date d'inscription mardi 25 février 2003 Statut Membre Dernière intervention 10 septembre 2009
29 févr. 2008 à 09:05
Merci pour vos réponses mais ça ne fonctionne pas :
> [auteur/LASSAAD83/760533.aspx lassaad83] : ExecuteReport(string str) est ma procédure qui charge un crystal report dans un viewer.
En gros, j'ai ceci comme code dedans :
crystalReport.ReportSource = crReportDocument; où crReportDocument est un rapport Crystal. Selon les paramètres introduits, le temps d'exécution est plus ou moins long (de 2 à 30sec).
> [auteur/MORPIONMX/5912.aspx MorpionMx] : J'ai essayé ce qui a été fait dans l'exemple mais ça ne fonctionne pas:

Dans votre exemple, il y a :

      for (int i = 0; i < 1000; 
i++) //on boucle 

      {
         IAsyncResult
ias = this.BeginInvoke(new monDelegate(MethodeTest), i.ToString()); //traitement léger
         Thread.Sleep(1000); //longue pause
         this.EndInvoke(ias);

      }
<!--[if !supportLineBreakNewLine]-->

Pour mon cas, on a :

     ...
     threadLoadReport = new Thread(new ThreadStart(ExecuteThreadReport));
     threadLoadReport.IsBackground = true; // je l'ai rajouté
     threadLoadReport.Start();
    ...

private void ExecuteThreadReport()
{
   //pas de boucle
   IAsyncResult
iar = this.BeginInvoke(new DelExecuteReport(ExecuteReport), lastReportOpened); //traitement lourd
   Thread.Sleep(1000); //pause ridicule par rapport au traitement
   this.EndInvoke(iar);
}

En appuyant comme un forcené sur mon bouton stop, on dirait qu'il peut de temps en temps recevoir l'event click. A mon avis, ça correspond au temps de pause d'une seconde.

Est-ce que quelqu'un a une idée? Merci d'avance.
0
cs_coq Messages postés 6349 Date d'inscription samedi 1 juin 2002 Statut Membre Dernière intervention 2 août 2014 101
1 mars 2008 à 19:07
Salut,

Que fait tu après le lancement du thread ?
Le problème se pose t'il aussi si tu neutralises la génération du rapport et que tu la remplaces par une attente longue ?

/*
coq
MVP Visual C#
CoqBlog
*/
0
littlekenny Messages postés 43 Date d'inscription mardi 25 février 2003 Statut Membre Dernière intervention 10 septembre 2009
3 mars 2008 à 14:48
> coq : "Que fait tu après le lancement du thread ?" Pour l'instant, rien.
J'essaye, via un popup avec un bouton (lancé dans un autre thread), si le programme me redonne la main pendant le chargement (un peu comme la méthode annuler le chargement dans Toad). Rien de concluant pour l'instant.

"Le problème se pose t'il aussi si tu neutralises la génération du rapport et que tu la remplaces par une attente longue ?"
Si je remplace la génération du rapport par un sleep, ça fonctionne. Je me demande si le problème n'est pas lié à la méthode invoke. J'avais lu dans un de tes posts que cette méthode créait une instance de la procédure appelée dans le thread principal (si je ne me trompe pas). Mon problème vient peut-être de là.

Je vais encore tester ça. Si je trouve quelque chose, je le posterai tantôt.
De même, si vous avez des idées, n'hésitez pas à partager. Merci d'avance.


 
0
Rejoignez-nous