a Control on a windows forms from another thread from, the Invoke () method of the form or controls are used. A Control can only be changed by the thread from which it was created!
following minimal example (incomplete ) shows a use case in which a thread reports its status to a form: The class
MathClass generated Thread objects whose method CalcBackground () should ausgefürt in a thread wird.Aus this method out the GUI on the current thread state be informed:
1:
2: public class MathClass
3: {
4:
5: private MainForm myForm;
6: private int iNumber ;
7:
8: public Thread Initialize(MainForm myform, int number)
9: {
10: this .myForm = myform;
11: this .iNumber = number;
12: return new Thread( new ThreadStart( this .CalcBackground));
13: }
14:
15: delegate void UpdateUI( int number, int state);
16: delegate void Finish( int number);
17:
18: public void CalcBackground()
19: {
20: UpdateUI updateUI = new UpdateUI( this .myForm.updateUIProc);
21: Finish finish = new Finish( this .myForm.FinishThread);
22:
23: try
24: {
25: // do something
26: // ...
27: // report status to form:
28: object [] param = new object [2] { this .iNumber, i };
29: myForm.Invoke(updateUI, param); // call myForm.updateUIProc(iNumber, i)
30: }
31: catch (ThreadAbortException)
32: {
33: // clean up
34: }
35: catch (Exception)
36: {
37: // catch any other exception
38: }
39: finally
40: {
41: try
42: {
43: // call myForm.FinishThread(iNumber)
44: myForm.Invoke(finish, new object [] { this .iNumber });
45: }
46: catch (ObjectDisposedException e)
47: {
48: }
49: catch (Exception ee)
50: {
51:
} 52:}
53:}
54:
55:}
created the Main form in the method StartThreads () two new threads. The methods updateUIProc () finish and thread () be started by Invoke () method of thread from the thread and run myself the Main Form :
1: public partial class MainForm : Form
2: {
3:
4: public MainForm()
5: {
6: InitializeComponent();
7: }
8:
9: private void Form1_FormClosing( object sender, FormClosingEventArgs e)
10: {
11: // kill threads before form closes
12: if (anyThreadAlive)
13: {
14: killThreads();
15: }
16: }
17:
18: public void updateUIProc( int number, int val)
19: {
20: this .textBox1.AppendText(
21: string .Format( "thread {0} has done {1} % of its job" , number, val));
22: }
23:
24: public void FinishThread( int number)
25: {
26: this .textBox1.AppendText(
27: string .Format( "thread {0} has finished" , number));
28: }
29:
30: private void startThreads()
31: {
32: Thread th1 = new MathClass().Initialize( this , 0);
33: Thread th2 = new MathClass().Initialize( this , 1);
34: th1.Start();
35: th2.Start ();
36:
} 37:}
It is not allowed to change the Control Mainform.textBox1 directly from the thread. A Control can only be changed by the thread from which it was created. order to still change a control from a thread out, use the method Invoke () and passes this one delegate (function pointer) and a parameter array. The actual method (eg updateUIProc () or finish thread ()) is then (in this case) in the thread of the main form. This has also means that neither of the two functions can be executed in parallel several times.
0 comments:
Post a Comment