/// <summary>
        /// Adds a key/page pair to the navigation service.
        /// This method should be used when working with Storyboard for the UI.
        /// </summary>
        /// <param name="key">The key that will be used later
        /// in the <see cref="NavigateTo(string)"/> or <see cref="NavigateTo(string, object)"/> methods.</param>
        /// <param name="storyboardId">The idea of the UIViewController
        /// in the Storyboard. Use the storyboardIdentifier/restorationIdentifier property
        /// in the *.storyboard document.</param>
        public void Configure(string key, string storyboardId)
        {
            var item = new TypeActionOrKey {
                StoryboardControllerKey = storyboardId
            };

            this.SaveConfigurationItem(key, item);
        }
        /// <summary>
        /// Adds a key/page pair to the navigation service.
        /// This method allows the caller to have fine grained control over the controller's
        /// creation.
        /// </summary>
        /// <param name="key">The key that will be used later
        /// in the <see cref="NavigateTo(string)"/> or <see cref="NavigateTo(string, object)"/> methods.</param>
        /// <param name="createAction">A Func returning the controller corresponding
        /// to the given key.</param>
        public void Configure(string key, Func <object, UIViewController> createAction)
        {
            var item = new TypeActionOrKey {
                CreateControllerAction = createAction
            };

            this.SaveConfigurationItem(key, item);
        }
        /// <summary>
        /// Adds a key/page pair to the navigation service.
        /// This method will create a new controller on demand, using
        /// reflection. You can use <see cref="Configure(string, Func{object,UIViewController})"/>
        /// if you need more fine-grained control over the controller's creation.
        /// </summary>
        /// <param name="key">The key that will be used later
        /// in the <see cref="NavigateTo(string)"/> or <see cref="NavigateTo(string, object)"/> methods.</param>
        /// <param name="controllerType">The type of the controller corresponding to the key.</param>
        public void Configure(string key, Type controllerType)
        {
            var item = new TypeActionOrKey {
                ControllerType = controllerType
            };

            this.SaveConfigurationItem(key, item);
        }
 private void SaveConfigurationItem(string key, TypeActionOrKey item)
 {
     lock (_pagesByKey)
     {
         if (_pagesByKey.ContainsKey(key))
         {
             _pagesByKey[key] = item;
         }
         else
         {
             _pagesByKey.Add(key, item);
         }
     }
 }
        private void NavigateTo(string pageKey, object parameter)
        {
            lock (_pagesByKey)
            {
                Exception       creationException = null;
                var             done = false;
                TypeActionOrKey item;

                if (_pagesByKey.ContainsKey(pageKey))
                {
                    item = _pagesByKey[pageKey];
                }
                else
                {
                    item = new TypeActionOrKey
                    {
                        StoryboardControllerKey = pageKey
                    };
                }

                UIViewController controller = null;

                if (item.CreateControllerAction != null)
                {
                    try
                    {
                        controller = item.CreateControllerAction(parameter);
                        done       = true;
                    }
                    catch (Exception ex)
                    {
                        creationException = ex;
                    }
                }

                if (!string.IsNullOrEmpty(item.StoryboardControllerKey))
                {
                    if (NavigationController == null)
                    {
                        throw new InvalidOperationException(
                                  "Unable to navigate: Did you forget to call NavigationService.Initialize?");
                    }

                    if (NavigationController.Storyboard == null)
                    {
                        throw new InvalidOperationException(
                                  "Unable to navigate: No storyboard found. You need to call NavigationService.Configure!");
                    }

                    try
                    {
                        controller =
                            NavigationController.Storyboard.InstantiateViewController(item.StoryboardControllerKey);
                        done = true;
                    }
                    catch (Exception ex)
                    {
                        creationException = ex;
                    }

                    if (parameter != null)
                    {
                        var casted = controller as ControllerBase;
                        if (casted != null)
                        {
                            casted.NavigationParameter = parameter;
                        }

                        // Save parameter in list for later
                        _parametersByController.Add(new WeakReference(controller), parameter);
                    }
                }

                if (!done &&
                    item.ControllerType != null)
                {
                    try
                    {
                        controller = MakeController(item.ControllerType, parameter);

                        if (controller == null)
                        {
                            throw new InvalidOperationException(
                                      "No suitable constructor found for page " + pageKey);
                        }
                    }
                    catch (Exception ex)
                    {
                        creationException = ex;
                    }
                }

                if (controller == null)
                {
                    throw new InvalidOperationException(
                              string.Format(
                                  "Unable to create a controller for key {0}",
                                  pageKey),
                              creationException);
                }

                if (item.ControllerType == null)
                {
                    item.ControllerType = controller.GetType();
                }

                NavigationController.PushViewController(controller, true);
            }
        }
        /// <summary>
        /// Adds a key/page pair to the navigation service.
        /// This method should be used when working with Storyboard for the UI.
        /// </summary>
        /// <param name="key">The key that will be used later
        /// in the <see cref="NavigateTo(string)"/> or <see cref="NavigateTo(string, object)"/> methods.</param>
        /// <param name="storyboardId">The idea of the UIViewController
        /// in the Storyboard. Use the storyboardIdentifier/restorationIdentifier property
        /// in the *.storyboard document.</param>
        public void Configure(string key, string storyboardId)
        {
            var item = new TypeActionOrKey
            {
                StoryboardControllerKey = storyboardId
            };

            SaveConfigurationItem(key, item);
        }
        /// <summary>
        /// Adds a key/page pair to the navigation service.
        /// This method allows the caller to have fine grained control over the controller's
        /// creation.
        /// </summary>
        /// <param name="key">The key that will be used later
        /// in the <see cref="NavigateTo(string)"/> or <see cref="NavigateTo(string, object)"/> methods.</param>
        /// <param name="createAction">A Func returning the controller corresponding
        /// to the given key.</param>
        public void Configure(string key, Func<object, UIViewController> createAction)
        {
            var item = new TypeActionOrKey
            {
                CreateControllerAction = createAction
            };

            SaveConfigurationItem(key, item);
        }
 private void SaveConfigurationItem(string key, TypeActionOrKey item)
 {
     lock (_pagesByKey)
     {
         if (_pagesByKey.ContainsKey(key))
         {
             _pagesByKey[key] = item;
         }
         else
         {
             _pagesByKey.Add(key, item);
         }
     }
 }
        /// <summary>
        /// Adds a key/page pair to the navigation service.
        /// This method will create a new controller on demand, using
        /// reflection. You can use <see cref="Configure(string, Func{object,UIViewController})"/>
        /// if you need more fine-grained control over the controller's creation.
        /// </summary>
        /// <param name="key">The key that will be used later
        /// in the <see cref="NavigateTo(string)"/> or <see cref="NavigateTo(string, object)"/> methods.</param>
        /// <param name="controllerType">The type of the controller corresponding to the key.</param>
        public void Configure(string key, Type controllerType)
        {
            var item = new TypeActionOrKey
            {
                ControllerType = controllerType
            };

            SaveConfigurationItem(key, item);
        }
        /// <summary>
        /// Displays a new page corresponding to the given key,
        /// and passes a parameter to the new page's constructor.
        /// Make sure to call the <see cref="Configure(string, Type)"/>
        /// or <see cref="Configure(string, Func{object,UIViewController})"/>
        /// method first.
        /// </summary>
        /// <param name="pageKey">The key corresponding to the page
        /// that should be displayed.</param>
        /// <param name="parameter">The parameter that should be passed
        /// to the new page's constructor.</param>
        /// <exception cref="ArgumentException">When this method is called for
        /// a key that has not been configured earlier.</exception>
        /// <exception cref="InvalidOperationException">When this method is called for
        /// a page that doesn't have a suitable constructor (i.e.
        /// a constructor with a parameter corresponding to the
        /// navigation parameter's type).</exception>
        public void NavigateTo(string pageKey, object parameter)
        {
            lock (_pagesByKey)
            {
                Exception       creationException = null;
                var             done = false;
                TypeActionOrKey item;

                if (_pagesByKey.ContainsKey(pageKey))
                {
                    item = _pagesByKey[pageKey];
                }
                else
                {
                    item = new TypeActionOrKey
                    {
                        StoryboardControllerKey = pageKey
                    };
                }

                UIViewController controller = null;

                if (item.CreateControllerAction != null)
                {
                    try
                    {
                        controller = item.CreateControllerAction(parameter);
                        done       = true;
                    }
                    catch (Exception ex)
                    {
                        creationException = ex;
                    }
                }

                if (!string.IsNullOrEmpty(item.StoryboardControllerKey))
                {
                    if (NavigationController == null)
                    {
                        throw new InvalidOperationException("Unable to navigate: Did you forget to call NavigationService.Initialize?");
                    }

                    if (NavigationController.Storyboard == null && _mainStoryboard == null)
                    {
                        throw new InvalidOperationException("Unable to navigate: No storyboard found. You need to call NavigationService.Configure!");
                    }

                    try
                    {
                        if (pageKey == App.LIST_SEEKIOS_PAGE)
                        {
                            _mainStoryboard = UIStoryboard.FromName("Main", null);
                            var listSeekiosView = _mainStoryboard.InstantiateViewController("ListSeekiosView") as iOS.ListSeekiosView;
                            LeftMenuView = _mainStoryboard.InstantiateViewController("MenuController") as iOS.Menu.MenuController;

                            var frontViewController = new UINavigationController(listSeekiosView);
                            var revealController    = new SWRevealViewController(LeftMenuView, frontViewController);

                            frontViewController.View.AddGestureRecognizer(revealController.PanGestureRecognizer);
                            frontViewController.View.AddGestureRecognizer(revealController.TapGestureRecognizer);

                            listSeekiosView.SliderViewButton.Target   = revealController;
                            listSeekiosView.SliderViewButton.Clicked += (sender, args) =>
                            {
                                revealController.RevealToggleAnimated(true);
                            };

                            revealController.RearViewRevealWidth = UIScreen.MainScreen.Bounds.Size.Width - 45.0f;

                            Initialize(listSeekiosView.NavigationController);
                            UIApplication.SharedApplication.KeyWindow.RootViewController = revealController;

                            return;
                        }
                        else if (NavigationController.Storyboard != null)
                        {
                            controller = NavigationController.Storyboard.InstantiateViewController(item.StoryboardControllerKey);
                        }
                        else if (_mainStoryboard != null)
                        {
                            if (pageKey == App.TUTORIAL_BACKGROUND_FIRST_LAUNCH_PAGE)
                            {
                                if (!App.Locator.Login.GetSavedFirstLaunchTuto())
                                {
                                    UIApplication.SharedApplication.KeyWindow.RootViewController = _mainStoryboard.InstantiateViewController("TutorialBackgroundView") as iOS.TutorialBackgroundView;
                                    return;
                                }
                                else
                                {
                                    controller = _mainStoryboard.InstantiateViewController(item.StoryboardControllerKey);
                                }
                            }
                            else
                            {
                                controller = _mainStoryboard.InstantiateViewController(item.StoryboardControllerKey);
                            }
                        }
                        done = true;
                    }
                    catch (Exception ex)
                    {
                        creationException = ex;
                    }

                    if (parameter != null)
                    {
                        var casted = controller as ControllerBase;
                        if (casted != null)
                        {
                            casted.NavigationParameter = parameter;
                        }
                        // Save parameter in list for later
                        _parametersByController.Add(new WeakReference(controller), parameter);
                    }
                }

                if (!done && item.ControllerType != null)
                {
                    try
                    {
                        controller = MakeController(item.ControllerType, parameter);

                        if (controller == null)
                        {
                            throw new InvalidOperationException(
                                      "No suitable constructor found for page " + pageKey);
                        }
                    }
                    catch (Exception ex)
                    {
                        creationException = ex;
                    }
                }

                if (controller == null)
                {
                    throw new InvalidOperationException(
                              string.Format(
                                  "Unable to create a controller for key {0}",
                                  pageKey),
                              creationException);
                }

                if (item.ControllerType == null)
                {
                    item.ControllerType = controller.GetType();
                }

                NavigationController.PushViewController(controller, true);
            }
        }