refactor: 使用flutter对原先的web项目重构,正在进行中
This commit is contained in:
1 parent
273224f5cf
commit
18017f819a
205 files changed
+13563
No files matched your search
@@ -0,0 +1,92 @@
|
||||
// 输入:IWBT 经典键位(Shift 跳 / Z 跳 / X 射击 / R 重来)
|
||||
export const BIND = {
|
||||
left: ['ArrowLeft', 'KeyA'],
|
||||
right: ['ArrowRight', 'KeyD'],
|
||||
up: ['ArrowUp', 'KeyW'],
|
||||
down: ['ArrowDown', 'KeyS'],
|
||||
jump: ['ShiftLeft', 'ShiftRight', 'Space', 'KeyZ', 'KeyN'],
|
||||
shoot: ['KeyX', 'KeyJ', 'KeyC', 'KeyM'],
|
||||
suicide: ['KeyR'], // IWBT 标准:自杀并回到最近存档点
|
||||
restart: ['Backspace'], // 整关从头再来(放弃所有存档点)
|
||||
pause: ['Escape', 'KeyP'],
|
||||
menu: ['KeyQ'],
|
||||
};
|
||||
|
||||
// 出厂键位快照(供设置里的「恢复默认」使用)
|
||||
const DEFAULT_BIND = JSON.parse(JSON.stringify(BIND));
|
||||
|
||||
const down = new Set(); // 当前按住的原始 code
|
||||
const now = {}; // action 是否按下
|
||||
const prev = {}; // 上一帧
|
||||
const touch = {}; // action -> bool(来自触屏虚拟按键)
|
||||
const blocked = new Set(['Space', 'ArrowUp', 'ArrowDown', 'ArrowLeft', 'ArrowRight', 'Tab']);
|
||||
|
||||
export const Input = {
|
||||
enabled: true,
|
||||
/** 是否按下 */
|
||||
is(action) { return !!now[action]; },
|
||||
/** 本帧刚按下 */
|
||||
hit(action) { return !!now[action] && !prev[action]; },
|
||||
/** 本帧刚松开 */
|
||||
released(action) { return !now[action] && !!prev[action]; },
|
||||
raw(code) { return down.has(code); },
|
||||
anyHit() { for (const k in now) if (now[k] && !prev[k]) return true; return false; },
|
||||
|
||||
clear() {
|
||||
down.clear();
|
||||
for (const k in now) now[k] = false;
|
||||
for (const k in prev) prev[k] = false;
|
||||
},
|
||||
|
||||
/** 每逻辑帧末尾调用 */
|
||||
endFrame() {
|
||||
for (const k in now) prev[k] = now[k];
|
||||
},
|
||||
};
|
||||
|
||||
function refresh() {
|
||||
for (const act in BIND) {
|
||||
let v = false;
|
||||
for (const c of BIND[act]) if (down.has(c)) { v = true; break; }
|
||||
if (touch[act]) v = true; // 触屏虚拟按键
|
||||
now[act] = Input.enabled ? v : false;
|
||||
}
|
||||
}
|
||||
|
||||
// ---------------- 触屏虚拟按键接口 ----------------
|
||||
export function setTouch(action, on) {
|
||||
if (!(action in touch)) touch[action] = false;
|
||||
if (touch[action] === on) return;
|
||||
touch[action] = on;
|
||||
refresh();
|
||||
}
|
||||
export function clearTouch() {
|
||||
let any = false;
|
||||
for (const k in touch) if (touch[k]) { touch[k] = false; any = true; }
|
||||
if (any) refresh();
|
||||
}
|
||||
|
||||
addEventListener('keydown', e => {
|
||||
if (blocked.has(e.code)) e.preventDefault();
|
||||
if (e.repeat) return;
|
||||
down.add(e.code);
|
||||
refresh();
|
||||
});
|
||||
addEventListener('keyup', e => {
|
||||
down.delete(e.code);
|
||||
refresh();
|
||||
});
|
||||
addEventListener('blur', () => { down.clear(); refresh(); });
|
||||
|
||||
// ---------------- 键位自定义(设置界面调用) ----------------
|
||||
/** 返回一份出厂键位的深拷贝 */
|
||||
export function defaultBindings() { return JSON.parse(JSON.stringify(DEFAULT_BIND)); }
|
||||
/** 用一份 {action: [code,...]} 映射覆盖当前生效键位(设置确定后调用) */
|
||||
export function applyBindings(map) {
|
||||
if (!map) return;
|
||||
for (const act in map) if (act in BIND) BIND[act] = map[act].slice();
|
||||
}
|
||||
|
||||
// 初始化
|
||||
for (const act in BIND) { now[act] = false; prev[act] = false; }
|
||||
export const ACTIONS = Object.keys(BIND);
|
||||
Reference in new issue
Block a user