mirror of
https://github.com/space-wizards/RobustToolbox.git
synced 2026-09-01 17:47:24 +02:00
Co-authored-by: metalgearsloth <31366439+metalgearsloth@users.noreply.github.com> Co-authored-by: metalgearsloth <comedian_vs_clown@hotmail.com>
126 lines
5.2 KiB
C#
126 lines
5.2 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
using Robust.Shared.Exceptions;
|
|
using Robust.Shared.IoC;
|
|
using Robust.Shared.ViewVariables;
|
|
using Timer = Robust.Shared.Timing.Timer;
|
|
|
|
namespace Robust.Shared.GameObjects
|
|
{
|
|
public sealed class TimerComponent : Component
|
|
{
|
|
[Dependency] private readonly IRuntimeLog _runtimeLog = default!;
|
|
|
|
private readonly List<(Timer timer, CancellationToken source)>
|
|
_timers = new();
|
|
|
|
public int TimerCount => _timers.Count;
|
|
|
|
/// <summary>
|
|
/// Should this component be removed when no more timers are running?
|
|
/// </summary>
|
|
[ViewVariables(VVAccess.ReadWrite)]
|
|
public bool RemoveOnEmpty { get; set; } = true;
|
|
|
|
public void Update(float frameTime)
|
|
{
|
|
// Manual for loop so we can modify the list while enumerating.
|
|
// ReSharper disable once ForCanBeConvertedToForeach
|
|
for (var i = 0; i < _timers.Count; i++)
|
|
{
|
|
var (timer, cancellationToken) = _timers[i];
|
|
|
|
if (cancellationToken.IsCancellationRequested)
|
|
{
|
|
continue;
|
|
}
|
|
|
|
timer.Update(frameTime, _runtimeLog);
|
|
}
|
|
|
|
_timers.RemoveAll(timer => !timer.Item1.IsActive || timer.source.IsCancellationRequested);
|
|
}
|
|
|
|
public void AddTimer(Timer timer, CancellationToken cancellationToken = default)
|
|
{
|
|
_timers.Add((timer, cancellationToken));
|
|
}
|
|
|
|
/// <summary>
|
|
/// Creates a task that will complete after a given delay.
|
|
/// The task is resumed on the main game logic thread.
|
|
/// </summary>
|
|
/// <param name="milliseconds">The length of time, in milliseconds, to delay for.</param>
|
|
/// <param name="cancellationToken"></param>
|
|
/// <returns>The task that can be awaited.</returns>
|
|
public Task Delay(int milliseconds, CancellationToken cancellationToken = default)
|
|
{
|
|
var tcs = new TaskCompletionSource<object?>();
|
|
Spawn(milliseconds, () => tcs.SetResult(null), cancellationToken);
|
|
return tcs.Task;
|
|
}
|
|
|
|
/// <summary>
|
|
/// Creates a task that will complete after a given delay.
|
|
/// The task is resumed on the main game logic thread.
|
|
/// </summary>
|
|
/// <param name="duration">The length of time to delay for.</param>
|
|
/// <param name="cancellationToken"></param>
|
|
/// <returns>The task that can be awaited.</returns>
|
|
public Task Delay(TimeSpan duration, CancellationToken cancellationToken = default)
|
|
{
|
|
return Delay((int) duration.TotalMilliseconds, cancellationToken);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Schedule an action to be fired after a certain delay.
|
|
/// The action will be resumed on the main game logic thread.
|
|
/// </summary>
|
|
/// <param name="milliseconds">The length of time, in milliseconds, to wait before firing the action.</param>
|
|
/// <param name="onFired">The action to fire.</param>
|
|
/// <param name="cancellationToken"></param>
|
|
public void Spawn(int milliseconds, Action onFired, CancellationToken cancellationToken = default)
|
|
{
|
|
var timer = new Timer(milliseconds, false, onFired);
|
|
AddTimer(timer, cancellationToken);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Schedule an action to be fired after a certain delay.
|
|
/// The action will be resumed on the main game logic thread.
|
|
/// </summary>
|
|
/// <param name="duration">The length of time, to wait before firing the action.</param>
|
|
/// <param name="onFired">The action to fire.</param>
|
|
/// <param name="cancellationToken"></param>
|
|
public void Spawn(TimeSpan duration, Action onFired, CancellationToken cancellationToken = default)
|
|
{
|
|
Spawn((int) duration.TotalMilliseconds, onFired, cancellationToken);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Schedule an action that repeatedly fires after a delay specified in milliseconds.
|
|
/// </summary>
|
|
/// <param name="milliseconds">The length of time, in milliseconds, to delay before firing the repeated action.</param>
|
|
/// <param name="onFired">The action to fire.</param>
|
|
/// <param name="cancellationToken">The CancellationToken for stopping the Timer.</param>
|
|
public void SpawnRepeating(int milliseconds, Action onFired, CancellationToken cancellationToken)
|
|
{
|
|
var timer = new Timer(milliseconds, true, onFired);
|
|
AddTimer(timer, cancellationToken);
|
|
}
|
|
|
|
/// <summary>
|
|
/// Schedule an action that repeatedly fires after a delay.
|
|
/// </summary>
|
|
/// <param name="duration">The length of time to delay before firing the repeated action.</param>
|
|
/// <param name="onFired">The action to fire.</param>
|
|
/// <param name="cancellationToken">The CancellationToken for stopping the Timer.</param>
|
|
public void SpawnRepeating(TimeSpan duration, Action onFired, CancellationToken cancellationToken)
|
|
{
|
|
SpawnRepeating((int) duration.TotalMilliseconds, onFired, cancellationToken);
|
|
}
|
|
}
|
|
}
|