C# 从另一个线程更新标签
我使用另一个类中的线程来更新标签。 标签是Winform主类中的内容C# 从另一个线程更新标签,c#,multithreading,winforms,C#,Multithreading,Winforms,我使用另一个类中的线程来更新标签。 标签是Winform主类中的内容 Scanner scanner = new Scanner(ref lblCont); scanner.ListaFile = this.listFiles; Thread trd = new Thread(new ThreadStart(scanner.automaticScanner)); trd.IsBackground = true; trd.Start(); while (!trd.IsAlive) ;
Scanner scanner = new Scanner(ref lblCont);
scanner.ListaFile = this.listFiles;
Thread trd = new Thread(new ThreadStart(scanner.automaticScanner));
trd.IsBackground = true;
trd.Start();
while (!trd.IsAlive) ;
trd.Join();
您看,我将label的引用传递给第二个类的构造函数。
在第二个类(扫描器)中,我有一个名为“automaticScanner”的方法,该方法应使用以下代码更新标签:
public Scanner(ref ToolStripStatusLabel _lblContatore)
{
lblCounter= _lblContatore;
}
Thread threadUpdateCounter = new Thread(new ThreadStart(this.UpdateCounter));
threadUpdateCounter.IsBackground = true;
threadUpdateCounter.Start();
while (!threadUpdateCounter .IsAlive) ;
threadUpdateCounter.Join();
private void AggiornaContatore()
{
this.lblCounter.Text = this.index.ToString();
}
我在更新标签时收到此错误:
跨线程操作无效:从创建控件“Main”的线程以外的线程访问控件“Main”
我将.net 4与Winform C#一起使用
谢谢你的回答
新闻:
问题在于这一行:
trd.Join();
这一行阻塞了我的GUI,标签没有更新。
有一些方法可以控制线程的结束,并更新标签直到结束?
感谢使用更新其他线程中的标签文本
private void AggiornaContatore()
{
MethodInvoker inv = delegate
{
this.lblCounter.Text = this.index.ToString();
}
this.Invoke(inv);
}
您得到这个错误是因为您的UI线程持有这个标签,并且由于您试图通过另一个线程更新它,您得到的是跨线程异常
您还可以看到:只需使用或
很好的例子:。您不能从UI线程以外的任何其他线程更新UI。 使用此选项更新UI线程上的线程
private void AggiornaContatore()
{
if(this.lblCounter.InvokeRequired)
{
this.lblCounter.BeginInvoke((MethodInvoker) delegate() {this.lblCounter.Text = this.index.ToString(); ;});
}
else
{
this.lblCounter.Text = this.index.ToString(); ;
}
}
请阅读本章以及本书中的更多内容,以清楚了解线程:
lblCounter不包含InvokeRequest的定义,与BeginInvoke的定义相同。我没有标签,但ToolStripStatusLabelIIRC,InvokeRequest存在于每个控件中,但受到保护,这就是为什么您只能在“您当前的类”(即表单、用户控件)中看到它,并尝试在另一个类(即标签、文本框)上访问它失败当我执行此代码时,标签没有改变…它应该设置为this.index.ToString()的值;请为我们提供更多代码以帮助您。我的类不支持接口IDisposable。由于这个原因,找不到this.IsDisposed..@Antonio,请删除该检查并直接在我的类Scanner的方法Aggiorna contatore中调用它,该方法调用未找到。但是。。。在这种模式下调用线程是否正确?线程trd=新线程(新线程开始(scanner.scansioneAutomatica));trd.IsBackground=true;trd.Start();而(!trd.IsAlive);trd.Join();在此模式下,GUI被阻止!:包括类内的代码动作y;以及参与计时器事件私密空TyEXP(对象发送器、Sypult.TimeServer、ELAP SEDENTARGARS E){{C++;//委托〉的函数是表达式“y=())> Label1.text = c toSTRIN()”Label1。调用(y=())> Label1.text = c toStReg());