在后台工作线程中更新进度条时出现异常

本文关键字:异常 工作 后台 线程 更新 | 更新日期: 2023-09-27 18:06:12

我创建了一个 wpf 应用程序。在我的应用程序中,我打开一个窗口并在后台复制一些文件。我想在复制期间显示和更新进度条。

我尝试使用后台工作者:

public partial class FenetreProgressBar : Window
{
    private readonly BackgroundWorker worker = new BackgroundWorker();

    public FenetreProgressBar(ObservableCollection<Evenement.FichierJoint> CollectionFicJointsToAdd)
    {
        InitializeComponent();
        worker.WorkerReportsProgress = true;
        worker.DoWork += worker_DoWork;
        worker.RunWorkerCompleted += worker_RunWorkerCompleted;
        worker.ProgressChanged +=worker_ProgressChanged;
        worker.RunWorkerAsync(CollectionFicJointsToAdd);
    }
    private void ProgressChanged(double Persentage, ref bool Cancel)
    {
        if (Cancel)
            this.Close();
        worker.ReportProgress((int)Persentage);
    }
    private void Completedelegate()
    {
        this.Close();
    }
    private void worker_DoWork(object sender, DoWorkEventArgs e)
    {
        ObservableCollection<Evenement.FichierJoint> collection = e.Argument as ObservableCollection<Evenement.FichierJoint>;
        //2) On ajoute les fichiers joints à l'évènements ( ce qui va donc les copier dans le répertoire paramétré)
        foreach (Evenement.FichierJoint FichierJoint in collection)
        {
            if (FichierJoint.strPathFichier.Length > 0)
            {
                Evenement.FichierJoint monFichierJoint = new Evenement.FichierJoint(FichierJoint.strPathFichier, App.obj_myEvenement.strEvtNumeroString);
                MaProgressBar.Minimum = 0;
                MaProgressBar.Maximum = 100;
                monFichierJoint.copyObject.OnProgressChanged += ProgressChanged;
                monFichierJoint.copyObject.OnComplete += Completedelegate;
                monFichierJoint.AddFichierJoint();
            }
        }
    }
    private void worker_RunWorkerCompleted(object sender,RunWorkerCompletedEventArgs e)
    {
        // Traitement terminé, on ferme la fenetre
        this.Close();
    }
    private void worker_ProgressChanged(object sender, ProgressChangedEventArgs e)
    {
        MaProgressBar.Value = e.ProgressPercentage;
    }
}

当节目在这里时:

MaProgressBar.Minimum = 0;
MaProgressBar.Maximum = 100;

我有一个例外:"调用线程无法访问此对象,因为其他线程拥有它"。

我已经在谷歌和stackoverflow上阅读了几个答案,但我不会尝试将这种方法与BackgroundWorker一起使用。

任何人都可以帮助我以避免此异常并解决问题吗?

多谢

最好的问候:)

在后台工作线程中更新进度条时出现异常

cannot modify UI objects from background worker .您需要像这样invoke UI dispatcher上的方法 -

App.Current.Dispatcher.Invoke((Action)delegate
            {
                MaProgressBar.Minimum = 0;
                MaProgressBar.Maximum = 100;
            });

但是由于您只需要set maximum an minimum values,我建议您在 constructor 的 backgroundWorker 之外设置这些值 -

public FenetreProgressBar(ObservableCollection<Evenement.FichierJoint> 
                      CollectionFicJointsToAdd)
{
    InitializeComponent();
    MaProgressBar.Minimum = 0;
    MaProgressBar.Maximum = 100;
    worker.WorkerReportsProgress = true;
    worker.DoWork += worker_DoWork;
    worker.RunWorkerCompleted += worker_RunWorkerCompleted;
    worker.ProgressChanged +=worker_ProgressChanged;
    worker.RunWorkerAsync(CollectionFicJointsToAdd);
}

为什么不使用 C# 新异步并等待新功能/关键字? 它们专门设计用于在执行冗长操作时使 UI 响应。

你应该试试这个:

_backgroundWorker.OnProgressChanged += new ProgressChangedEventHandler(backgroundWorker_ProgressChanged);

然后

// Event handler
private void backgroundWorker_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
    // Update main thread here
}