Beispiel #1
0
            // TODO (CR Apr 2013): the reason this is overloaded is because there's not always a task to return. Would be better
            // to return some other object, possibly with the task as a property, but also with the volume itself, if it's available.
            private Task LoadAsync(VolumeLoadProgressCallback onProgress = null, VolumeLoadCompletionCallback onComplete = null, VolumeLoadErrorCallback onError = null)
            {
                AssertNotDisposed();

                // TODO (CR Apr 2013): Not a good idea to return nothing; why not return a struct with the volume in it?
                if (_volumeReference != null)
                {
                    return(null);
                }
                if (_backgroundLoadTask != null)
                {
                    return(_backgroundLoadTask);
                }

                lock (_backgroundLoadSyncRoot)
                {
                    if (_volumeReference != null)
                    {
                        return(null);
                    }
                    if (_backgroundLoadTask != null)
                    {
                        return(_backgroundLoadTask);
                    }

                    _backgroundLoadTask = new Task(() => LoadCore(onProgress));
                    _backgroundLoadTask.ContinueWith(t =>
                    {
                        // TODO (CR Apr 2013): Can probably just lock the part that
                        // changes the _backgroundLoadTask variable.
                        lock (_backgroundLoadSyncRoot)
                        {
                            if (t.IsFaulted && t.Exception != null)
                            {
                                var ex = t.Exception.Flatten().InnerExceptions.FirstOrDefault();
                                if (onError != null)
                                {
                                    onError.Invoke(this, ex);
                                }
                                else
                                {
                                    Platform.Log(LogLevel.Warn, ex, "Unhandled exception thrown in background volume loader");
                                }
                            }
                            else
                            {
                                if (onComplete != null)
                                {
                                    onComplete.Invoke(this);
                                }
                            }

                            if (ReferenceEquals(t, _backgroundLoadTask))
                            {
                                _backgroundLoadTask.Dispose();
                                _backgroundLoadTask = null;
                            }
                        }
                    });
                    _backgroundLoadTask.Start();
                    return(_backgroundLoadTask);
                }
            }
Beispiel #2
0
 // TODO (CR Apr 2013): API is a bit overloaded; the task provides completion and error info already
 // so probably all that is needed is the progress callback argument.
 public Task LoadAsync(VolumeLoadProgressCallback onProgress = null, VolumeLoadCompletionCallback onComplete = null, VolumeLoadErrorCallback onError = null)
 {
     return(_cachedVolume.LoadAsync(onProgress, onComplete, onError));
 }
Beispiel #3
0
            private IAsyncResult LoadAsync(VolumeLoadProgressCallback onProgress = null, VolumeLoadCompletionCallback onComplete = null, VolumeLoadErrorCallback onError = null)
            {
                AssertNotDisposed();

                if (_volumeReference != null)
                {
                    return(null);
                }
                if (_backgroundLoadMethod != null)
                {
                    return(_backgroundLoadMethodAsyncResult);
                }

                lock (_backgroundLoadSyncRoot)
                {
                    if (_volumeReference != null)
                    {
                        return(null);
                    }
                    if (_backgroundLoadMethod != null)
                    {
                        return(_backgroundLoadMethodAsyncResult);
                    }

                    _backgroundLoadMethod = () =>
                    {
                        try
                        {
                            LoadCore(onProgress);

                            if (onComplete != null)
                            {
                                onComplete.Invoke(this);
                            }
                        }
                        catch (Exception ex)
                        {
                            if (onError != null)
                            {
                                onError.Invoke(this, ex);
                            }
                            else
                            {
                                Platform.Log(LogLevel.Debug, ex, "Unhandled exception thrown in asynchronous volume loader");
                            }
                        }
                    };
                    return(_backgroundLoadMethodAsyncResult = _backgroundLoadMethod.BeginInvoke(ar =>
                    {
                        _backgroundLoadMethod.EndInvoke(ar);
                        _backgroundLoadMethod = null;
                        _backgroundLoadMethodAsyncResult = null;
                    }, null));
                }
            }