Skip to main content

Spell Queue

Overview

The Spell Queue module provides a priority-based system for queuing spells and items. Instead of trying to cast spells directly (which may fail due to GCD, movement, or other conditions), you queue them with a priority and the system handles execution at the optimal time.

Key Features:

  • Priority System - Higher priority casts execute first
  • Fast Variants - Queue casts that skip GCD checks (off-GCD abilities)
  • Multiple Cast Types - Self-cast, target, and position-based casts
  • Items & Spells - Queue both spells and item uses
  • Movement Control - Allow or block movement during cast
  • Queue Management - Inspect and purge queued entries
When to Use

Use Spell Queue when you want the framework to handle cast timing intelligently. It's ideal for:

  • Rotations where abilities have different priorities
  • Off-GCD abilities that should weave between GCD spells
  • Items that need to be used at specific times

Importing The Module

---@type spell_queue
local sq = require("common/modules/spell_queue")
Method Access

Access functions with : (colon), not . (dot).


Priority System

The priority parameter determines execution order - higher numbers execute first.

PriorityUse Case
1Low priority fillers
2-3Normal rotation abilities
4-5Important procs or cooldowns
6+Critical abilities (interrupts, defensives)

Spell Functions

sq:queue_spell_target

Syntax
sq:queue_spell_target(
spell_id: number,
target: game_object,
priority: number,
message?: string,
allow_movement?: boolean
): nil

Parameters

ParameterTypeDefaultDescription
spell_idnumberRequiredThe spell ID to cast
targetgame_objectRequiredTarget for the spell
prioritynumberRequiredExecution priority (higher = first)
messagestringnilOptional debug/display message
allow_movementbooleanfalseAllow movement during cast

Example Usage

local sq = require("common/modules/spell_queue")

local FIREBALL = 133
local target = core.object_manager.get_target()

-- Queue a fireball at normal priority
sq:queue_spell_target(FIREBALL, target, 3, "Fireball")

-- Queue an interrupt at high priority
local COUNTERSPELL = 2139
sq:queue_spell_target(COUNTERSPELL, target, 6, "Interrupt!")

sq:queue_spell_target_fast

Syntax
sq:queue_spell_target_fast(
spell_id: number,
target: game_object,
priority: number,
message?: string,
allow_movement?: boolean
): nil

Same as queue_spell_target but skips GCD checks. Use for off-GCD abilities like Fire Blast, Rune of Power activations, etc.

Example Usage

-- Fire Blast is off-GCD, use fast variant
local FIRE_BLAST = 108853
sq:queue_spell_target_fast(FIRE_BLAST, target, 5, "Fire Blast (off-GCD)")

sq:queue_spell_position

Syntax
sq:queue_spell_position(
spell_id: number,
position: vec3,
priority: number,
message?: string,
allow_movement?: boolean
): nil

Queue a ground-targeted spell at a world position.

Example Usage

local BLIZZARD = 190356
local target_pos = target:get_position()

sq:queue_spell_position(BLIZZARD, target_pos, 3, "Blizzard")

sq:queue_spell_position_fast

sq:queue_spell_position_fast(
spell_id: number,
position: vec3,
priority: number,
message?: string,
allow_movement?: boolean
): nil

Position-targeted spell that skips GCD checks.


Item Functions

sq:queue_item_self

Syntax
sq:queue_item_self(item_id: number, priority: number, message?: string): nil

Queue an item for self-use (potions, food, etc.).

Example Usage

local HEALTH_POTION = 191380

-- Use health potion at high priority
sq:queue_item_self(HEALTH_POTION, 5, "Health Potion")

sq:queue_item_self_fast

sq:queue_item_self_fast(item_id: number, priority: number, message?: string): nil

Self-use item that skips GCD checks.


sq:queue_item_target

Syntax
sq:queue_item_target(
item_id: number,
target: game_object,
priority: number,
message?: string
): nil

Queue an item to use on a target.


sq:queue_item_target_fast

sq:queue_item_target_fast(
item_id: number,
target: game_object,
priority: number,
message?: string
): nil

Target item that skips GCD checks.


sq:queue_item_position

