Improved Autofocus code on ScanPage for better cancellation and exception handling #1228 (#1759)

This commit is contained in:
Federico Maccaroni 2022-02-09 14:22:04 -03:00 committed by GitHub
parent 3491c1aaeb
commit 76f1057951
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23

View file

@ -1,5 +1,8 @@
using System;
using System.Collections.Generic;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.AppCenter.Crashes;
using Xamarin.Forms;
namespace Bit.App.Pages
@ -8,9 +11,6 @@ namespace Bit.App.Pages
{
private readonly Action<string> _callback;
private DateTime? _timerStarted = null;
private TimeSpan _timerMaxLength = TimeSpan.FromMinutes(3);
public ScanPage(Action<string> callback)
{
_callback = callback;
@ -27,26 +27,54 @@ namespace Bit.App.Pages
ToolbarItems.RemoveAt(0);
}
}
private CancellationTokenSource _autofocusCts;
protected override void OnAppearing()
{
base.OnAppearing();
_zxing.IsScanning = true;
_timerStarted = DateTime.Now;
Device.StartTimer(new TimeSpan(0, 0, 2), () =>
// Fix for Autofocus, now it's done every 2 seconds so that the user does't have to do it
// https://github.com/Redth/ZXing.Net.Mobile/issues/414
_autofocusCts?.Cancel();
_autofocusCts = new CancellationTokenSource();
var autofocusCts = _autofocusCts;
Task.Run(async () =>
{
if (_timerStarted == null || (DateTime.Now - _timerStarted) > _timerMaxLength)
await Task.Delay(TimeSpan.FromMinutes(3), autofocusCts.Token);
autofocusCts.Cancel();
});
Device.StartTimer(TimeSpan.FromSeconds(2), () =>
{
try
{
if (autofocusCts.IsCancellationRequested)
{
return false;
}
_zxing.AutoFocus();
return true;
}
catch (Exception ex)
{
// we don't need to display anything to the user because at the most they just lose autofocus
#if !FDROID
Crashes.TrackError(ex);
#endif
autofocusCts?.Cancel(); // we also cancel here to cancel the Task.Delay as well.
return false;
}
_zxing.AutoFocus();
return true;
});
}
protected override void OnDisappearing()
{
_timerStarted = null;
_autofocusCts?.Cancel();
_zxing.IsScanning = false;
base.OnDisappearing();
}