Skip to content

Instantly share code, notes, and snippets.

@weitzhandler
Last active July 23, 2017 19:41
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save weitzhandler/e9a31d300824a48799a446ca0ac624df to your computer and use it in GitHub Desktop.
Save weitzhandler/e9a31d300824a48799a446ca0ac624df to your computer and use it in GitHub Desktop.
Device.Timer wrapper for Xamarin with Prism DI support
using System;
using System.Linq;
using System.Collections.Generic;
using Prism.Services;
namespace Xamarin.Forms
{
public class DeviceTimer
{
readonly Action _Task;
readonly TimeSpan _Interval;
public bool IsRecurring { get; }
readonly Action<TimeSpan, Func<bool>> _DeviceTimer;
readonly List<TaskWrapper> _Tasks = new List<TaskWrapper>();
public bool IsRunning => _Tasks.Any(t => t.IsRunning);
public DeviceTimer(Action task, TimeSpan interval,
bool isRecurring = false, bool start = false) : this(task, interval, isRecurring, start, Device.StartTimer)
{
}
protected DeviceTimer(Action task, TimeSpan interval,
bool isRecurring = false, bool start = false, Action<TimeSpan, Func<bool>> deviceTimer = null)
{
_DeviceTimer = deviceTimer ?? throw new ArgumentNullException(nameof(deviceTimer));
_Task = task;
_Interval = interval;
IsRecurring = isRecurring;
if (start)
Start();
}
public void Restart()
{
Stop();
Start();
}
public void Start()
{
if (IsRunning)
// Already Running
return;
var wrapper = new TaskWrapper(_Task, IsRecurring, true);
_Tasks.Add(wrapper);
_DeviceTimer(_Interval, wrapper.RunTask);
}
public void Stop()
{
foreach (var task in _Tasks)
task.IsRunning = false;
_Tasks.Clear();
}
private class TaskWrapper
{
public bool IsRunning { get; set; }
bool _IsRecurring;
Action _Task;
public TaskWrapper(Action task, bool isRecurring, bool isRunning)
{
_Task = task;
_IsRecurring = isRecurring;
IsRunning = isRunning;
}
public bool RunTask()
{
if (IsRunning)
{
_Task();
if (_IsRecurring)
return true;
}
return IsRunning = false;
}
}
}
}
namespace Prism.Services
{
public class PrismDeviceTimer : Xamarin.Forms.DeviceTimer
{
public PrismDeviceTimer(IDeviceService deviceService, Action task, TimeSpan interval,
bool isRecurring = false, bool start = false) : base(task, interval, isRecurring, start, GetMethod(deviceService))
{
}
static Action<TimeSpan, Func<bool>> GetMethod(IDeviceService deviceService)
{
if (deviceService == null) throw new ArgumentNullException(nameof(deviceService));
return deviceService.StartTimer;
}
}
}
@weitzhandler
Copy link
Author

IDeviceService can easily be removed an replaced by the Xamarin static one for projects without Prism.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment