2016-06-08 21 views
0

当我点击一个按钮时,我在我的winform中进行了长时间的处理;即,我正在加载大量文件并处理它们。在处理期间,我的GUI被冻结并且没有响应,这是一个问题,因为处理可能需要10分钟以上。有没有办法将代码放入某种泡泡或某种东西中,以便在处理文件时使用GUI?也许甚至添加“取消”按钮。在处理过程中启用响应式图形用户界面

编辑:勒内的解决方案有效,而且,这里的progressbar控制我也想:

private async void button1_Click(object sender, EventArgs e) 
    { 
     progressBar1.Maximum = ValueWithTOtalNumberOfIterations.Length; 
     IProgress<int> progress = new Progress<int>(value => { progressBar1.Value = value;}); 

     await Task.Run(() => 
     { 
      var tempCount = 0; 

     //long processing here 
     //after each iteration: 

      if (progress != null) 
      { 
       progress.Report((tempCount)); 
      } 
      tempCount++;   
     }    
    } 
+2

看异步/等待https://msdn.microsoft.com/en-us/library/mt674882.aspx –

+1

可以使用的BackgroundWorker。请参阅此链接 - https://msdn.microsoft.com/en-us/library/cc221403%28v=vs.95%29.aspx对于取消按钮操作,请使用CancelAsync方法。 – Sanket

+1

是的,有不同的方法来实现这一点。您应该搜索async-await(如果您使用net fw 4.5或更高版本),因为您已经正确标记了该内容,然后提出您的尝试;) – Mono

回答

2

你可以简单地让你的按钮的点击处理async并开始Task您的长时间运行的操作:

public async void button1_Click(object sender, EventArgs e) 
{ 
    button1.Enabled = false; // disable button to not get called twice 

    await Task.Run(() => 
    { 
     // process your files 
    } 

    button1.Enabled = true; // re-enable button 
} 

编译器将其变成状态机。控制流程以关键字await返回给调用者(UI)。当您的Task已完成时,将继续执行此方法。


要使用“取消” - 按钮,你可以使用一个TaskCancellationSource或简单地定义你检查,而你正在处理您的文件标志,如果该标志被设置返回(通过单击处理您的“取消” 按钮):

private bool _stop = false; 

private void cancelButton_Click(object sender, EventArgs e) 
{ 
    _stop = true; 
} 
private async void button1_Click(object sender, EventArgs e) 
{ 
    button1.Enabled = false; // disable button to not get called twice 

    _stop = false; 

    await Task.Run(() => 
    { 
     // process your files 
     foreach(var file in files) 
     { 
      if (_stop) return; 
      // process file 
     } 
    } 

    button1.Enabled = true; // re-enable button 
} 
+0

这太棒了,谢谢!但是现在我的处理代码中出现了一个错误,例如我的DialogResult result = folder.ShowDialog();上的ThreadStateException。在进行OLE调用之前,必须将当前线程设置为STA模式。我知道我不应该在这里问这个问题,但是你能知道如何解决它吗? – Romy

+1

哦,你不应该在任务内部打开另一个对话框,因为它在不同于ui的线程上执行。 –

+0

啊我明白了。首先启动处理的按钮打开folderBrowserDialog以选择文件。那我应该把Task.Run的东西放在下面吗? – Romy