none
Gestion des Thread RRS feed

  • Question

  • Bonjour à tous, 

    Je pose les bases, je suis totalement novice en gestion des Thread. :)

    Maintenant que c'est dit, je coince avec avec l'utilisation d'un Thread et voici mon code. 

    Thread.Sleep(500);
                System.Threading.Thread thread =
                  new System.Threading.Thread(() =>
                  {
                      t = new Thread(Work);
                      t.Start();
                      Decryptage();
                      t.Abort();
                      BarreProgressionPB.Visibility = Visibility.Hidden;
                  });
                thread.Start();

    L'idée, c'est de lancer un décryptage de fichiers dans Thread pour ne pas bloquer l'interface utilisateur et d'arrêter ma barre de progression quand ces terminé.

    Mon soucis, c'est quand je ne sais pas attendre que le Thread soit terminé pour rendre invisible ma barre de progression. Avec ce code, il plante toujours sur le Visibility.Hidden en me disant que ça fait parti d'un autre Thread. 

    Est-ce que vous pourriez m'aiguiller SVP ? Je m'y perds un peu et je ne trouve pas de solution avec mon ami Google (ou alors je ne sais pas les interpreter). 

    Par avance merci.


    MCITP EA Windows Server 2008 R2 MCSA Windows Server 2012 Apprenti développeur C# EF WPF

    lundi 3 août 2020 10:32

Réponses

  • Un exemple basique en C#/Winforms avec un Button lançant un thread mettant à jour une ProgressBar de 0 à 100 =>

    public partial class Form1 : Form
    {
        private System.Windows.Forms.Button button1;
        private System.Windows.Forms.ProgressBar progressBar1;
        private Thread workerThread = null;
        private readonly AutoResetEvent isCanceled = new AutoResetEvent(false);
    
        public Form1()
        {
            InitializeComponent();
        }
    
        private void Form1_Load(object sender, EventArgs e)
        {
            button1 = new System.Windows.Forms.Button();
            progressBar1 = new System.Windows.Forms.ProgressBar();
    
            button1.Location = new System.Drawing.Point(103, 62);
            button1.Name = "button1";
            button1.Size = new System.Drawing.Size(75, 23);
            button1.TabIndex = 0;
            button1.Text = "button1";
            button1.UseVisualStyleBackColor = true;
            button1.Click += new System.EventHandler(this.button1_Click);
    
            progressBar1.Location = new System.Drawing.Point(40, 150);
            progressBar1.Name = "progressBar1";
            progressBar1.Size = new System.Drawing.Size(201, 30);
            progressBar1.TabIndex = 1;
    
            ClientSize = new System.Drawing.Size(284, 261);
            Controls.Add(this.progressBar1);
            Controls.Add(this.button1);
    
            CenterToScreen();
        }
    
        private void button1_Click(object sender, EventArgs e)
        {
            progressBar1.Visible = true;
            progressBar1.Value = 0;
            if (workerThread != null)
            {
                workerThread.Abort();
                workerThread.Join();
            }
            workerThread = new Thread(new ThreadStart(this.WorkerThread));
            workerThread.Start();
        }
    
        private void WorkerThread()
        {
            for (; !isCanceled.WaitOne(0);)
            {
                Invoke(new Action(DrawProgressBar));
                // Attente 1/10ème de seconde
                System.Threading.Thread.Sleep(100);
            }
        }
    
        private void DrawProgressBar()
        {
            if (progressBar1.Value < 100)
            {
                progressBar1.Value++;
                progressBar1.Refresh();
            }
            else
            {
                isCanceled.Set();
                progressBar1.Visible = false;
            }
        }
    
        protected override void OnFormClosing(FormClosingEventArgs e)
        {
            if (workerThread != null)
                workerThread.Abort();
            base.OnFormClosing(e);
        }
    }

    jeudi 6 août 2020 13:10

