我遇到了对silverlight的busyindicator控件的问题。 我有一个datagrid(datagrid1),其源设置为wcf服务(客户端)。 当datagrid加载自己时,我想使用silvelright工具包的busyindicator控件(bi)。
但是当我使用“ThreadPool”时,我有一个“无效的跨线程访问”。
Sub LoadGrid()
Dim caisse As Integer = ddl_caisse.SelectedValue
Dim env As Integer = ddl_env.SelectedValue
bi.IsBusy = True
ThreadPool.QueueUserWorkItem(Sub(state)
AddHandler client.Get_PosteSPTCompleted, AddressOf client_Get_PosteSPTCompleted
client.Get_PosteSPTAsync(caisse, env)
Dispatcher.BeginInvoke(Sub()
bi.IsBusy = False
End Sub)
End Sub)
End Sub
Private Sub client_Get_PosteSPTCompleted(sender As Object, e As ServiceReference1.Get_PosteSPTCompletedEventArgs)
DataGrid1.ItemsSource = e.Result ' Here, Invalid cross thread access
End Sub
我知道“新线程”中不存在datagrid控件,但是我必须如何避免此错误?
谢谢。
威廉
答案 0 :(得分:1)
ThreadPool
?如果您的服务是同步的,那么使用ThreadPool
将是一个好主意,但您的WCF服务是异步的:它在使用Get_PosteSPTAsync
调用后不会阻止您的UI线程。
IsBusy
财产似乎存在问题。您首先将其设置为true
,然后异步启动操作,然后立即将其设置为false
。您应该在Completed
处理程序中将其设置为false。client_Get_PosteSPTCompleted
处理程序不会在与UI线程相同的线程中执行(即使您不使用ThreadPool
)。这就是为什么你必须在这里使用调度程序所以强制使用UI线程。您的DataGrid1.ItemsSource = e.Result
必须修改为:
Dispatcher.BeginInvoke(Sub()
DataGrid1.ItemsSource = e.Result ' Fixes the UI thread issue
bi.IsBusy = False ' Sets busy as false AFTER completion (see point 2)
End Sub)
(请注意VB.Net语法,但这就是想法)
client
对象的生命周期,但每次调用Get_PosteSPTCompleted
时,您都会向LoadGrid
添加新的处理程序。也许您可以考虑在使用后分离处理程序。