v26110480 踢屏幕统一静止 25~35 秒一次;精彩分享 4~6 篇也出点赞头像(4~6 个随机),白底头像换深色
This commit is contained in:
42
js/bump.js
42
js/bump.js
@@ -83,9 +83,10 @@
|
||||
/* ---------- 孕周 → 阶段 ---------- */
|
||||
const STAGES = {
|
||||
// drum:原地带节奏连踢的概率;chain:踢完不歇、旁边紧接着再踢的概率,最多连 chainMax 下(2026-10-04 用户:「有时会带点节奏、可以连续踢」)
|
||||
flutter: { order: ['flick', 'flick', 'tap', 'flick'], gap: [10, 18], kick: false, again: 0, double: .45, follow: false, drum: 0, chain: 0 },
|
||||
active: { order: ORDER, gap: [14, 25], kick: true, again: .34, double: 0, follow: true, drum: .4, chain: .3, chainMax: 3 },
|
||||
late: { order: ['roll', 'butt', 'foot', 'roll', 'knee'], gap: [14, 25], kick: false, again: .15, double: 0, follow: true, slow: true, drum: .22, chain: .15, chainMax: 2 }
|
||||
// 11-05 起间隔统一 25~35 秒(gap() 读 GAP,这里各阶段的 gap 只作记录)
|
||||
flutter: { order: ['flick', 'flick', 'tap', 'flick'], gap: [25, 35], kick: false, again: 0, double: .45, follow: false, drum: 0, chain: 0 },
|
||||
active: { order: ORDER, gap: [25, 35], kick: true, again: .34, double: 0, follow: true, drum: .4, chain: .3, chainMax: 3 },
|
||||
late: { order: ['roll', 'butt', 'foot', 'roll', 'knee'], gap: [25, 35], kick: false, again: .15, double: 0, follow: true, slow: true, drum: .22, chain: .15, chainMax: 2 }
|
||||
};
|
||||
// 原地连踢的节奏型(每拍间隔,秒):匀速「哒哒哒」、「哒哒—哒」、「哒—哒哒」、两下一组
|
||||
const RHYTHMS = [[.42, .42, .42], [.3, .3, .75, .3], [.6, .28, .28], [.32, .9, .32], [.38, .38, .38, .38]];
|
||||
@@ -94,7 +95,12 @@
|
||||
const stageOf = w => w == null || w < 20 ? null : w < 26 ? STAGES.flutter : w < 34 ? STAGES.active : STAGES.late;
|
||||
let stage = stageOf(week);
|
||||
// 两次之间隔多久:20~22 周最稀(再 +40%),越往后越接近本阶段的基准
|
||||
const gap = () => { const g = stage ? stage.gap : [6, 10], m = week != null && week < 23 ? 1.4 : 1; return (g[0] + Math.random() * (g[1] - g[0])) * m; };
|
||||
/* 11-05 用户:「用户来到首页静止不动,至少停 25 秒、25~35 秒之间随机才踢一次,所有孕周都这样」→ 各阶段统一 25~35 秒,不再按阶段 / 20~22 周加长;
|
||||
而且要「一直没动」:点屏幕、滑动都会把倒计时重新从 25~35 秒数起(见 restart() 调用处),回到首页、开关打开也从头数 */
|
||||
const GAP = [25, 35];
|
||||
const gap = () => GAP[0] + Math.random() * (GAP[1] - GAP[0]);
|
||||
let lastInput = -1e9; /* 最近一次真正的手指 / 滚轮操作(图片加载、布局变化引起的 scroll 不算用户动了) */
|
||||
const restart = () => { if (mode === 'wait') wait = gap(); };
|
||||
addEventListener('mb-preg', e => {
|
||||
if (dbgWeek) return;
|
||||
week = e.detail ? e.detail.week : null; stage = stageOf(week);
|
||||
@@ -313,7 +319,7 @@
|
||||
}
|
||||
|
||||
scr.addEventListener('pointerdown', e => {
|
||||
lastTouch = performance.now();
|
||||
lastTouch = lastInput = performance.now(); restart();
|
||||
if (isOff() || (mode !== 'show' && !(mode === 'hide' && ft.h.v > 3)) || !ft.catchable) return;
|
||||
const p = toContent(e.clientX, e.clientY), fx = ft.x + ft.ox, fy = ft.y + ft.oy;
|
||||
// 只认鼓包中心那一圈;点在边上照常走原来的点击
|
||||
@@ -329,7 +335,9 @@
|
||||
window.addEventListener('click', e => {
|
||||
if (performance.now() < blockUntil) { blockUntil = 0; e.preventDefault(); e.stopImmediatePropagation(); }
|
||||
}, true);
|
||||
scr.addEventListener('scroll', () => { lastTouch = performance.now(); run(); }, { passive: true });
|
||||
/* 手指松开后的惯性滑动(3 秒内)也算在动;上面模块高度变化引起的滚动校正(浏览器 scroll anchoring)不算,否则停在页面中间时一直数不到 */
|
||||
scr.addEventListener('scroll', () => { const t = performance.now(); if (t - lastInput < 3000) { lastTouch = t; restart(); } run(); }, { passive: true });
|
||||
['touchstart', 'wheel'].forEach(t => scr.addEventListener(t, () => { lastInput = performance.now(); restart(); }, { passive: true }));
|
||||
|
||||
/* ---------- 物理 ---------- */
|
||||
function step(dt) {
|
||||
@@ -381,8 +389,8 @@
|
||||
else if (still < .4 && (still += dt) >= .4) {
|
||||
const fy = ft.y + ft.oy - top, seen = fy > 30 && fy < scr.clientHeight - 30;
|
||||
if (!seen && stage && stage.follow) {
|
||||
if (mode === 'show' || mode === 'hide') { ft.h.v = 0; ft.h.vel = 0; mode = 'wait'; release(); }
|
||||
if (mode === 'wait') wait = Math.min(wait, 1 + Math.random() * .6);
|
||||
if (mode === 'show' || mode === 'hide') { ft.h.v = 0; ft.h.vel = 0; mode = 'wait'; release(); wait = gap(); ft.chainNext = false; } /* 11-05 正踢着被滑走:重新等 25~35 秒 */
|
||||
/* 11-05 起不再把等待缩到 1 秒多(要静止 25~35 秒才踢),只把宝宝挪到这一屏 */
|
||||
}
|
||||
}
|
||||
spring(ft.h, dt); if (ft.h.v < 0) { ft.h.v = 0; ft.h.vel *= -.2; }
|
||||
@@ -495,9 +503,12 @@
|
||||
/* ---------- 循环:有东西在动才跑 rAF,静止时只用定时器数「下一次什么时候顶」 ---------- */
|
||||
let running = false, last = 0, painted = false;
|
||||
function frame(now) {
|
||||
const dt = Math.min((now - last) / 1000, 1 / 20); last = now;
|
||||
const wall = Math.min((now - last) / 1000, 1), dt = Math.min(wall, 1 / 20); last = now;
|
||||
/* 物理按 dt 封顶防跳帧;等待倒计时按真实时间补齐(掉帧 / 省电模式下 rAF 慢,按封顶的 dt 数会数成一倍长) */
|
||||
if (mode === 'wait' && active() && idle() && wall > dt) wait -= wall - dt;
|
||||
if (!active()) {
|
||||
if (mode !== 'wait') { mode = 'wait'; wait = 2; }
|
||||
if (mode !== 'wait') mode = 'wait';
|
||||
wait = gap(); /* 不在首页时一直重置:回到首页后从头数 25~35 秒 */
|
||||
ft.h.v = ft.h.vel = 0; pk.d.v = pk.d.vel = 0; pk.held = false; jg.x.v = jg.y.v = jg.x.vel = jg.y.vel = 0;
|
||||
}
|
||||
const n = Math.max(1, Math.round(dt * 120));
|
||||
@@ -515,18 +526,21 @@
|
||||
let tickT = 0;
|
||||
function tick() {
|
||||
clearTimeout(tickT);
|
||||
const t0 = performance.now();
|
||||
tickT = setTimeout(() => {
|
||||
if (running) return;
|
||||
if (active() && idle() && mode === 'wait') { wait -= .25; if (wait <= 0) { appear(); if (running) return; } }
|
||||
const el = Math.min((performance.now() - t0) / 1000, 1); /* 按真实经过的时间减(定时器会拖慢,按 .25 数会越数越长) */
|
||||
if (!active()) { if (mode === 'wait') wait = gap(); } /* 11-05 不在首页 / 切后台:回来从头数 25~35 秒 */
|
||||
else if (idle() && mode === 'wait') { wait -= el; if (wait <= 0) { appear(); if (running) return; } }
|
||||
tick();
|
||||
}, 250);
|
||||
}
|
||||
// 开关切换(「隐私权限」里那一行)
|
||||
addEventListener('mb-bump', () => {
|
||||
if (isOff()) { mode = 'wait'; ft.h.v = pk.d.v = 0; release(); cx.clearRect(0, 0, cv.width, cv.height); }
|
||||
else { wait = 1.2; tick(); }
|
||||
else { wait = gap(); tick(); }
|
||||
});
|
||||
// 调试 / 截图用:URL 带 bumpdebug 才挂
|
||||
if (/bumpdebug/.test(location.href)) window.__bump = { ft, pk, atoms: () => atoms.map(a => [a.el.className || a.el.tagName, Math.round(a.x), Math.round(a.y), a.el.style.transform.slice(0, 90)]), mode: () => mode, now: () => { wait = 0; lastTouch = 0; }, week: () => week, at: (k, x, y) => { lastTouch = 0; appear(k, { x, y: y + scr.scrollTop }); } };
|
||||
wait = 3; tick();
|
||||
if (/bumpdebug/.test(location.href)) window.__bump = { ft, pk, atoms: () => atoms.map(a => [a.el.className || a.el.tagName, Math.round(a.x), Math.round(a.y), a.el.style.transform.slice(0, 90)]), mode: () => mode, w: () => [Math.round(wait * 10) / 10, Math.round(performance.now() - lastTouch), active(), running], now: () => { wait = 0; lastTouch = 0; }, week: () => week, at: (k, x, y) => { lastTouch = 0; appear(k, { x, y: y + scr.scrollTop }); } };
|
||||
wait = gap(); tick();
|
||||
})();
|
||||
|
||||
Reference in New Issue
Block a user