132 lines
3.4 KiB
Lua
Raw Normal View History

2025-01-04 23:00:19 +08:00
-- Tick工具可用于简化一些需要临时tick的逻辑
GlobalTickTool = GlobalTickTool or {};
---@class GlobalTickItem
---@generic T
---@field o T 代表函数拥有者
---@field f fun(o:T, dt: float, st: float) 代表函数拥有者
---@field e fun(o:T): bool 支持执行的函数
---@field s float 表示开始的时间
--- 要执行的函数
GlobalTickTool.Functions = {};
GlobalTickTool.InternalTicks = {};
function GlobalTickTool:MakeHandle(o, f, ...)
return tostring(o) .. '#' .. tostring(f);
end
--- 找到有哪些 Handle
function GlobalTickTool:FindHandles(o)
local Ret = {};
local o_Name = tostring(o);
for i, v in pairs(self.Functions) do
local SplitNum = string.find(i, '#')
if SplitNum ~= nil then
local Name = string.sub(i, SplitNum);
if Name == o_Name then table.insert(Ret, i); end
end
end
return Ret;
end
--- 是否可以添加 Tick
function GlobalTickTool:CanAddTick(o, f, t)
if type(f) ~= 'function' then return false; end
return t[self:MakeHandle(o, f)] == nil;
end
--- 注册tick回调函数
---@generic T
---@param o T
---@param f fun(o:T, dt: float, st: float) tick 函数
---@param f1 fun(o:T): bool 是否要执行 tick
---@param c float 间隔时间
function GlobalTickTool:AddTick(o, f, c, f1)
-- 说明当前存在了
if not self:CanAddTick(o, f, GlobalTickTool.Functions) then return; end
if c == nil then c = 0; end
GlobalTickTool.Functions[self:MakeHandle(o, f)] = {
o = o, -- 执行的是谁的
f = f, -- 执行函数
s = 0, -- 开始时间
c = 0, -- 表示间隔时间
e = f1, -- 验证是否可以执行的函数
};
end
function GlobalTickTool:RemoveTick(o, f)
GlobalTickTool.Functions[self:MakeHandle(o, f)] = nil;
end
--- 添加间隔执行,执行多少次的逻辑
---@generic T
---@param o T
---@param f fun(o:T, dt: float, st: float, t:int32) tick 函数 t:倒计时
---@param i float 每次间隔时间
---@param c int32 执行次数
---@param lf fun(o: T) 结束的时候执行的函数
---@param inf fun(o:T):bool 打断函数
function GlobalTickTool:AddInternalCount(o, f, i, c, lf, inf)
if not self:CanAddTick(o, f, self.InternalTicks) then return; end
if i <= 0 then i = 0 end
if c == 0 then
lf(o);
else
self.InternalTicks[self:MakeHandle(o, f)] = {
o = o,
f = f,
s = 0,
i = i,
c = math.abs(c),
inf = inf,
l = lf,
}
end
end
function GlobalTickTool:UpdateInternalCount(o, f, c)
GlobalTickTool.InternalTicks[self:MakeHandle(o, f)].c = c;
end
function GlobalTickTool:GetInternalCount(o, f)
return GlobalTickTool.InternalTicks[self:MakeHandle(o, f)].c;
end
function GlobalTickTool:RemoveAll(o)
local Ret = self:FindHandles(o)
for i, v in pairs(Ret) do
GlobalTickTool.Functions[v] = nil;
end
end
--- 调用所有注册的回调函数此函数需要在gamestate的tick里调用一下
---@param dt float
---@param ServerTime float
function GlobalTickTool:ReceiveTick(dt, ServerTime)
for o, t in pairs(self.Functions) do
if t.e == nil or t.e(t.o) then
t.s = t.s + dt;
if t.s >= t.c then
t.s = t.s - t.c;
t.f(t.o, dt, ServerTime);
end
end
end
for o, t in pairs(self.InternalTicks) do
t.s = t.s + dt;
if t.s >= t.i and t.c > 0 then
t.s = t.s - t.i;
t.c = t.c - 1; -- 次数 - 1
t.f(t.o, dt, ServerTime, t.c);
if (t.c == 0) or (t.inf ~= nil and t.inf(t.o)) then
-- 移除
if t.l ~= nil then t.l(t.o); end
self.InternalTicks[o] = nil;
end
end
end
end
return GlobalTickTool