在c#中使用Background Controller运行进度条

时间:2013-11-29 09:33:07

标签: c# multithreading progress-bar backgroundworker threadpool

我对c#中的线程控制没有全面的了解。我想在运行方法时创建进度条。

我有两种形式:

  1. Form1是运行应用时显示的表单。它有一个名为btnScrape的按钮。单击该方法时,应调用该方法,并显示带有进度条的表单。在进度条完成之前,应对用户禁用Form1

  2. ProgressBarForm - 这里面有进度条和标签。

  3. 代码如下。

       //In Form1.cs I have a button.
          private void btnScrape_Click(object sender, EventArgs e)
        {
                //gather data for folloeing parameters from the form.
                 Controller cntrlr = new Controller(urlFilePath, destinationPath, destinationfilename,cmbDepth.SelectedIndex);
    
                cntrlr.Vmain(); // this is the method in controller class. while this is running i want show the progress bar.
        }
    
       // in Contrller class     
        class Controller{
              List<string> urlList = null; 
              URLFileReader urlFileReader = null;
              HTTPWorker httpWorker = null;
              SourceReader srcreader = null;
              ReportWriter reportWriter = null;
    
               string urlFilePath, destinationPath, destinationFileName;
               int depth;
    
        public Controller(string urlFilePath,string destinationPath,string destinationFileName,int depth)
        {
            this.urlFilePath = urlFilePath;
            this.destinationPath = destinationPath;
            this.destinationFileName = destinationFileName;
            this.urlList = new List<string>();
            this.urlFileReader = new URLFileReader();
            this.httpWorker = new HTTPWorker(this.destinationPath);
            this.reportWriter = new ReportWriter(this.destinationPath,this.destinationFileName);
            this.srcreader = new SourceReader(this.reportWriter);
            this.depth = depth;
    
        }
    
           //this is the method
             public void Vmain(){
    
                  this.urlFileReader.ReadURL(urlFilePath);
                  this.urlList = urlFileReader.geturlList();           
    
                  string pageSrc;
    
                    foreach (string requestUrl in urlList)
                    {
                       //do sruff for requestUrl
                       //the progressbar should move as the urlList iterate.
                       //additionally i want the label on the top of progress bar to     display the current "requestUrl"
                       //as the urlList is over i want quit from the progressbar window and come back to Form1. Till the progrss bar is completed Form1 should be disabled for the user.
    
                    }
    
             }
    
    
    
        }
    

    请解释那里发生的事情并尽可能提供有效的代码。先感谢您。没有任何完美的答案对我有用,即使我花了两天时间。我尝试使用BackgroundWorker和线程。但没有找到解决方案。 :(

2 个答案:

答案 0 :(得分:1)

在主窗体中,您可以使用以下代码:

    private Progressfrm _loadForm;
    private void ShowProgress()
    {
        ToggleForm();
        _loadForm = new Progressfrm();
        _loadForm.ShowDialog();
        var tcheck = new Thread(CheckLoadedProgress);
        tcheck.Start();
        //do stuff here
    }
    private void CheckLoadedProgress()
    {
        while (_loadForm.IsAccessible) { }
        ToggleForm();
    }
    private void ToggleForm()
    {
        Invoke(new Action(() => Enabled = !Enabled));
    }
    private void btnScrape_Click(object sender, EventArgs e)
    {
        var tform = new Thread(ShowProgress);
        tform.Start();
    }

然后进度 - Form将一直显示,直到它被填充:

    private ProgressBar _progressBar;
    private void Progressfrm_Shown(object sender, EventArgs e)
    {
        _progressBar = new ProgressBar { Size = new Size(100, 20), Location = new Point(10, 10) };
        Controls.Add(_progressBar);
        _progressBar.Show();
        Refresh();
        LoadProgress();
    }
    private void LoadProgress()
    {
        while (_progressBar.Value < 100)
        {
            _progressBar.Value++;
            Thread.Sleep(100);
        }
        Close();
    }

在此表单上,您必须添加事件Shown并添加代码,如我的示例中所示。希望这会有所帮助。

答案 1 :(得分:0)

使用BackgroundWorker类输出progressBar和statusLabel更改:

BackgroundWorker bgw;
private void btnScrape_Click(object sender, EventArgs e)
{
  bgw = new BackgroundWorker();
  bgw.WorkerReportsProgress = true;
  bgw.DoWork += new DoWorkEventHandler(bgw_DoWork);
  bgw.ProgressChanged += new ProgressChangedEventHandler(bgw_ProgressChanged);
  bgw.RunWorkerAsync();
}

void bgw_DoWork(object sender, DoWorkEventArgs e)
{
  for (int i = 1; i <= 100; i++)
  {
    Thread.Sleep(100);
    bgw.ReportProgress(i);
  }
}

private void bgw_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
  progressBar1.Value = e.ProgressPercentage;
}

这只是一个如何以异步方式更新控件的示例。