51 lines
1.6 KiB
Lua
51 lines
1.6 KiB
Lua
---@alias ActionResult {}
|
|
|
|
---@type table<string, ActionResult>
|
|
-- selene: allow(unscoped_variables)
|
|
ActionResult = {
|
|
Succeeded = {},
|
|
Failed = {},
|
|
NeedsMoreTime = {},
|
|
}
|
|
|
|
-- selene: allow(unscoped_variables)
|
|
actionQueue = {
|
|
---@type ({ action: Action, expireTimeMs: number })[]
|
|
queue = {},
|
|
}
|
|
|
|
---@alias Action fun(deltaSeconds: number): ActionResult
|
|
|
|
--- Added actions will be called on every runWaiting() update.
|
|
--- They will continue to be executed until they return Succeeded or Failed instead of NeedsMoreTime.
|
|
---
|
|
--- Replaces any existing action with the given name.
|
|
--- If the initial call of action() doesn't return NeedsMoreTime, this function will not bother adding it to the queue.
|
|
---@param name string
|
|
---@param maxTimeMs number
|
|
---@param action Action
|
|
function actionQueue:upsert(name, maxTimeMs, action)
|
|
if action(0) ~= ActionResult.NeedsMoreTime then
|
|
return
|
|
end
|
|
|
|
self.queue[name] = {
|
|
action = action,
|
|
expireTimeMs = maxTimeMs + playdate.getCurrentTimeMilliseconds(),
|
|
}
|
|
end
|
|
|
|
--- Must be called on every playdate.update() to check for (and run) any waiting tasks.
|
|
--- Actions that return NeedsMoreTime will not be removed from the queue unless they have expired.
|
|
function actionQueue:runWaiting(deltaSeconds)
|
|
local currentTimeMs = playdate.getCurrentTimeMilliseconds()
|
|
for name, actionObject in pairs(self.queue) do
|
|
local result = actionObject.action(deltaSeconds)
|
|
if
|
|
result ~= ActionResult.NeedsMoreTime
|
|
or currentTimeMs > actionObject.expireTimeMs
|
|
then
|
|
self.queue[name] = nil
|
|
end
|
|
end
|
|
end |