In a previous question I asked how to get access to UI elements in a callback thread. I got a lot of good answers, one of which was to implement a wrapper class such as this:
public static class UIThread
{
private static readonly Dispatcher Dispatcher;
static UIThread()
{
Dispatcher = Deployment.Current.Dispatcher;
}
public static void Invoke(Action action)
{
if (Dispatcher.CheckAccess())
{
action.Invoke();
}
else
{
Dispatcher.BeginInvoke(action);
}
}
}
And you can call this using
UIThread.Invoke(() => TwitterPost.Text = "hello there");
However I tried extending this by calling the following in my callback function
UIThread.Invoke(() => loadUserController(jsonObject));
with the following method:
private void loadUserController(JObject jsonObject)
{
string profile_image_url = (string)jsonObject["profile_image_url"];
string screen_name = (string)jsonObject["screen_name"];
string name = (string)jsonObject["name"];
string location开发者_JS百科 = (string)jsonObject["location"];
int statuses_count = (int)jsonObject["statuses_count"];
if (!string.IsNullOrEmpty(profile_image_url))
{
ProfileImage.Source = new BitmapImage(new Uri("blahblahbalhb.jpg", UriKind.Absolute));
}
// Set the screen name and display name if it differs
if (!string.IsNullOrEmpty(name) && !string.IsNullOrEmpty(screen_name))
{
ScreenName.Text = screen_name;
if (!screen_name.Equals(name))
{
_Name.Text = name;
}
}
if (!string.IsNullOrEmpty(location))
{
Location.Text = location;
}
Tweets.Text = statuses_count.ToString() + " Tweets";
}
then the image will not render until another action forces a redraw (clicking a button) but the text controls will be updated. If within my callback function I call setImageFile(string imageFile) which is implemented as:
private void setImageFile(string imageFile)
{
if (this.Dispatcher.CheckAccess())
{
ProfileImage.Source = new BitmapImage(new Uri("fdsfdfdsf.jpg", UriKind.Absolute));
}
else
{
this.Dispatcher.BeginInvoke(new Action<string>(setImageFile), imageFile);
}
}
then the image will be rendered immediately. Why is this happening? What properties of the Dispatcher am I not fully understanding?
I strongly recommend that you not do this. SynchronizationObject
was designed to handle this kind of scenario, along with AsyncOperation
and AsyncOperationManager
.
The only disadvantage to SynchronizationObject
is that there isn't the ability to test whether the code is already running on the correct thread. That shouldn't be a problem, since business logic code should always be aware of its thread context.
精彩评论