Toutes les réponses


  • Mon soucis, c'est quand je ne sais pas attendre que le Thread soit terminé pour rendre invisible ma barre de progression. Avec ce code, il plante toujours sur le Visibility.Hidden en me disant que ça fait parti d'un autre Thread. 


    Il faut utiliser Invoke  (ou BackgroundWorker)

    pour accéder aux contrôles d'une Fenêtre depuis un thread

    Voir la doc : How to: Make thread-safe calls to Windows Forms controls

    lundi 3 août 2020 12:29
  • Merci pour la réponse. 

    Ça fait un moment que je suis sur la doc et je n'y arrive pas...


    MCITP EA Windows Server 2008 R2 MCSA Windows Server 2012 Apprenti développeur C# EF WPF

    jeudi 6 août 2020 12:19
  • Bon ben j'ai trouve. 

    J'ai juste rajouté le code ci dessous mais je ne sais pas si c'est la bonne méthode.

    Dispatcher.Invoke(() => { BarreProgressionPB.Visibility = Visibility.Hidden; });

    MCITP EA Windows Server 2008 R2 MCSA Windows Server 2012 Apprenti développeur C# EF WPF

    jeudi 6 août 2020 12:51
  • Un exemple basique en C#/Winforms avec un Button lançant un thread mettant à jour une ProgressBar de 0 à 100 =>

    public partial class Form1 : Form
    {
        private System.Windows.Forms.Button button1;
        private System.Windows.Forms.ProgressBar progressBar1;
        private Thread workerThread = null;
        private readonly AutoResetEvent isCanceled = new AutoResetEvent(false);
    
        public Form1()
        {
            InitializeComponent();
        }
    
        private void Form1_Load(object sender, EventArgs e)
        {
            button1 = new System.Windows.Forms.Button();
            progressBar1 = new System.Windows.Forms.ProgressBar();
    
            button1.Location = new System.Drawing.Point(103, 62);
            button1.Name = "button1";
            button1.Size = new System.Drawing.Size(75, 23);
            button1.TabIndex = 0;
            button1.Text = "button1";
            button1.UseVisualStyleBackColor = true;
            button1.Click += new System.EventHandler(this.button1_Click);
    
            progressBar1.Location = new System.Drawing.Point(40, 150);
            progressBar1.Name = "progressBar1";
            progressBar1.Size = new System.Drawing.Size(201, 30);
            progressBar1.TabIndex = 1;
    
            ClientSize = new System.Drawing.Size(284, 261);
            Controls.Add(this.progressBar1);
            Controls.Add(this.button1);
    
            CenterToScreen();
        }
    
        private void button1_Click(object sender, EventArgs e)
        {
            progressBar1.Visible = true;
            progressBar1.Value = 0;
            if (workerThread != null)
            {
                workerThread.Abort();
                workerThread.Join();
            }
            workerThread = new Thread(new ThreadStart(this.WorkerThread));
            workerThread.Start();
        }
    
        private void WorkerThread()
        {
            for (; !isCanceled.WaitOne(0);)
            {
                Invoke(new Action(DrawProgressBar));
                // Attente 1/10ème de seconde
                System.Threading.Thread.Sleep(100);
            }
        }
    
        private void DrawProgressBar()
        {
            if (progressBar1.Value < 100)
            {
                progressBar1.Value++;
                progressBar1.Refresh();
            }
            else
            {
                isCanceled.Set();
                progressBar1.Visible = false;
            }
        }
    
        protected override void OnFormClosing(FormClosingEventArgs e)
        {
            if (workerThread != null)
                workerThread.Abort();
            base.OnFormClosing(e);
        }
    }

    jeudi 6 août 2020 13:10
  • Bonjour Hageshii,

    Avez-vous avancé dans votre projet? Pouvons-nous considérer que vous avez résolu votre problème avec le scénario proposé ou avec un autre? Si la réponse proposée vous a aidé, n'oubliez pas de marquer comme réponse.

    Cordialement,
    Nina


    Microsoft propose ce service gratuitement, dans le but d'aider les utilisateurs et d'élargir les connaissances générales liées aux produits et technologies Microsoft. Ce contenu est fourni "tel quel" et il n'implique aucune responsabilité de la part de Microsoft.

    lundi 31 août 2020 08:41
    Modérateur