大家知道WPF中多线程访问UI控件时会提示UI线程的数据不能直接被其他线程访问或者修改,该怎样来做呢?
分下面两种情况
1.WinForm程序
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
|
1)第一种方法,使用委托: private delegate void SetTextCallback( string text); private void SetText( string text) { // InvokeRequired需要比较调用线程ID和创建线程ID // 如果它们不相同则返回true if ( this .txt_Name.InvokeRequired) { SetTextCallback d = new SetTextCallback(SetText); this .Invoke(d, new object [] { text }); } else { this .txt_Name.Text = text; } } 2)第二种方法,使用匿名委托 private void SetText(Object obj) { if ( this .InvokeRequired) { this .Invoke( new MethodInvoker( delegate { this .txt_Name.Text = obj; })); } else { this .txt_Name.Text = obj; } } 这里说一下BeginInvoke和Invoke和区别:BeginInvoke会立即返回,Invoke会等执行完后再返回。 |
2.WPF程序
1)可以使用Dispatcher线程模型来修改
如果是窗体本身可使用类似如下的代码:
1
2
3
4
|
this .lblState.Dispatcher.Invoke( new Action( delegate { this .lblState.Content = "状态:" + this ._statusText; })); |
那么假如是在一个公共类中弹出一个窗口、播放声音等呢?这里我们可以使用:System.Windows.Application.Current.Dispatcher,如下所示
1
2
3
4
5
6
7
8
|
System.Windows.Application.Current.Dispatcher.Invoke( new Action(() => { if (path.EndsWith( ".mp3" ) || path.EndsWith( ".wma" ) || path.EndsWith( ".wav" )) { _player.Open( new Uri(path)); _player.Play(); } })); |