Beispiel #1
0
        /// <summary>
        /// Begins loading routines for the specified fileReference, which is expected to point to a valid model.
        /// This function takes a delegate which will correctly load the file pointed to by the FileReference,
        /// and another delegate which will create a correct <see cref="IRenderable"/> object from the resulting
        /// object.
        /// </summary>
        /// <param name="fileReference">A <see cref="FileReference"/> which points to the desired file.</param>
        /// <param name="referenceLoadingRoutine">A delegate which correctly loads the desired file, returning a generic type T.</param>
        /// <param name="createRenderableDelegate">A delegate which accepts a generic type T and returns a renderable object.</param>
        /// <param name="associatedControlPage">The control page which the file is associated with, that is, the one with relevant controls.</param>
        /// <typeparam name="T">The type of model to load.</typeparam>
        private void BeginLoadingFile <T>(
            FileReference fileReference,
            DataLoadingDelegates.LoadReferenceDelegate <T> referenceLoadingRoutine,
            DataLoadingDelegates.CreateRenderableDelegate <T> createRenderableDelegate,
            ControlPage associatedControlPage)
        {
            Log.Info($"Loading \"{fileReference.FilePath}\".");

            this.StatusSpinner.Active = true;

            string modelName = fileReference.Filename;
            uint   modelStatusMessageContextID = this.MainStatusBar.GetContextId($"itemLoad_{modelName}");
            uint   modelStatusMessageID        = this.MainStatusBar.Push(modelStatusMessageContextID,
                                                                         $"Loading \"{modelName}\"...");

            Task.Factory.StartNew(() => referenceLoadingRoutine(fileReference))
            .ContinueWith(modelLoadTask => createRenderableDelegate(modelLoadTask.Result, fileReference), this.UIThreadScheduler)
            .ContinueWith(createRenderableTask => this.RenderingEngine.SetRenderTarget(createRenderableTask.Result), this.UIThreadScheduler)
            .ContinueWith
            (
                result =>
            {
                this.StatusSpinner.Active = false;
                this.MainStatusBar.Remove(modelStatusMessageContextID, modelStatusMessageID);
                EnableControlPage(associatedControlPage);
            },
                this.UIThreadScheduler
            );
        }
Beispiel #2
0
        /// <summary>
        /// Loads and displays the specified fileReference in the UI, which is expected to point to a valid object.
        /// This function takes a delegate which will correctly load the file pointed to by the FileReference,
        /// and another delegate which will create a correct <see cref="IRenderable"/> object from the resulting
        /// object.
        /// </summary>
        /// <param name="gamePage">The game page that the renderable originated from.</param>
        /// <param name="fileReference">A <see cref="FileReference"/> which points to the desired file.</param>
        /// <param name="referenceLoadingRoutine">A delegate which correctly loads the desired file, returning a generic type T.</param>
        /// <param name="createRenderableDelegate">A delegate which accepts a generic type T and returns a renderable object.</param>
        /// <param name="associatedControlPage">The control page which the file is associated with, that is, the one with relevant controls.</param>
        /// <param name="ct">A cancellation token for this operation.</param>
        /// <typeparam name="T">The type of object to load.</typeparam>
        private async Task DisplayRenderableFile <T>(
            GamePage gamePage,
            FileReference fileReference,
            DataLoadingDelegates.LoadReferenceDelegate <T> referenceLoadingRoutine,
            DataLoadingDelegates.CreateRenderableDelegate <T> createRenderableDelegate,
            ControlPage associatedControlPage,
            CancellationToken ct)
        {
            if (fileReference == null)
            {
                throw new ArgumentNullException(nameof(fileReference));
            }

            Log.Info($"Loading \"{fileReference.FilePath}\".");

            this.StatusSpinner.Active = true;

            string modelName = fileReference.Filename;
            uint   modelStatusMessageContextID = this.MainStatusBar.GetContextId($"itemLoad_{modelName}");
            uint   modelStatusMessageID        = this.MainStatusBar.Push
                                                 (
                modelStatusMessageContextID,
                $"Loading \"{modelName}\"..."
                                                 );

            try
            {
                T item = await Task.Run
                         (
                    () => referenceLoadingRoutine(fileReference),
                    ct
                         );

                IRenderable renderable = await Task.Factory.StartNew
                                         (
                    () => createRenderableDelegate(item, fileReference, gamePage.Version),
                    ct,
                    TaskCreationOptions.None,
                    this.UiThreadScheduler
                                         );

                if (renderable != null)
                {
                    ct.ThrowIfCancellationRequested();

                    // Replace the renderable on the UI thread
                    await Task.Factory.StartNew
                    (
                        () => this.RenderingEngine.SetRenderTarget(renderable),
                        ct,
                        TaskCreationOptions.None,
                        this.UiThreadScheduler
                    );

                    EnableControlPage(associatedControlPage);
                }
            }
            catch (OperationCanceledException)
            {
                Log.Info($"Cancelled loading of {fileReference.Filename}");
            }
            finally
            {
                this.StatusSpinner.Active = false;
                this.MainStatusBar.Remove(modelStatusMessageContextID, modelStatusMessageID);
            }
        }