139 lines
4.0 KiB
Lua
139 lines
4.0 KiB
Lua
---@class SkillManager 技能管理器,区别于 BuffManager,技能管理器不会创建,都是瞬时的,但是会记录每个玩家使用技能的时间和 CD
|
||
local BaseDir = "Script.Blueprint.SceneObj.Skill."
|
||
local SkillManager = {};
|
||
|
||
--- 在最开始的时候进行全部加载
|
||
SkillManager.Config = nil;
|
||
SkillManager.Owner = nil;
|
||
SkillManager.Skills = {}; -- 所有的技能
|
||
SkillManager.OwnerSkills = {};
|
||
|
||
function SkillManager:Init(InOwner)
|
||
UGCLogSystem.Log("[SkillManager:Init] 执行")
|
||
-- 加载 Config
|
||
self.Config = require(BaseDir .. 'SkillConfig');
|
||
self.Owner = InOwner;
|
||
GlobalTickTool:AddTick(self, self.OnTick)
|
||
for i, v in pairs(self.Config) do
|
||
self:InitSingle(i, v);
|
||
end
|
||
end
|
||
|
||
function SkillManager:InitSingle(i, v)
|
||
local Item = require(BaseDir .. 'Script.Skill_' .. v.Name);
|
||
self.Skills[i] = Item;
|
||
Item.SkillID = i;
|
||
if not table.isEmpty(v.Params) then
|
||
for Name, Value in pairs(v.Params) do
|
||
Item[Name] = Value;
|
||
end
|
||
end
|
||
local HadInit = table.func(Item, "Init");
|
||
Item.HadInit = HadInit;
|
||
end
|
||
|
||
function SkillManager:OnTick(dt, st)
|
||
if st == nil then return ; end
|
||
for PlayerKey, Skills in pairs(self.OwnerSkills) do
|
||
for SkillId, TimeInfo in pairs(Skills) do
|
||
if not TimeInfo.CanExec then
|
||
if TimeInfo.EndTime <= st then
|
||
TimeInfo.CanExec = true;
|
||
self:ResetSkill(SkillId, PlayerKey);
|
||
end
|
||
end
|
||
end
|
||
end
|
||
end
|
||
|
||
function SkillManager:GetSkillItem(InSkillId)
|
||
if self.Skills[InSkillId] == nil then
|
||
self:InitSingle(InSkillId, self.Config[InSkillId]);
|
||
end
|
||
return self.Skills[InSkillId];
|
||
end
|
||
|
||
-- 发送 RPC
|
||
function SkillManager:SendSkillRPC(InFuncName, InSkillId, InPlayerKey, ...)
|
||
if IsServer then
|
||
UnrealNetwork.CallUnrealRPC_Multicast_Unreliable(self.Owner, "SendSkillRPC", InFuncName, InSkillId, InPlayerKey, ...);
|
||
end
|
||
end
|
||
|
||
--- 添加技能
|
||
---@param InSkillId int32
|
||
function SkillManager:AddSkill(InSkillId, InPlayerKey, ...)
|
||
assert(InSkillId ~= nil);
|
||
UGCLogSystem.LogTree(string.format("[SkillManager:AddSkill] self.Config ="), self.Config)
|
||
UGCLogSystem.Log("[SkillManager:AddSkill] InSkillId = %s", tostring(InSkillId));
|
||
assert(self.Config[InSkillId] ~= nil);
|
||
local Item = self:GetSkillItem(InSkillId);
|
||
if Item == nil then
|
||
UGCLogSystem.Log("[SkillManager:AddSkill] SkillId = %d 的技能没有成功加入表中", InSkillId);
|
||
return false;
|
||
end
|
||
|
||
-- 检查能量是否够,如果不够那么就无法执行
|
||
local Cost = self.Config[InSkillId].Cost;
|
||
if IsServer then
|
||
if Cost ~= nil and Cost > 0 then
|
||
-- 获取 PS 里面的能量
|
||
local PS = UGCGameSystem.GetPlayerStateByPlayerKey(InPlayerKey);
|
||
if UE.IsValid(PS) then
|
||
if not self:AddSkillEnergy(-Cost) then
|
||
return false;
|
||
end
|
||
end
|
||
end
|
||
end
|
||
|
||
-- 验证一下是否可以执行
|
||
if self.OwnerSkills[InPlayerKey] == nil then
|
||
self.OwnerSkills[InPlayerKey] = {};
|
||
else
|
||
local SkillInfo = self.OwnerSkills[InPlayerKey][InSkillId];
|
||
if SkillInfo ~= nil then
|
||
-- 没有到执行的时间呢
|
||
if not SkillInfo.CanExec then
|
||
if IsServer then return false; end
|
||
end
|
||
end
|
||
end
|
||
|
||
-- 执行
|
||
Item.SkillId = InSkillId;
|
||
local bSuccess = table.func(Item, "Add", InPlayerKey, ...);
|
||
-- 执行成功
|
||
if not bSuccess then
|
||
UGCLogSystem.Log("[SkillManager:AddSkill] 没有执行 %s 的 AddSkill 成功,请检查", self.Config[InSkillId].Name)
|
||
return false;
|
||
end
|
||
-- 那就添加进去
|
||
local StartTime = UE.GetServerTime();
|
||
local Cooldown = self.Config[InSkillId].Cooldown;
|
||
if Cooldown == nil then Cooldown = 0; end
|
||
self.OwnerSkills[InPlayerKey][InSkillId] = {
|
||
StartTime = StartTime,
|
||
EndTime = StartTime + Cooldown;
|
||
CanExec = false; -- 在冷却
|
||
};
|
||
if IsServer then
|
||
self:SendSkillRPC("AddSkill", InSkillId, InPlayerKey, ...);
|
||
end
|
||
return true;
|
||
end
|
||
|
||
function SkillManager:RemoveSkill(InSkillId, InPlayerKey)
|
||
table.func(self:GetSkillItem(InSkillId), "Remove", InPlayerKey);
|
||
end
|
||
|
||
function SkillManager:ResetSkill(InSkillId, InPlayerKey)
|
||
table.func(self:GetSkillItem(InSkillId), "Reset", InPlayerKey);
|
||
if IsServer then
|
||
self:SendSkillRPC("ResetSkill", InSkillId, InPlayerKey);
|
||
else
|
||
|
||
end
|
||
end
|
||
|
||
return SkillManager; |