local leishen = {}
local function showEffect(msgID, p1, p2, p3, msgData)
local data = SL:JsonDecode(msgData, false) or {}
SL:print("特效数据", data)
local num = data.num or 0
local eff1, eff2 = data.preEff, data.startEff
-- 创建父节
🤖 回答引擎: 前端Lua |
🕒 时间: 2026-03-24 15:35:00 |
👁️ 阅读: 5
你的特效没有持续40秒是因为你在`showEffect`函数中使用了**动作序列**来执行倒计时,但动作序列的延迟时间总共只有1.5秒(0.5秒×3),而不是40秒。
在`showEffect`函数中,你创建了一个倒计时动作:
```lua
local countdownAction = GUI:ActionSequence(
GUI:CallFunc(function()
GUI:Text_setString(countdownText, "3")
end),
GUI:DelayTime(0.5),
GUI:CallFunc(function()
GUI:Text_setString(countdownText, "2")
end),
GUI:DelayTime(0.5),
GUI:CallFunc(function()
GUI:Text_setString(countdownText, "1")
end),
GUI:DelayTime(0.5),
GUI:CallFunc(function()
-- 这里创建技能特效并移除其他组件
end)
)
```
这个动作序列总共只有1.5秒,所以特效会在1.5秒后就结束并移除。
要实现40秒的持续效果,你需要:
1. **在`showEffect`函数中增加定时器**来管理40秒的倒计时
2. **使用`SL:Schedule`或`SL:ScheduleOnce`来创建定时器**
修改后的`showEffect`函数应该这样写:
```lua
local function showEffect(msgID, p1, p2, p3, msgData)
local data = SL:JsonDecode(msgData, false) or {}
SL:print("特效数据", data)
local num = data.num or 0
local eff1, eff2 = data.preEff, data.startEff
-- 创建父节点作为容器
local sceneLayer = GUI:Win_Create("EffectLayer", 0, 0, 0, 0, false, false, true, false, false, false, 1)
-- 存储所有需要管理的对象
local effectObjects = {}
local timers = {} -- 存储定时器
for i = 1, num do
-- 获取屏幕尺寸
local screenWidth = SL:GetMetaValue("SCREEN_WIDTH") or 1280
local screenHeight = SL:GetMetaValue("SCREEN_HEIGHT") or 720
-- 在屏幕范围内随机位置显示特效
local posX, posY
if data.mapdata and data.mapdata[i] then
posX = data.mapdata[i].x or math.random(100, screenWidth - 100)
posY = data.mapdata[i].y or math.random(100, screenHeight - 100)
else
posX = math.random(100, screenWidth - 100)
posY = math.random(100, screenHeight - 100)
end
-- 创建预警特效
local circleEffect = GUI:Effect_Create(sceneLayer, "circle_effect_" .. i,
posX, posY, 0, eff1, 0, 0, 0, 1)
-- 创建进度条作为倒计时显示
local loadingBar = GUI:LoadingBar_Create(circleEffect, "LoadingBar_" .. i,
0, 30, "res/er dalu/leishen/jdt/1.png", 0)
GUI:setContentSize(loadingBar, 100, 20)
GUI:LoadingBar_setPercent(loadingBar, 100)
-- 创建图片
local image6 = GUI:Image_Create(sceneLayer, "Image_6",
posX - 50, posY - 50, "res/er dalu/leishen/jdt/leishen.png")
GUI:setVisible(image6, true)
GUI:setContentSize(image6, 100, 100)
GUI:setAnchorPoint(image6, 0.5, 0.5)
-- 创建倒计时数字文本
local countdownText = GUI:Text_Create(circleEffect, "countdown_" .. i,
0, 30, 20, "#FF0000", "40")
-- 存储对象
effectObjects[i] = {
circleEffect = circleEffect,
loadingBar = loadingBar,
countdownText = countdownText,
image6 = image6,
posX = posX,
posY = posY,
eff2 = eff2
}
-- 40秒倒计时定时器
local countdown = 40
local timer = SL:Schedule(function()
if countdown > 0 then
countdown = countdown - 1
GUI:Text_setString(countdownText, tostring(countdown))
-- 更新进度条
local percent = (countdown / 40) * 100
GUI:LoadingBar_setPercent(loadingBar, percent)
-- 最后3秒显示数字倒计时
if countdown <= 3 then
-- 可以添加闪烁效果
local blinkAction = GUI:ActionSequence(
GUI:ActionFadeTo(0.2, 100),
GUI:ActionFadeTo(0.2, 255)
)
GUI:runAction(countdownText, GUI:ActionRepeat(blinkAction, 2))
end
else
-- 倒计时结束,创建技能特效
local skillEffect = GUI:Effect_Create(sceneLayer, "skill_effect_" .. i..math.random(999999),
posX, posY, 0, eff2, 0, 0, 0, 1)
local skillAction = GUI:ActionSequence(
GUI:ActionScaleTo(0.2, 2.0),
GUI:DelayTime(0.3),
GUI:ActionFadeTo(0.5, 0),
GUI:CallFunc(function()
GUI:removeFromParent(skillEffect)
end)
)
GUI:runAction(skillEffect, skillAction)
-- 移除圈、进度条、图片和倒计时文本
GUI:removeFromParent(circleEffect)
GUI:removeFromParent(loadingBar)
GUI:removeFromParent(countdownText)
GUI:removeFromParent(image6)
-- 停止定时器
SL:UnSchedule(timer)
timers[i] = nil
end
end, 1)
timers[i] = timer
end
end
```
**关键修改点:**
1. **使用`SL:Schedule`创建每秒执行的定时器**,而不是使用动作序列
2. **在定时器回调中更新倒计时数字和进度条**
3. **倒计时结束后才创建技能特效并移除组件**
4. **添加了`timers`表来管理所有定时器**,便于后续清理
**注意:** 记得在适当的时候清理定时器,比如界面关闭时,可以使用`SL:UnSchedule(timer)`来停止定时器。
这样修改后,你的特效就会持续40秒,并且每秒更新倒计时显示和进度条了。
你的特效没有持续40秒是因为你在`showEffect`函数中使用了**动作序列**来执行倒计时,但动作序列的延迟时间总共只有1.5秒(0.5秒×3),而不是40秒。
在`showEffect`函数中,你创建了一个倒计时动作:
```lua
local countdownAction = GUI:ActionSequence(
GUI:CallFunc(function()
GUI:Text_setString(countdownText, "3")
end),
GUI:DelayTime(0.5),
GUI:CallFunc(function()
GUI:Text_setString(countdownText, "2")
end),
GUI:DelayTime(0.5),
GUI:CallFunc(function()
GUI:Text_setString(countdownText, "1")
end),
GUI:DelayTime(0.5),
GUI:CallFunc(function()
-- 这里创建技能特效并移除其他组件
end)
)
```
这个动作序列总共只有1.5秒,所以特效会在1.5秒后就结束并移除。
要实现40秒的持续效果,你需要:
1. **在`showEffect`函数中增加定时器**来管理40秒的倒计时
2. **使用`SL:Schedule`或`SL:ScheduleOnce`来创建定时器**
修改后的`showEffect`函数应该这样写:
```lua
local function showEffect(msgID, p1, p2, p3, msgData)
local data = SL:JsonDecode(msgData, false) or {}
SL:print("特效数据", data)
local num = data.num or 0
local eff1, eff2 = data.preEff, data.startEff
-- 创建父节点作为容器
local sceneLayer = GUI:Win_Create("EffectLayer", 0, 0, 0, 0, false, false, true, false, false, false, 1)
-- 存储所有需要管理的对象
local effectObjects = {}
local timers = {} -- 存储定时器
for i = 1, num do
-- 获取屏幕尺寸
local screenWidth = SL:GetMetaValue("SCREEN_WIDTH") or 1280
local screenHeight = SL:GetMetaValue("SCREEN_HEIGHT") or 720
-- 在屏幕范围内随机位置显示特效
local posX, posY
if data.mapdata and data.mapdata[i] then
posX = data.mapdata[i].x or math.random(100, screenWidth - 100)
posY = data.mapdata[i].y or math.random(100, screenHeight - 100)
else
posX = math.random(100, screenWidth - 100)
posY = math.random(100, screenHeight - 100)
end
-- 创建预警特效
local circleEffect = GUI:Effect_Create(sceneLayer, "circle_effect_" .. i,
posX, posY, 0, eff1, 0, 0, 0, 1)
-- 创建进度条作为倒计时显示
local loadingBar = GUI:LoadingBar_Create(circleEffect, "LoadingBar_" .. i,
0, 30, "res/er dalu/leishen/jdt/1.png", 0)
GUI:setContentSize(loadingBar, 100, 20)
GUI:LoadingBar_setPercent(loadingBar, 100)
-- 创建图片
local image6 = GUI:Image_Create(sceneLayer, "Image_6",
posX - 50, posY - 50, "res/er dalu/leishen/jdt/leishen.png")
GUI:setVisible(image6, true)
GUI:setContentSize(image6, 100, 100)
GUI:setAnchorPoint(image6, 0.5, 0.5)
-- 创建倒计时数字文本
local countdownText = GUI:Text_Create(circleEffect, "countdown_" .. i,
0, 30, 20, "#FF0000", "40")
-- 存储对象
effectObjects[i] = {
circleEffect = circleEffect,
loadingBar = loadingBar,
countdownText = countdownText,
image6 = image6,
posX = posX,
posY = posY,
eff2 = eff2
}
-- 40秒倒计时定时器
local countdown = 40
local timer = SL:Schedule(function()
if countdown > 0 then
countdown = countdown - 1
GUI:Text_setString(countdownText, tostring(countdown))
-- 更新进度条
local percent = (countdown / 40) * 100
GUI:LoadingBar_setPercent(loadingBar, percent)
-- 最后3秒显示数字倒计时
if countdown <= 3 then
-- 可以添加闪烁效果
local blinkAction = GUI:ActionSequence(
GUI:ActionFadeTo(0.2, 100),
GUI:ActionFadeTo(0.2, 255)
)
GUI:runAction(countdownText, GUI:ActionRepeat(blinkAction, 2))
end
else
-- 倒计时结束,创建技能特效
local skillEffect = GUI:Effect_Create(sceneLayer, "skill_effect_" .. i..math.random(999999),
posX, posY, 0, eff2, 0, 0, 0, 1)
local skillAction = GUI:ActionSequence(
GUI:ActionScaleTo(0.2, 2.0),
GUI:DelayTime(0.3),
GUI:ActionFadeTo(0.5, 0),
GUI:CallFunc(function()
GUI:removeFromParent(skillEffect)
end)
)
GUI:runAction(skillEffect, skillAction)
-- 移除圈、进度条、图片和倒计时文本
GUI:removeFromParent(circleEffect)
GUI:removeFromParent(loadingBar)
GUI:removeFromParent(countdownText)
GUI:removeFromParent(image6)
-- 停止定时器
SL:UnSchedule(timer)
timers[i] = nil
end
end, 1)
timers[i] = timer
end
end
```
**关键修改点:**
1. **使用`SL:Schedule`创建每秒执行的定时器**,而不是使用动作序列
2. **在定时器回调中更新倒计时数字和进度条**
3. **倒计时结束后才创建技能特效并移除组件**
4. **添加了`timers`表来管理所有定时器**,便于后续清理
**注意:** 记得在适当的时候清理定时器,比如界面关闭时,可以使用`SL:UnSchedule(timer)`来停止定时器。
这样修改后,你的特效就会持续40秒,并且每秒更新倒计时显示和进度条了。
← 返回问答库