예제 #1
0
        /// <summary>
        /// Sets the active section using the provided section name and navigates.
        /// </summary>
        /// <typeparam name="TViewModel">The type of the view model.</typeparam>
        /// <param name="sectionsNavigator">The sections navigator.</param>
        /// <param name="ct">The cancellation token.</param>
        /// <param name="sectionName">The name of the section to set as active.</param>
        /// <param name="viewModelProvider">The method to make the view model instance. It will be invoked only if necessary.</param>
        /// <param name="returnToRoot">When this is true, the navigator will navigate back to the view model matching the type <typeparamref name="TViewModel"/>.</param>
        /// <returns>The stack navigator of the active section.</returns>
        public static async Task <ISectionStackNavigator> SetActiveSection <TViewModel>(this ISectionsNavigator sectionsNavigator,
                                                                                        CancellationToken ct,
                                                                                        string sectionName,
                                                                                        Func <TViewModel> viewModelProvider,
                                                                                        bool returnToRoot = false)
            where TViewModel : INavigableViewModel
        {
            if (ct.IsCancellationRequested)
            {
                typeof(SectionsNavigatorExtensions).Log().LogWarning($"Canceled 'SetActiveSection' operation to '{typeof(TViewModel).Name}' because of cancellation token.");

                return(null);
            }

            // No cancellation beyond this point.
            ct = CancellationToken.None;

            var sectionNavigator = sectionsNavigator.State.Sections[sectionName];

            if (sectionNavigator.State.Stack.LastOrDefault() == null)
            {
                // Create the default page if there's nothing in the section.
                await sectionNavigator.Navigate(ct, StackNavigatorRequest.GetNavigateRequest(viewModelProvider, suppressTransition: true));
            }
            else if (returnToRoot && sectionNavigator.State.Stack.Last().ViewModel.GetType() != typeof(TViewModel))
            {
                if (sectionNavigator.State.Stack.Any(e => e.ViewModel.GetType() == typeof(TViewModel)))
                {
                    // If the stack contains the root page of the section, remove all other entries and navigate back to it.
                    var indexesToRemove = sectionNavigator.State.Stack
                                          .Select((entry, index) => (entry, index))
                                          .Where(t => t.entry.ViewModel.GetType() != typeof(TViewModel) && t.index < sectionNavigator.State.Stack.Count - 1)
                                          .Select(t => t.index)
                                          .ToList();

                    await sectionNavigator.RemoveEntries(ct, indexesToRemove);

                    await sectionNavigator.NavigateBack(ct);
                }
                else
                {
                    // If the section root page isn't in the stack, clear everything and navigate to it.
                    await sectionNavigator.Navigate(ct, StackNavigatorRequest.GetNavigateRequest(viewModelProvider, suppressTransition: true, clearBackStack: true));
                }
            }

            return(await sectionsNavigator.SetActiveSection(ct, SectionsNavigatorRequest.GetSetActiveSectionRequest(sectionName)));
        }
예제 #2
0
 /// <summary>
 /// Sets the active section using the provided section name.
 /// </summary>
 /// <param name="sectionsNavigator">The sections navigator.</param>
 /// <param name="ct">The cancellation token.</param>
 /// <param name="sectionName">The name of the section to set as active.</param>
 /// <returns>The stack navigator of the active section.</returns>
 public static Task <ISectionStackNavigator> SetActiveSection(this ISectionsNavigator sectionsNavigator, CancellationToken ct, string sectionName)
 {
     return(sectionsNavigator.SetActiveSection(ct, SectionsNavigatorRequest.GetSetActiveSectionRequest(sectionName)));
 }