C#启动和停止同一按钮点击事件内的线程
我正在使用C#、.Net4.0和Visual Studio 2010,当用户单击按钮时,我试图从我的windows窗体应用程序中获得此行为:C#启动和停止同一按钮点击事件内的线程,c#,multithreading,winforms,visual-studio-2010,.net-4.0,C#,Multithreading,Winforms,Visual Studio 2010,.net 4.0,我正在使用C#、.Net4.0和Visual Studio 2010,当用户单击按钮时,我试图从我的windows窗体应用程序中获得此行为: GUI LED开始闪烁 长横档操作开始 当点2的操作结束时,LED停止闪烁 private void Btn_WebService_Click(object sender, EventArgs e) { Thread_Blink = new Thread(() => { LED_Blink(LED.WS); }); Thread_Bl
private void Btn_WebService_Click(object sender, EventArgs e)
{
Thread_Blink = new Thread(() => { LED_Blink(LED.WS); });
Thread_Blink.Start();
// Do something that takes time.. Let's imulate with a sleep
Thread.Sleep(2000);
Thread_Blink.Abort();
}
private void Btn_WebService_MouseDown(object sender, MouseEventArgs e)
{
Timer_Blink.Enabled = true;
}
private void Btn_WebService_Click(object sender, EventArgs e)
{
// Do something that takes time.. Let's imulate with a sleep
Thread.Sleep(2000);
}
private void Btn_WebService_MouseUp(object sender, MouseEventArgs e)
{
Timer_Blink.Enabled = false;
}
结果总是一样的:只有在长时间运行的操作结束时(Thread.Sleep(2000);
)LED才会开始闪烁,然后突然停止,使您看不到任何东西。为什么会发生这种情况?我如何才能获得期望的行为
我添加了更多信息。我尝试使用BackgroundWorked并以这种方式实现了想要的行为:
private void Btn_WebService_Click(object sender, EventArgs e)
{
BlinkWorker.RunWorkerAsync(LED.WS);
LedOn(LED.WS);
TestWebService(); // This method takes about 2 seconds to answer..
LedOff(LED.WS);
BlinkWorker.CancelAsync();
}
当TestWebService()运行时,我会关闭指示灯(LedOn(LED.WS);)。TestWebService()完成后,指示灯亮起。
如果在Click事件中启动并取消,BlinkWorker仍不工作
仅供参考:如果我制作了一个启动闪烁的按钮和另一个停止闪烁的按钮,那么效果会很好。我建议您查看一下BackgroundWorker类和ReportProgress方法。问题是,您将UI线程捆绑在
线程中。Sleep
。UI线程是特殊的-它是唯一可以更改UI的线程-因此,当它忙于睡眠时,它无法为BackgroundWorker
或LED闪烁
计时器回调更改UI状态的任何尝试提供服务
因此,您不需要占用UI线程。您需要将线程.Sleep
代码(或其实际等效代码)放入BackgroundWorker
sDoWork
处理程序,或使用其他方法避免阻塞UI线程
如果您尝试执行的实际工作已经提供了异步替代方案(例如,wait Task.Delay(2000);
相当于您当前的线程。Sleep(2000);
),则当前常用的方法是使用async
/wait
)。不幸的是,使用async
和await
将需要您迁移到.NET/Visual Studio的更高版本,但无论如何您都应该考虑这一点。2010年已经过时了(而且,IMO可能是最糟糕的一年——它的速度非常慢),而.NET 4.0(相对于.NET 4.5.2或更高版本)不再受支持