1
0
mirror of https://github.com/bitwarden/mobile.git synced 2024-06-29 11:05:52 +02:00

PM-3349 Added Handler that enables the ExtendedDatePicker to get IsFocused events in Android. This is a workaround for fixing the current bug where it's not possible to select the "current day" in the expiration date of a Send.

Fix for TimePicker not displaying default Time Value
Updated some "Device" code to the new MAUI "DeviceInfo"
This commit is contained in:
Dinis Vieira 2023-11-02 02:32:12 +00:00
parent e90409d842
commit 946c465f0c
No known key found for this signature in database
GPG Key ID: 9389160FF6C295F3
12 changed files with 120 additions and 56 deletions

View File

@ -29,6 +29,7 @@
Bit.App.Handlers.ToolbarHandlerMappings.Setup();
handlers.AddHandler(typeof(Bit.App.Pages.TabsPage), typeof(Bit.App.Handlers.CustomTabbedPageHandler));
handlers.AddHandler(typeof(Bit.App.Controls.ExtendedDatePicker), typeof(Bit.App.Handlers.ExtendedDatePickerHandler));
#else
iOS.Core.Utilities.iOSCoreHelpers.ConfigureMAUIHandlers(handlers);
#endif

View File

@ -23,12 +23,12 @@ namespace Bit.App.Handlers
}
});
DatePickerHandler.Mapper.AppendToMapping(nameof(IDatePicker.Date), UpdateTextPlaceholderOnFormatLikePlacholder);
DatePickerHandler.Mapper.AppendToMapping(nameof(IDatePicker.Date), UpdateTextPlaceholderOnFormatLikePlaceholder);
DatePickerHandler.Mapper.AppendToMapping(nameof(IDatePicker.Format), UpdateTextPlaceholderOnFormatLikePlacholder);
DatePickerHandler.Mapper.AppendToMapping(nameof(IDatePicker.Format), UpdateTextPlaceholderOnFormatLikePlaceholder);
}
private static void UpdateTextPlaceholderOnFormatLikePlacholder(IDatePickerHandler handler, IDatePicker datePicker)
private static void UpdateTextPlaceholderOnFormatLikePlaceholder(IDatePickerHandler handler, IDatePicker datePicker)
{
if (datePicker is ExtendedDatePicker extDatePicker && extDatePicker.Format == extDatePicker.PlaceHolder)
{

View File

@ -0,0 +1,76 @@
using Android.App;
using Microsoft.Maui.Handlers;
using Microsoft.Maui.Platform;
namespace Bit.App.Handlers
{
// Note: This Handler exists only to allow the ExtendedDatePicker to receive IsFocused events on Android. iOS Already does this with this fix: https://github.com/dotnet/maui/pull/13321
// If MAUI eventually implements this behavior we can remove this handler completely. There is another Handler (DatePickerHandlerMappings) for the other DatePicker customizations.
public partial class ExtendedDatePickerHandler : DatePickerHandler
{
public static PropertyMapper<IDatePicker, ExtendedDatePickerHandler> PropertyMapper = new (DatePickerHandler.Mapper)
{
[nameof(IDatePicker.IsFocused)] = MapIsFocused
};
public ExtendedDatePickerHandler() : base(PropertyMapper)
{
}
public static void MapIsFocused(ExtendedDatePickerHandler handler, IDatePicker datePicker)
{
if (handler.PlatformView.IsFocused == datePicker.IsFocused) return;
if (datePicker.IsFocused)
{
handler.PlatformView.RequestFocus();
}
else
{
handler.PlatformView.ClearFocus();
}
}
private DatePickerDialog? _dialog;
protected override DatePickerDialog CreateDatePickerDialog(int year, int month, int day)
{
_dialog = base.CreateDatePickerDialog(year, month, day);
return _dialog;
}
protected override void ConnectHandler(MauiDatePicker platformView)
{
base.ConnectHandler(platformView);
if (_dialog != null)
{
_dialog.ShowEvent += OnDialogShown;
_dialog.DismissEvent += OnDialogDismissed;
}
}
//Currently the Disconnect Handler needs to be manually called from the App: https://github.com/dotnet/maui/issues/3604
protected override void DisconnectHandler(MauiDatePicker platformView)
{
if (_dialog != null)
{
_dialog.ShowEvent -= OnDialogShown;
_dialog.DismissEvent -= OnDialogDismissed;
}
base.DisconnectHandler(platformView);
_dialog = null;
}
private void OnDialogShown(object sender, EventArgs e)
{
this.VirtualView.IsFocused = true;
}
private void OnDialogDismissed(object sender, EventArgs e)
{
this.VirtualView.IsFocused = false;
}
}
}

View File

@ -16,19 +16,19 @@ namespace Bit.App.Handlers
handler.PlatformView.Gravity = GravityFlags.CenterHorizontal;
// use placeholder until NullableTime set
if (!extTimePicker.NullableTime.HasValue)
if (!extTimePicker.NullableTime.HasValue && !string.IsNullOrWhiteSpace(extTimePicker.PlaceHolder))
{
handler.PlatformView.Text = extTimePicker.PlaceHolder;
}
}
});
TimePickerHandler.Mapper.AppendToMapping(nameof(ITimePicker.Time), UpdateTextPlaceholderOnFormatLikePlacholder);
TimePickerHandler.Mapper.AppendToMapping(nameof(ITimePicker.Time), UpdateTextPlaceholderOnFormatLikePlaceholder);
TimePickerHandler.Mapper.AppendToMapping(nameof(ITimePicker.Format), UpdateTextPlaceholderOnFormatLikePlacholder);
TimePickerHandler.Mapper.AppendToMapping(nameof(ITimePicker.Format), UpdateTextPlaceholderOnFormatLikePlaceholder);
}
private static void UpdateTextPlaceholderOnFormatLikePlacholder(ITimePickerHandler handler, ITimePicker timePicker)
private static void UpdateTextPlaceholderOnFormatLikePlaceholder(ITimePickerHandler handler, ITimePicker timePicker)
{
if (timePicker is ExtendedTimePicker extDatePicker && extDatePicker.Format == extDatePicker.PlaceHolder)
{

View File

@ -4,6 +4,7 @@
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:controls="clr-namespace:Bit.App.Controls"
x:Class="Bit.App.Controls.DateTimePicker"
Unloaded="DateTimePicker_OnUnloaded"
ColumnDefinitions="*,*">
<controls:ExtendedDatePicker
x:Name="_datePicker"

View File

@ -1,11 +1,4 @@
using System.Runtime.CompilerServices;
using Microsoft.Maui.Controls;
using Microsoft.Maui;
using CommunityToolkit.Maui.Converters;
using CommunityToolkit.Maui.ImageSources;
using CommunityToolkit.Maui;
using CommunityToolkit.Maui.Core;
using CommunityToolkit.Maui.Layouts;
using CommunityToolkit.Maui.Views;
namespace Bit.App.Controls
@ -32,6 +25,11 @@ namespace Bit.App.Controls
_timePicker.PlaceHolder = dateTimeViewModel.TimePlaceholder;
}
}
private void DateTimePicker_OnUnloaded(object sender, EventArgs e)
{
_datePicker?.DisconnectHandler();
}
}
public class LazyDateTimePicker : LazyView<DateTimePicker>

