0

I'm currently looking into both windows store apps & wp8 apps, both being sl and c# projects.

Fetching the dispatcher is different from wpf, and I'm a bit pussled as the one in Window.Current seems to disappear in some of my async methods.

All I could do was basicly just to put a propery in the App class, but it seems so unsafe, I don't follow the logics here.

I'll post an example:

internal class MainviewModel : ViewModelBase 
{
 ..............
    private async void GetLastDocumetAsync()
    {
            // Window.Current is null here, but not outside async!
            await Window.Current.Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
            {
                ObservableCollection<ScannedDocument> docs = await ServiceLocator.DocumentClient.GetLastScannedDocumentsAsync();                    
                ScannedDocuments.AddRange(docs);
                SelectedDocument = ScannedDocuments.LastOrDefault();
            }
    }
    ...
    public void SomeMethod(){
        // Window.Current is not null
        Task.Factory.StartNew(() => GetLastDocumetAsync());

    }
}

When SomeMethod() is called, Window.Current is not null. When we're in the async method, and I need the dispatcher, it's null.

Any pointers?

Brgds,

polkaextremist

1 Answers1

2

First, I strongly recommend as much as possible to restructure your code so that explicit capturing and restoring of the context isn't necessary. As long as you just use plain async and await, you won't need to capture the context at all.

In your example code, there's no need for StartNew, so you could do something like this:

private async Task GetLastDocumentsAsync()
{
    ObservableCollection<ScannedDocument> docs = await ServiceLocator.DocumentClient.GetLastScannedDocumentsAsync();                    
    ScannedDocuments.AddRange(docs);
    SelectedDocument = ScannedDocuments.LastOrDefault();
}

public async Task SomeMethodAsync()
{
    await GetLastDocumentsAsync();
    ...
}

If you really do need to explicitly capture a context, I recommend you use SynchronizationContext. You can think of it sort of like a cross-platform Dispatcher; I have more info in my MSDN article.

Stephen Cleary
  • 437,863
  • 77
  • 675
  • 810