我一直在尝试实现多类线程GUI管理。因为我希望不同的线程分布在不同的.cs文件中的多个类中,以根据需要更新UI。
我搜索了stackoverflow和其他来源,发现大多数人都使用Dispatcher.Invoke或类似的东西。所以我决定开始测试......
下面是一个名为wThread.cs的类中的线程,
public class wThread
{
public EventHandler SignalLabelUpdate;
public Dispatcher uiUpdate;
public wThread()
{
uiUpdate = Program.myForm.dispat;
//the uiUpdate seems to be null for some reason... If i am doing it wrong how do i get the dispatcher?
Thread myThread = new Thread(run);
myThread.Start();
}
Action myDelegate = new Action(updateLabel);
// is there a way i can pass a string into the above so updatelabel will work?
public void updateLabel(String text)
{
if (SignalLabelUpdate != null)
SignalLabelUpdate(this, new TextChangedEvent(text));
}
public void run()
{
while (uiUpdate == null)
Thread.Sleep(500);
for (int i = 0; i < 1000; i++)
{
//I hope that the line below would work
uiUpdate.BeginInvoke(new Action(delegate() { Program.myForm.label1.Text = "count at " + i; }));
// was also hoping i can do the below commented code
// uiUpdate.Invoke(myDelegate)
Thread.Sleep(1000);
}
}
}
下面是我的form1.cs,它是visual studio 2012预装的代码,
public partial class Form1 : Form
{
public Dispatcher dispat;
public Form1()
{
dispat = Dispatcher.CurrentDispatcher;
InitializeComponent();
wThread worker = new wThread();
}
}
我的大多数问题都在上面的评论中,但是这些是列出的:
uiUpdate由于某种原因似乎是空的...如果我做错了我怎么得到调度员? (wThread.cs问题)
uiUpdate = Program.myForm.dispat'
有没有办法可以将字符串传递到上面,所以updatelabel会有效吗?
Action myDelegate = new Action(updateLabel);
我希望下面这行能够正常工作
uiUpdate.BeginInvoke(new Action(delegate() { Program.myForm.label1.Text = "count at " + i; }));
也希望我能做以下评论代码
uiUpdate.Invoke(myDelegate)
不幸的是,在我关闭UI之前,wThread不会启动。对此最好的做法是什么?在Application.Run启动我的Form并使用该线程启动我的真实线程之前创建另一个线程?
答案 0 :(得分:0)
@ 1:在Form1
构造函数中,在dispat = Dispatcher.CurrentDispatcher;
放置一个断点并检查值是多少。可能只是Dispatcher.CurrentDispatcher
为空而你必须得到它,即稍晚,而不是在ctor
@ 2是的。使用Func<string>
代替操作。 Invoke
和BeginInvoke
接受委托,还有一组params object[]
形成委托调用的参数。当然,传递的参数数组必须与委托签名完全匹配,因此当使用Func<string>
时,只使用一个对象[]:字符串。
@ 3 - 是的,只要i
是一个可以被委托闭包捕获的简单局部变量,那就行了。如果它是foreach
迭代器或某个非本地成员,它可能会有问题,但是,不同的故事。
@ 4 - 是的,它会起作用,只记得传递Func<string>
的参数。