Syntax
sq:queue_item_position(
item_id: number,
position: vec3,
priority: number,
message?: string
): nil

Queue an item to use at a position (engineering items, etc.).


sq:queue_item_position_fast

sq:queue_item_position_fast(
item_id: number,
position: vec3,
priority: number,
message?: string
): nil

Position item that skips GCD checks.


Queue Management

sq:get_queue_snapshot

Syntax
sq:get_queue_snapshot(): table
Returns

Returns a shallow snapshot of the normal queue for debugging/telemetry:

{
[1] = {
spell_id = number,
spell_type = integer,
target = game_object | nil,
position = vec3 | nil,
priority = number,
timestamp = number,
skips_global = boolean,
is_item_exception = boolean,
allow_movement = boolean
},
-- ...
}

Example Usage

local snapshot = sq:get_queue_snapshot()
core.log(string.format("Queued entries: %d", #snapshot))

for i, entry in ipairs(snapshot) do
core.log(string.format(" %d: spell=%d priority=%d",
i, entry.spell_id, entry.priority))
end

sq:purge_by_spell

Syntax
sq:purge_by_spell(spell_id: number, target?: game_object): integer

Parameters

ParameterTypeDescription
spell_idnumberSpell ID to remove
targetgame_objectOptional: only remove entries for this target
Returns
  • integer - Number of entries removed

Example Usage

-- Remove all queued Immolates
local removed = sq:purge_by_spell(348)
core.log(string.format("Purged %d Immolate entries", removed))

-- Remove Immolates only for a specific target
local removed = sq:purge_by_spell(348, some_target)
core.log(string.format("Purged %d Immolate entries for target", removed))

Complete Examples

Basic Rotation with Priorities

local sq = require("common/modules/spell_queue")

local SPELLS = {
FIREBALL = 133,
FIRE_BLAST = 108853,
PYROBLAST = 11366,
COMBUSTION = 190319,
}

local function rotation(target, player)
-- Cooldowns at high priority
if should_use_combustion() then
sq:queue_spell_target(SPELLS.COMBUSTION, player, 5, "Combustion")
end

-- Off-GCD abilities with fast variant
if has_heating_up() then
sq:queue_spell_target_fast(SPELLS.FIRE_BLAST, target, 4, "Fire Blast")
end

-- Procs at medium-high priority
if has_hot_streak() then
sq:queue_spell_target(SPELLS.PYROBLAST, target, 4, "Hot Streak Pyro")
end

-- Filler at normal priority
sq:queue_spell_target(SPELLS.FIREBALL, target, 2, "Fireball")
end

Interrupt Priority

local sq = require("common/modules/spell_queue")

local COUNTERSPELL = 2139

local function check_interrupt(enemies)
for _, enemy in ipairs(enemies) do
if enemy:is_casting() and should_interrupt(enemy) then
-- Interrupts get highest priority
sq:queue_spell_target(COUNTERSPELL, enemy, 10, "INTERRUPT!")
return
end
end
end

Defensive Rotation

local sq = require("common/modules/spell_queue")

local ITEMS = {
HEALTH_POTION = 191380,
HEALTHSTONE = 5512,
}

local SPELLS = {
ICE_BLOCK = 45438,
BARRIER = 235313,
}

local function defensives(player)
local hp = player:get_health_percent()

-- Critical: Ice Block
if hp < 15 then
sq:queue_spell_target(SPELLS.ICE_BLOCK, player, 10, "ICE BLOCK!")
return
end

-- High priority: Health items
if hp < 35 then
sq:queue_item_self(ITEMS.HEALTHSTONE, 8, "Healthstone")
sq:queue_item_self(ITEMS.HEALTH_POTION, 7, "Health Pot")
end

-- Medium: Barrier
if hp < 60 then
sq:queue_spell_target(SPELLS.BARRIER, player, 5, "Barrier")
end
end

Movement-Allowed Casts

local sq = require("common/modules/spell_queue")

local SCORCH = 2948 -- Castable while moving with talent

-- Allow movement for Scorch
sq:queue_spell_target(SCORCH, target, 3, "Scorch (moving)", true)