收口聊天室安全边界并优化特效生命周期
This commit is contained in:
@@ -87,7 +87,7 @@ const LightningEffect = (() => {
|
||||
* @param {HTMLCanvasElement} canvas
|
||||
* @param {CanvasRenderingContext2D} ctx
|
||||
*/
|
||||
function _flash(canvas, ctx) {
|
||||
function _flash(canvas, ctx, timers) {
|
||||
const w = canvas.width;
|
||||
const h = canvas.height;
|
||||
|
||||
@@ -122,16 +122,16 @@ const LightningEffect = (() => {
|
||||
}
|
||||
|
||||
// 短促残影:闪电消失后保留一层很淡的余辉,避免“闪一下就没了”。
|
||||
setTimeout(() => {
|
||||
timers.push(setTimeout(() => {
|
||||
ctx.clearRect(0, 0, w, h);
|
||||
_drawStormGlow(canvas, ctx);
|
||||
ctx.fillStyle = "rgba(185, 205, 255, 0.12)";
|
||||
ctx.fillRect(0, 0, w, h);
|
||||
}, 90);
|
||||
}, 90));
|
||||
|
||||
setTimeout(() => {
|
||||
timers.push(setTimeout(() => {
|
||||
ctx.clearRect(0, 0, w, h);
|
||||
}, 190);
|
||||
}, 190));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -146,6 +146,7 @@ const LightningEffect = (() => {
|
||||
const DURATION = 7600;
|
||||
let count = 0;
|
||||
let finished = false;
|
||||
const timers = [];
|
||||
|
||||
/**
|
||||
* 统一结束特效,避免多次触发 onEnd。
|
||||
@@ -156,6 +157,7 @@ const LightningEffect = (() => {
|
||||
}
|
||||
|
||||
finished = true;
|
||||
timers.forEach((timer) => clearTimeout(timer));
|
||||
ctx.clearRect(0, 0, canvas.width, canvas.height);
|
||||
onEnd();
|
||||
}
|
||||
@@ -163,29 +165,41 @@ const LightningEffect = (() => {
|
||||
// 间隔不规则触发多次闪电(模拟真实雷电节奏)
|
||||
function nextFlash() {
|
||||
if (count >= FLASHES) {
|
||||
setTimeout(() => {
|
||||
timers.push(setTimeout(() => {
|
||||
finish();
|
||||
}, 520);
|
||||
}, 520));
|
||||
return;
|
||||
}
|
||||
|
||||
_flash(canvas, ctx);
|
||||
_flash(canvas, ctx, timers);
|
||||
count++;
|
||||
|
||||
// 让雷电节奏有“成组爆发”的感觉:有时连续两下,有时间隔更久。
|
||||
const delay = Math.random() > 0.65
|
||||
? 140 + Math.random() * 140
|
||||
: 420 + Math.random() * 520;
|
||||
setTimeout(nextFlash, delay);
|
||||
timers.push(setTimeout(nextFlash, delay));
|
||||
}
|
||||
|
||||
// 短暂延迟后开始第一次闪电
|
||||
setTimeout(nextFlash, 300);
|
||||
timers.push(setTimeout(nextFlash, 300));
|
||||
|
||||
// 安全兜底:超时强制结束
|
||||
setTimeout(() => {
|
||||
timers.push(setTimeout(() => {
|
||||
finish();
|
||||
}, DURATION + 500);
|
||||
}, DURATION + 500));
|
||||
|
||||
return {
|
||||
cancel() {
|
||||
if (finished) {
|
||||
return;
|
||||
}
|
||||
|
||||
finished = true;
|
||||
timers.forEach((timer) => clearTimeout(timer));
|
||||
ctx.clearRect(0, 0, canvas.width, canvas.height);
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
return { start };
|
||||
|
||||
Reference in New Issue
Block a user