@implements IDisposable
@if (_isCooldown)
{
@_remainingSeconds
}
@code {
[Parameter] public RenderFragment? ChildContent { get; set; }
[Parameter] public EventCallback OnClick { get; set; }
[Parameter] public int CooldownSeconds { get; set; } = 12;
[Parameter] public int Size { get; set; } = 120;
private bool _isCooldown;
private int _elapsedAngle;
private int _remainingSeconds;
private DateTime _startTime;
private System.Timers.Timer? _timer;
private async Task HandleClick()
{
if (_isCooldown) return;
await OnClick.InvokeAsync(null);
StartCooldown();
}
private void StartCooldown()
{
_isCooldown = true;
_startTime = DateTime.UtcNow;
_elapsedAngle = 0;
_remainingSeconds = CooldownSeconds;
_timer = new System.Timers.Timer(33);
_timer.Elapsed += OnTick;
_timer.AutoReset = true;
_timer.Enabled = true;
}
private void OnTick(object? sender, System.Timers.ElapsedEventArgs e)
{
var elapsed = (DateTime.UtcNow - _startTime).TotalSeconds;
if (elapsed >= CooldownSeconds)
{
_isCooldown = false;
_timer?.Stop();
_timer?.Dispose();
_timer = null;
InvokeAsync(StateHasChanged);
return;
}
_elapsedAngle = (int)(elapsed / CooldownSeconds * 360);
_remainingSeconds = CooldownSeconds - (int)elapsed;
InvokeAsync(StateHasChanged);
}
public void Dispose()
{
if (_timer != null)
{
_timer.Stop();
_timer.Dispose();
_timer = null;
}
}
}