View File

@ -1,5 +1,4 @@
using System;
using Bit.Core.Utilities;
using Bit.Core.Utilities;
namespace Bit.App.Controls
{

View File

@ -1,8 +1,4 @@
using System;
using Microsoft.Maui.Controls;
using Microsoft.Maui;
namespace Bit.App.Controls
namespace Bit.App.Controls
{
public class ExtendedDatePicker : DatePicker
{
@ -83,5 +79,11 @@ namespace Bit.App.Controls
}
}
}
//Currently the Disconnect Handler needs to be manually called from the App: https://github.com/dotnet/maui/issues/3604
public void DisconnectHandler()
{
Handler?.DisconnectHandler();
}
}
}

View File

@ -1,8 +1,4 @@
using System;
using Microsoft.Maui.Controls;
using Microsoft.Maui;
namespace Bit.App.Controls
namespace Bit.App.Controls
{
public class ExtendedTimePicker : TimePicker
{

View File

@ -12,6 +12,7 @@
xmlns:core="clr-namespace:Bit.Core"
x:DataType="pages:SendAddEditPageViewModel"
HideSoftInputOnTapped="True"
Unloaded="OnUnloaded"
x:Name="_page"
Title="{Binding PageTitle}">
<ContentPage.BindingContext>
@ -310,6 +311,7 @@
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<controls:ExtendedDatePicker
x:Name="_deletionExtendedDatePicker"
NullableDate="{Binding DeletionDateTimeViewModel.Date, Mode=TwoWay}"
Format="d"
IsEnabled="{Binding SendEnabled}"
@ -353,6 +355,7 @@
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<controls:ExtendedDatePicker
x:Name="_expirationExtendedDatePicker"
NullableDate="{Binding ExpirationDateTimeViewModel.Date, Mode=TwoWay}"
PlaceHolder="mm/dd/yyyy"
Format="d"

View File

@ -1,7 +1,4 @@
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Bit.App.Models;
using Bit.App.Models;
using Bit.Core.Resources.Localization;
using Bit.App.Utilities;
using Bit.Core.Abstractions;
@ -9,8 +6,6 @@ using Bit.Core.Enums;
using Bit.Core.Utilities;
using Microsoft.Maui.Controls.PlatformConfiguration;
using Microsoft.Maui.Controls.PlatformConfiguration.iOSSpecific;
using Microsoft.Maui.Controls;
using Microsoft.Maui;
namespace Bit.App.Pages
{
@ -39,8 +34,7 @@ namespace Bit.App.Pages
_vm.SendId = sendId;
_vm.Type = appOptions?.CreateSend?.Item1 ?? type;
SetActivityIndicator();
// TODO Xamarin.Forms.Device.RuntimePlatform is no longer supported. Use Microsoft.Maui.Devices.DeviceInfo.Platform instead. For more details see https://learn.microsoft.com/en-us/dotnet/maui/migration/forms-projects#device-changes
if (Device.RuntimePlatform == Device.Android)
if (DeviceInfo.Platform == DevicePlatform.Android)
{
if (_vm.EditMode)
{
@ -57,7 +51,7 @@ namespace Bit.App.Pages
_btnOptionsDown.WidthRequest = 30;
_btnOptionsUp.WidthRequest = 30;
}
else if (Device.RuntimePlatform == Device.iOS)
else if (DeviceInfo.Platform == DevicePlatform.iOS)
{
ToolbarItems.Add(_closeItem);
if (_vm.EditMode)
@ -102,7 +96,7 @@ namespace Bit.App.Pages
{
if (message.Command == "selectFileResult")
{
Device.BeginInvokeOnMainThread(() =>
MainThread.BeginInvokeOnMainThread(() =>
{
var data = message.Data as Tuple<byte[], string>;
_vm.FileData = data.Item1;
@ -141,8 +135,7 @@ namespace Bit.App.Pages
protected override bool OnBackButtonPressed()
{
// TODO Xamarin.Forms.Device.RuntimePlatform is no longer supported. Use Microsoft.Maui.Devices.DeviceInfo.Platform instead. For more details see https://learn.microsoft.com/en-us/dotnet/maui/migration/forms-projects#device-changes
if (_vm.IsAddFromShare && Device.RuntimePlatform == Device.Android)
if (_vm.IsAddFromShare && DeviceInfo.Platform == DevicePlatform.Android)
{
_appOptions.CreateSend = null;
}
@ -152,13 +145,18 @@ namespace Bit.App.Pages
protected override void OnDisappearing()
{
base.OnDisappearing();
// TODO Xamarin.Forms.Device.RuntimePlatform is no longer supported. Use Microsoft.Maui.Devices.DeviceInfo.Platform instead. For more details see https://learn.microsoft.com/en-us/dotnet/maui/migration/forms-projects#device-changes
if (Device.RuntimePlatform != Device.iOS)
if (DeviceInfo.Platform == DevicePlatform.iOS)
{
_broadcasterService.Unsubscribe(nameof(SendAddEditPage));
}
}
private void OnUnloaded(object sender, EventArgs e)
{
_deletionExtendedDatePicker?.DisconnectHandler();
_expirationExtendedDatePicker?.DisconnectHandler();
}
private async void TextType_Clicked(object sender, EventArgs eventArgs)
{
await _vm.TypeChangedAsync(SendType.Text);
@ -310,8 +308,7 @@ namespace Bit.App.Pages
private void AdjustToolbar()
{
_saveItem.IsEnabled = _vm.SendEnabled;
// TODO Xamarin.Forms.Device.RuntimePlatform is no longer supported. Use Microsoft.Maui.Devices.DeviceInfo.Platform instead. For more details see https://learn.microsoft.com/en-us/dotnet/maui/migration/forms-projects#device-changes
if (!_vm.SendEnabled && _vm.EditMode && Device.RuntimePlatform == Device.Android)
if (!_vm.SendEnabled && _vm.EditMode && DeviceInfo.Platform == DevicePlatform.Android)
{
ToolbarItems.Remove(_removePassword);
ToolbarItems.Remove(_copyLink);

View File

@ -1,7 +1,4 @@
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using Bit.App.Abstractions;
using Bit.App.Abstractions;
using Bit.App.Controls;
using Bit.Core.Resources.Localization;
using Bit.App.Utilities;
@ -11,9 +8,6 @@ using Bit.Core.Enums;
using Bit.Core.Exceptions;
using Bit.Core.Models.View;
using Bit.Core.Utilities;
using Microsoft.Maui.Networking;
using Microsoft.Maui.Controls;
using Microsoft.Maui;
namespace Bit.App.Pages
{
@ -395,8 +389,7 @@ namespace Bit.App.Pages
var sendId = await _sendService.SaveWithServerAsync(send, encryptedFileData);
await _deviceActionService.HideLoadingAsync();
// TODO Xamarin.Forms.Device.RuntimePlatform is no longer supported. Use Microsoft.Maui.Devices.DeviceInfo.Platform instead. For more details see https://learn.microsoft.com/en-us/dotnet/maui/migration/forms-projects#device-changes
if (Device.RuntimePlatform == Device.Android && IsFile)
if (DeviceInfo.Platform == DevicePlatform.Android && IsFile)
{
// Workaround for https://github.com/xamarin/Xamarin.Forms/issues/5418
// Exiting and returning (file picker) calls OnAppearing on list page instead of this modal, and
@ -455,8 +448,7 @@ namespace Bit.App.Pages
{
if (IsAddFromShare)
{
// TODO Xamarin.Forms.Device.RuntimePlatform is no longer supported. Use Microsoft.Maui.Devices.DeviceInfo.Platform instead. For more details see https://learn.microsoft.com/en-us/dotnet/maui/migration/forms-projects#device-changes
if (Device.RuntimePlatform == Device.Android)
if (DeviceInfo.Platform == DevicePlatform.Android)
{
_deviceActionService.CloseMainApp();
return;
@ -513,8 +505,7 @@ namespace Bit.App.Pages
await _platformUtilsService.ShowDialogAsync(AppResources.SendFileEmailVerificationRequired);
}
// TODO Xamarin.Forms.Device.RuntimePlatform is no longer supported. Use Microsoft.Maui.Devices.DeviceInfo.Platform instead. For more details see https://learn.microsoft.com/en-us/dotnet/maui/migration/forms-projects#device-changes
if (IsAddFromShare && Device.RuntimePlatform == Device.Android)
if (IsAddFromShare && DeviceInfo.Platform == DevicePlatform.Android)
{
_deviceActionService.CloseMainApp();
return;
@ -630,7 +621,7 @@ namespace Bit.App.Pages
internal void TriggerSendTextPropertyChanged()
{
Device.BeginInvokeOnMainThread(() => TriggerPropertyChanged(nameof(Send)));
MainThread.BeginInvokeOnMainThread(() => TriggerPropertyChanged(nameof(Send)));
}
}
}