如何在不阻止GUI但将信息传回主线程的情况下执行后台任务?

时间:2015-04-01 13:13:19

标签: c# multithreading backgroundworker

我想做以下事情:

  • 在GUI上有一个按钮和一个表。
  • 当我按下按钮时,任务开始
  • 此任务是一个while循环,为每个迭代提供数据

如何在不阻塞GUI的情况下运行此循环并从主GUI表中的每次迭代中获取数据?这很重要,因为while stop条件又是GUI上的一个按钮。

我尝试过使用BackgroundWorker,但我真的无法弄清楚如何在每次循环迭代时发回数据(???)我可以在结束时返回结果,但那不是目标。如果我在循环中启动worker(但没有在worker中循环),则它不起作用。

private void ContinuousCoordinateAquisition(object sender, DoWorkEventArgs e)
{
    while (continuousPositionAquisitionFlag == true)                       //  while the monitoring is not stopped, get positions
    {
        // get xyzwpr world coordinates
        robotCoordinatesXYZWPRworld XYZWPRworld = robi.getRobotPosition_xyzwpr_world();

        Do something........... retuns values I need in GUI

        // sleep for defined time
        System.Threading.Thread.Sleep(1000); //  wait 
    } 
}

呼叫将是

BackgroundWorker bw = new BackgroundWorker();
bw.DoWork += new DoWorkEventHandler(ContinuousCoordinateAquisition); 
bw.RunWorkerCompleted += new RunWorkerCompletedEventHandler(ContinuousCoordinateAquisitionCompleted);

continuousPositionAquisitionFlag是通过按钮(停止按钮)设置的。 ContinuousCoordinateAquisitionCompleted这里只做一次遗憾,而不是每次迭代。

2 个答案:

答案 0 :(得分:2)

你走在正确的轨道上。您应该使用后台工作程序,但不要等待RunWorkerCompletedEventHandler,这在一切都完成后会发生。

相反,在循环内定期调用后台工作程序上的ReportProgress方法。这将触发您可以在GUI线程中处理的ProgressChanged事件。

见这里:https://msdn.microsoft.com/en-us/library/system.componentmodel.backgroundworker.progresschanged(v=vs.110).aspx

答案 1 :(得分:0)

尝试设置BackgroundWorkClass WorkerReportsProgress属性并处理ProgressChanged事件,如本文所述: https://msdn.microsoft.com/en-us/library/cc221403%28v=vs.95%29.aspx