Timer
Timer schedules work that should happen over game time: repeating effects, one-off delays, and tweens that smoothly change numeric values. Game advances its shared Timer once per frame, so durations use seconds, not milliseconds.
Quick Start
Section titled “Quick Start”Create a timer once and advance it from your game’s update loop. Game already does this for its services.timer instance; states can use that same timer through this.game.timer.
const timer = new Timer();
function update(dt) { timer.update(dt);}
// Schedule work anywhere that can access the timer.timer.after(0.5, () => { console.log('Half a second has passed.');});flowchart TD
A[Game loop receives dt in seconds] --> B["Timer.update(dt)"]
B --> C[Remove tasks marked done\nfrom a previous frame]
C --> D[Advance every active Task]
D --> E{Interval reached?}
E -- yes --> F[Run task action]
E -- no --> G{Duration reached?}
F --> G
G -- yes --> H[Run completion callback\nand mark task done]
G -- no --> I[Keep task scheduled]
H --> J[Next update removes it]
Public API
Section titled “Public API”new Timer()
Section titled “new Timer()”Creates an empty scheduler.
update(dt)
Section titled “update(dt)”timer.update(dt);Advances every scheduled task by dt seconds. Call it once per frame when using a standalone timer. Game.update(dt) already does this for services.timer; see delta time for the meaning of dt.
every(interval, action)
Section titled “every(interval, action)”const handle = timer.every(interval, action);Runs action repeatedly. interval is measured in seconds. An interval of 0 runs the action once on every timer update. Returns a timer handle that can stop the task.
// Increment a counter once per second.const counterHandle = timer.every(1, () => { counter++;});
// Stop the clock later.counterHandle.cancel();after(duration, action)
Section titled “after(duration, action)”const handle = timer.after(duration, action);Runs action once after duration seconds and returns a timer handle.
// Hide a notification after a short delay.timer.after(2, () => { notification.visible = false;});Use a positive duration. A task whose duration has elapsed is marked done after its callback runs and is removed at the beginning of the next update().
cancelAll()
Section titled “cancelAll()”timer.cancelAll();Immediately clears the timer’s task list. Use it when disposing a screen, resetting a scene, or otherwise discarding work that must not continue later. A State can do this from exit() when it owns work that must not outlive that state.
function dispose() { timer.cancelAll();}tween(object, parameters, duration, options)
Section titled “tween(object, parameters, duration, options)”const handle = timer.tween(object, parameters, duration, options);Changes one or more numeric properties from their current values to the values in parameters over duration seconds. It runs in the background; code after tween() continues immediately. Returns a timer handle.
options is optional and may contain:
easing: an easing function; defaults toEasing.linear. See the Easing reference.callback: a function called after the tween reaches its destination.
import { Easing } from './lib/Easing.js';
const panel = { x: 0, opacity: 0 };
timer.tween(panel, { x: 96, opacity: 1 }, 0.25, { easing: Easing.easeOutQuad, callback: () => { console.log('Panel is visible.'); },});The timer records each starting value when the tween is scheduled. On each frame it calculates and assigns the next value; the final frame is clamped to the exact destination.
sequenceDiagram
participant Code as Application code
participant Timer
participant Panel
Code->>Timer: tween(panel, { x: 96 }, 0.25)
Note over Code: Continues immediately
loop Each Timer.update(dt)
Timer->>Panel: set x to eased value
end
Timer->>Panel: set x = 96 (final value)
Timer-->>Code: run options.callback()
tweenAsync(object, parameters, duration, easing)
Section titled “tweenAsync(object, parameters, duration, easing)”await timer.tweenAsync(object, parameters, duration, easing);Starts a tween and returns a Promise that resolves when it finishes. Await it when later code must wait for the animation.
const firstPanel = { x: 0 };const secondPanel = { x: 320 };
// Start both movements together, then continue when both finish.await Promise.all([ timer.tweenAsync(firstPanel, { x: 320 }, 0.2), timer.tweenAsync(secondPanel, { x: 0 }, 0.2),]);
console.log('Panels have swapped places.');Awaiting pauses only the surrounding async function. It does not pause rendering, input processing, or Timer.update(dt), which Game continues to call every frame.
delay(duration)
Section titled “delay(duration)”await timer.delay(duration);Returns a Promise that resolves after duration seconds without changing any properties. It is useful for readable async sequences.
async function showNotification() { notification.visible = true; await timer.delay(0.15); notification.highlighted = true;}Timer Handle
Section titled “Timer Handle”every(), after(), and tween() return a TimerHandle:
const handle = timer.every(1, action);
console.log(handle.isDone); // falsehandle.cancel(); // Prevent future scheduled updates.console.log(handle.isDone); // trueA handle has these members:
| Member | Description |
|---|---|
cancel() |
Marks this task done without running its completion callback. |
isDone |
true after cancellation or after a duration-based task completes. |
A cancelled or completed task is removed when Timer.update() next begins. Keep the handle when you may need to stop one task; use cancelAll() when discarding every task in the timer.