From 34590fbc7d5235d43a5aa44cd194e879fb0356d6 Mon Sep 17 00:00:00 2001 From: Tobias Reski Date: Tue, 9 Nov 2021 14:22:53 +0100 Subject: [PATCH] Fixed issue where location permissions was called infinite times on decline. --- TINK/TINK/App.xaml.cs | 2 +- TINK/TINK/View/Map/MapPage.xaml.cs | 91 +++++++++++++++-------- TINKLib/ViewModel/Map/MapPageViewModel.cs | 41 ++++++---- 3 files changed, 89 insertions(+), 45 deletions(-) diff --git a/TINK/TINK/App.xaml.cs b/TINK/TINK/App.xaml.cs index bcae1d1..85b826f 100644 --- a/TINK/TINK/App.xaml.cs +++ b/TINK/TINK/App.xaml.cs @@ -282,7 +282,7 @@ namespace TINK if (_PermissionsService != null) return _PermissionsService; - _PermissionsService = new Services.Permissions.Plugin.Permissions(); + _PermissionsService = new Services.Permissions.Essentials.Permissions(); return _PermissionsService; } } diff --git a/TINK/TINK/View/Map/MapPage.xaml.cs b/TINK/TINK/View/Map/MapPage.xaml.cs index f8907a1..02a8d14 100644 --- a/TINK/TINK/View/Map/MapPage.xaml.cs +++ b/TINK/TINK/View/Map/MapPage.xaml.cs @@ -21,6 +21,9 @@ namespace TINK.View.Map /// View model to notify about whether page appears or hides. private MapPageViewModel MapPageViewModel { get; set; } + /// Initialization status to ensure initialization logic is not called multiple times. + private bool viewInitialized = false; + /// /// Constructs map page instance. /// @@ -125,30 +128,22 @@ namespace TINK.View.Map public INavigationMasterDetail NavigationMasterDetail { private get; set; } #endif + /// /// Invoked when page is shown. /// Starts update process. /// protected async override void OnAppearing() { + // Don't repeat the initialization if it has been completed already. + if (viewInitialized) return; + // Pass reference to member Navigation to show bikes at station x dialog. try { - Log.ForContext().Verbose("Constructing map page view model."); - -#if TRYNOTBACKSTYLE - MapPageViewModel = new MapPageViewModel(); -#else - MapPageViewModel = new MapPageViewModel( - App.ModelRoot, - App.PermissionsService, - App.BluetoothService, - App.GeolocationServicesContainer.Active, - (mapspan) => MyMap.MoveToRegion(mapspan), - this, - Navigation); -#endif - } catch (Exception exception) + MapPageViewModel = createMapPageViewModel(); + } + catch (Exception exception) { Log.ForContext().Error("Constructing map page view model failed. {Exception}", exception); @@ -171,15 +166,7 @@ namespace TINK.View.Map try { - if (Device.RuntimePlatform == Device.iOS) - { - TINKButton.BackgroundColor = Color.LightGray; - TINKButton.BorderColor = Color.Black; - TINKButton.Margin = new Thickness(10, 10, 10, 10); - KonradButton.BackgroundColor = Color.LightGray; - KonradButton.BorderColor = Color.Black; - KonradButton.Margin = new Thickness(10, 10, 10, 10); - } + applyCustomiOSStyling(); } catch (Exception exception) { @@ -201,11 +188,7 @@ namespace TINK.View.Map try { // Pre move and scanle maps to avoid initial display of map in Rome. - Log.ForContext().Verbose("Moving and scaling map."); - MapPageViewModel.MoveAndScale( - (mapSpan) => MyMap.MoveToRegion(mapSpan), - App.ModelRoot.Uris.ActiveUri, - App.ModelRoot.GroupFilterMapPage); + premoveAndScaleMap(); } catch(Exception exception) { @@ -223,6 +206,54 @@ namespace TINK.View.Map Log.ForContext().Error("Invoking OnAppearing on map page view model failed. {Exception}", exception); return; } + viewInitialized = true; + } + + + /// + /// Premoves the Map to a certain location. + /// + private void premoveAndScaleMap() + { + Log.ForContext().Verbose("Moving and scaling map."); + MapPageViewModel.MoveAndScale( + (mapSpan) => MyMap.MoveToRegion(mapSpan), + App.ModelRoot.Uris.ActiveUri, + App.ModelRoot.GroupFilterMapPage); + } + + + /// + /// Creates the Map Page's view model. + /// + private MapPageViewModel createMapPageViewModel() + { + Log.ForContext().Verbose("Constructing map page view model."); + return new MapPageViewModel( + App.ModelRoot, + App.PermissionsService, + App.BluetoothService, + App.GeolocationServicesContainer.Active, + (mapspan) => MyMap.MoveToRegion(mapspan), + this, + Navigation); + } + + + /// + /// Applies iOS specific styling to branded Buttons. + /// + private void applyCustomiOSStyling() + { + if (Device.RuntimePlatform == Device.iOS) + { + TINKButton.BackgroundColor = Color.LightGray; + TINKButton.BorderColor = Color.Black; + TINKButton.Margin = new Thickness(10, 10, 10, 10); + KonradButton.BackgroundColor = Color.LightGray; + KonradButton.BorderColor = Color.Black; + KonradButton.Margin = new Thickness(10, 10, 10, 10); + } } /// @@ -236,7 +267,7 @@ namespace TINK.View.Map // View model might be null. await MapPageViewModel?.OnDisappearing(); } - + viewInitialized = false; base.OnDisappearing(); } } diff --git a/TINKLib/ViewModel/Map/MapPageViewModel.cs b/TINKLib/ViewModel/Map/MapPageViewModel.cs index e896765..2d55ccc 100644 --- a/TINKLib/ViewModel/Map/MapPageViewModel.cs +++ b/TINKLib/ViewModel/Map/MapPageViewModel.cs @@ -322,9 +322,9 @@ namespace TINK.ViewModel.Map && !GeolocationService.IsSimulation && status != Status.Granted) { - var permissionResult = await PermissionsService.RequestAsync(); + status = await PermissionsService.RequestAsync(); - if (permissionResult != Status.Granted) + if (status != Status.Granted) { var dialogResult = await ViewService.DisplayAlert( AppResources.MessageTitleHint, @@ -420,19 +420,8 @@ namespace TINK.ViewModel.Map // Move and scale before getting stations and bikes which takes some time. ActionText = AppResources.ActivityTextCenterMap; - Location currentLocation = null; - try - { - currentLocation = TinkApp.CenterMapToCurrentLocation - ? await GeolocationService.GetAsync() - : null; - } - catch (Exception ex) - { - Log.ForContext().Error("Getting location failed. {Exception}", ex); - } - MoveAndScale(m_oMoveToRegionDelegate, TinkApp.Uris.ActiveUri, ActiveFilterMap, currentLocation); + moveMapToCurrentPositionOfUser(); m_oViewUpdateManager = CreateUpdateTask(); @@ -468,6 +457,30 @@ namespace TINK.ViewModel.Map } } + /// + /// Moves the map to the current position of the user. + /// If location permission hasn't been granted, the position is not adjusted. + /// + private async void moveMapToCurrentPositionOfUser() + { + var status = await PermissionsService.CheckStatusAsync(); + if (status != Status.Granted) return; + Location currentLocation = null; + try + { + currentLocation = TinkApp.CenterMapToCurrentLocation + ? await GeolocationService.GetAsync() + : null; + } + catch (Exception ex) + { + Log.ForContext().Error("Getting location failed. {Exception}", ex); + } + + MoveAndScale(m_oMoveToRegionDelegate, TinkApp.Uris.ActiveUri, ActiveFilterMap, currentLocation); + + } + /// Moves map and scales visible region depending on active filter. public static void MoveAndScale( Action moveToRegionDelegate,