Phaser AE

Abilities

Free packv3.0.0-3Arcade

Castable abilities as plain data: costs, targeting, windups, charges, cooldowns and interruption, with effects delivered on time as events. It is the logic behind a spell bar, kept apart from sprites, input and storage.

This is a Free pack. Every phaser.io account can use it in their games.

Released October 14, 2026 · updated October 19, 2026

Abilities: a screenshot of its demo
A note about these graphics

Expansion packs don't come with graphics. This screenshot is one way of drawing what the pack does, made for its demo: none of the sprites, tiles or backgrounds in it are in the pack.

That's by design. A pack is a game's logic, mechanics and effects, and it works with whatever art you give it. Some packs draw effects, backdrops or 3D scenes of their own, but none carries a game's sprites.

So the look is yours. Make the art on phaser.io, bring your own, or let your agent draw it in code: the same pack can look like anything.

The pack

abilities

function abilities():Pack<{abilities:typeof rules}>

Install renderer-independent abilities policies.

Helpers

checkAbilityState

function checkAbilityState(state: unknown, definitions: readonly AbilityDefinition[]): string | null

Why a saved state cannot be restored into abilities of these definitions, or null when it can: the time and every resource finite and 0 or more; the actor with an id, a team and its two flags; a slot for each ability and none other, its charges a whole number up to the ability's and its recharge within the cooldown; and the cast null or one of the abilities, with its targets, elapsed time and a cursor within its effects. restore throws with this.

createAbilities

function createAbilities(definitions: readonly AbilityDefinition[], actor: AbilityActor)

Create abilities for actor from definitions. Throws on duplicate or empty ids, a cooldown of 0, charges or maxTargets outside 1 to 1000, a refund outside 0 to 1, or a negative or non-finite cost, delay, windup, range or resource.

Classes

Abilities

class Abilities

