I'm developing a Windows Metro app, and am getting an issue with the UI becoming unresponsive. As far as I can tell, the cause is as follows:
<ListView
...
SelectionChanged="ItemListView_SelectionChanged"
...
This event is handled here:
async void ItemListView_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
if (this.UsingLogicalPageNavigation()) this.InvalidateVisualState();
MyDataItem dataItem = e.AddedItems[0] as MyDataItem;
await LoadMyPage(dataItem);
}
private async Task LoadMyPage(MyDataItem dataItem)
{
SyndicationClient client = new SyndicationClient();
SyndicationFeed feed = await client.RetrieveFeedAsync(new Uri(FEED_URI));
string html = ConvertRSSToHtml(feed)
myWebView.NavigateToString(html, true);
}
LoadMyPage
takes a while to complete, as it gets data from a web service and loads it onto the screen. However, it looks like the UI is waiting for it: my guess is that until the above event completes.
So my question is: what can I do about this? Is there a better event I can hook into, or is there another way to handle this? I thought about starting a background task, but that seems like overkill to me.
EDIT:
Just to clarify the scale of this problem, I'm talking about a maximum of 3 - 4 seconds unresponsive. This is by no means a long running job.
EDIT:
I've tried some of the suggestion below, however, the entire call stack from the SelectionChanged
function is using async/await. I've tracked it down to this statement:
myFeed = await client.RetrieveFeedAsync(uri);
Which doesn't seem to be continuing processing until it's complete.
EDIT:
I realise this is turning into War & Peace, but below is a replication of the problem using a blank metro app and a button:
XAML:
<Grid Background="{StaticResource ApplicationPageBackgroundThemeBrush}">
<StackPanel>
<Button Click="Button_Click_1" Width="200" Height="200">test</Button>
<TextBlock x:Name="test"/>
</StackPanel>
</Grid>
Code behind:
private async void Button_Click_1(object sender, RoutedEventArgs e)
{
SyndicationFeed feed = null;
SyndicationClient client = new SyndicationClient();
Uri feedUri = new Uri(myUri);
try
{
feed = await client.RetrieveFeedAsync(feedUri);
foreach (var item in feed.Items)
{
test.Text += item.Summary.Text + Environment.NewLine;
}
}
catch
{
test.Text += "Connection failed\n";
}
}
foreach
loop altogether – Paul Michaels