【问题标题】:MVVM progressbar and background worker visibilityMVVM 进度条和后台工作人员可见性
【发布时间】:2012-12-13 13:41:42
【问题描述】:

我正在使用 WPF MVVM 并且有一个进度条来报告任务的进度,使用后台工作人员。它可以工作,除非我在工作完成时让进度条折叠起来,如果我这样做,进度条永远不会结束。如果我让进度条可见,那很好,但我不希望在任务完成时进度条可见。有人可以告诉我哪里出错了吗?在下面的 GenerateOutput 只是一个创建一些文件并更新进度的函数。 ShowSummary() 是任务完成后需要运行的东西。我尝试在 RunWorkerCompleted 中放置一个 Thread.Sleep,这样用户就可以在其折叠之前实际看到已完成的栏,但您仍然看不到它完整。

public void BackgroundWorkerGenerateOutputProgress()
    {
        ProgressVisibility = Visibility.Visible;
        BackgroundWorker worker = new BackgroundWorker();
        worker.DoWork += new DoWorkEventHandler(DoWork);
        worker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(RunWorkerCompleted);
        worker.RunWorkerAsync();
    }

void DoWork(object sender, DoWorkEventArgs e)
    {
        if (IsInProgress)
            return;
        CurrentProgress = 0;
        IsInProgress = true;
        BackgroundWorker worker = sender as BackgroundWorker;
        GenerateOutput();
    }
void RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    {
        IsInProgress = false;
        ProgressVisibility = Visibility.Collapsed;
        ShowSummary();
    }

编辑:我已将其更改为以下内容,我仍然没有看到进度条到达末尾:

public void BackgroundWorkerGenerateOutputProgress()
    {
        ProgressVisibility = Visibility.Visible;
        CurrentProgress = 0;
        BackgroundWorker worker = new BackgroundWorker();
        worker.WorkerReportsProgress = true;
        worker.DoWork += new DoWorkEventHandler(DoWork);
        worker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(RunWorkerCompleted);
        worker.ProgressChanged += new ProgressChangedEventHandler(ProgressChanged);
        worker.RunWorkerAsync();
    }

    private void ProgressChanged(object sender,
        ProgressChangedEventArgs e)
    {
        CurrentProgress = e.ProgressPercentage;
    }
 void DoWork(object sender, DoWorkEventArgs e)
    {
        if (IsInProgress)
            return;
        IsInProgress = true;
        BackgroundWorker worker = sender as BackgroundWorker;

        DoIt(worker);
    }
    void DoIt(BackgroundWorker worker)
    {
        worker.ReportProgress(20);
        Thread.Sleep(1000);
        worker.ReportProgress(40);
        Thread.Sleep(1000);
        worker.ReportProgress(60);
        Thread.Sleep(1000);
        worker.ReportProgress(80);
        Thread.Sleep(1000);
        worker.ReportProgress(100);

    }
    void RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    {

        IsInProgress = false;
        ShowSummary();
        System.Threading.Thread.Sleep(2000);
        ProgressVisibility = Visibility.Collapsed;
    }

xaml(抱歉无法格式化):

<ProgressBar HorizontalAlignment="Left" Value="{Binding CurrentProgress, Mode=OneWay}" Height="20" Width="200" Visibility="{Binding Path=ProgressVisibility}" Minimum="0" Maximum="100" />

【问题讨论】:

  • 它是如何工作的?我没有看到任何对 ReportProgress 或 WorkerReportsProgress = true 的调用。
  • 在 GenerateOutput 方法中,我在执行每个操作后更新 CurrentProgress 属性(双精度)。 ProgressBar 的值绑定到 CurrentProgress。我不确定这是正确的方法,因此我的问题是,但它确实有效。我在 GenerateOutput 结束时将 CurrentProgress 设置为 100(最大值,最小值为 0)。

标签: c# wpf mvvm progress-bar backgroundworker


【解决方案1】:

尝试使用此链接中显示的 ReportProgress。你没有 WorkerReportsProgress = true

BackgroundWorker Class

如果您在 GenerateOutput() 的末尾设置它,那么它被设置为 Visibility.Collapsed;在呈现 UI 之前。

【讨论】:

  • 查看我的编辑。还没看到进度在崩溃前走到尽头。
  • 所以您看到的进展不是 100%?
  • 是的,我看到了,但它永远不会达到 100%。如果我取出将可见性设置为折叠的行,它将达到 100%。
  • 一旦达到 100% 就完成并设置为 Visibility.Collapsed。在worker.ReportProgress(100)之后尝试睡眠
  • 成功了,非常感谢。但是为什么在 RunWorkerCompleted 中调用睡眠(在调用设置 Visibility=Collapsed 之前)不起作用?
【解决方案2】:

我没有尝试过,但逻辑上认为我会这样做。在隐藏之前将进度的值设置为最大值。

void RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
{
    CurrentProgress = 0; //Set this to max value
    IsInProgress = false;
    ProgressVisibility = Visibility.Collapsed;
    ShowSummary();
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-06-11
    • 2013-02-27
    • 1970-01-01
    • 2011-10-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-09-05
    相关资源
    最近更新 更多