Costs reserve on start; interruption refunds an explicit fraction. Effect delivery is an adapter boundary.

  • readonly definitions: AbilityDefinition[] — Validated copies of the ability definitions, with each ability's effects sorted by delay.
  • state: AbilityState — The live state. Read it freely; change it only through start, tick, interrupt and restore (or the game-owned actor fields). Use snapshot for a copy.
  • readonly events: AbilityEvent[] — Events queued since the last drain, oldest first.
  • constructor(definitions: readonly AbilityDefinition[], actor: AbilityActor)
  • preview(id: string, targets: readonly AbilityTarget[]): { /** True when no rule rejects the cast. */ ok: boolean; /** One message for each rule that rejects the cast; empty when \ok` is true. */ reasons: string[]; }— Whether abilityidcould start now againsttargets, without changing anything. Returns okand areasons` list naming every rejection, such as 'recharging' or 'insufficient mana'. Throws 'Unknown ability' for an unknown id.
  • start(id: string, targets: readonly AbilityTarget[]) — Start a cast if preview allows it: spends the costs and one charge, starts the recharge timer if every charge was ready, and queues 'started'. Effects already due (zero windup and delay) are delivered at once. Returns the preview result; when ok is false nothing changed. Throws for an unknown id.
  • tick(dt: number) — Advance time by dt seconds: recharge charges and deliver each effect as it falls due, completing the cast, and queue the events. Long steps are split at every due moment so none is skipped. Throws unless dt is finite and 0 or more.
  • interrupt(): boolean — Cancel the cast in progress: undelivered effects are dropped and the interruptRefund fraction of each cost is returned, but the spent charge is not. Queues 'interrupted'. Returns false when no cast was running.
  • drain() — Remove and return every queued event, oldest first.
  • snapshot() — An owned deep copy of the state, for saving and a later restore.
  • restore(state: AbilityState) — Replace the state with a copy of state. Throws abilities.restore: …, changing nothing, on a state checkAbilityState refuses for these definitions.

Types

AbilityActor

interface AbilityActor

The caster: its identity, team, whether it can act, and the resources it can spend.

  • id: string — Actor id; the only valid target of a 'self' ability.
  • team: string — Team name, compared with each target's team.
  • alive: boolean — Whether the caster is alive; a dead caster cannot start a cast.
  • disabled: boolean — Whether the caster is currently unable to act, for example stunned; a disabled caster cannot start a cast. The composing game sets it through state.actor.
  • resources: Record<string, number> — Spendable amounts by resource name, in the game's own units (mana, energy); each finite and 0 or more. Costs are deducted here and refunds added back.

AbilityDefinition

interface AbilityDefinition

A castable ability: its costs, timing, charges, targeting and the effects it delivers.

  • id: string — Unique non-empty ability id; names the ability in preview, start, events and AbilityState.slots.
  • cost: Record<string, number> — Resources spent when a cast starts, by resource name; each amount is a finite number of 0 or more, in the actor's own resource units.
  • cooldown: number — Seconds a spent charge takes to recharge; greater than 0 (at least 0.000001).
  • charges: number — Most charges the ability holds, a whole number from 1 to 1000; it starts with all of them. Each cast uses one.
  • windup: number — Seconds from the start of a cast until its effects begin; 0 or more. Each effect's after delay counts from the end of the windup.
  • range: number — Furthest a target may be from the caster, in the same units as AbilityTarget.distance; 0 or more.
  • target: 'self' | 'ally' | 'enemy' | 'any' — Who may be targeted: 'self' only the caster, 'ally' anyone on the caster's team (the caster included), 'enemy' anyone on another team, 'any' anyone.
  • maxTargets: number — Most targets one cast may name, a whole number from 1 to 1000; a cast needs at least one.
  • effects: { /** Seconds after the windup ends at which the effect is delivered; 0 or more. */ after: number; /** The combat-rules effect to apply to each target; each 'effect' event carries a copy. */ effect: Effect; }[] — Effects a cast delivers to every target, each after seconds after the windup ends. Sorted by after when the abilities are created and delivered in that order.
  • interruptRefund?: number — Fraction of each cost returned if the cast is interrupted, from 0 to 1; default 0.

AbilityEvent

interface AbilityEvent

Something the abilities did: a cast started, an effect was delivered, a cast completed or was interrupted, or a charge recharged. Queued until drain.

  • kind: 'started' | 'effect' | 'complete' | 'interrupted' | 'recharged' — What happened: 'started' a cast began, 'effect' an effect reached a target, 'complete' the cast finished, 'interrupted' it was cancelled, 'recharged' a charge came back.
  • ability: string — Id of the ability concerned.
  • target: string — Id of the target an 'effect' event reached; the empty string for every other kind.
  • effect?: Effect — Copy of the delivered effect; set only on 'effect' events.
  • time: number — Value of AbilityState.time when this happened: seconds since the abilities were created.

AbilityState

interface AbilityState

Everything that changes: the clock, the actor, each ability's charges and the cast in progress. snapshot and restore carry it.

  • time: number — Seconds simulated so far; advances only in tick.
  • actor: AbilityActor — The caster, including its current resources.
  • slots: Record<string, { /** Charges ready to use now, from 0 up to the definition's \charges`. / charges: number; /* Seconds until the next charge returns; 0 when every charge is ready. */ recharge: number; }>` — Charge state for each ability, by ability id.
  • cast: null | { /** Id of the ability being cast. */ id: string; /** Ids of the targets chosen when the cast started. */ targets: string[]; /** Seconds since the cast started. */ elapsed: number; /** * Index into the ability's sorted \effects` of the next effect to deliver; equals the number of effects once * all have been delivered. */ cursor: number; }` — The cast in progress, or null when idle. Only one cast runs at a time.

AbilityTarget

interface AbilityTarget

A candidate target as the caller observes it; the rules take its team, life and distance from here and never look it up.

  • id: string — Target id, unique within one target list. For a 'self' ability it must equal the actor's id.
  • team: string — Team name, compared with the actor's team for 'ally' and 'enemy' abilities.
  • alive: boolean — Whether the target is alive; a dead target is rejected.
  • distance: number — Distance from the caster in game units, compared with the ability's range; finite, 0 or more.