JS开发2048时addEventListener keydown触发后方块不移动问题
2048游戏按键触发但方块不移动问题修复
你的代码里有2个直接导致逻辑失效的错误,修复后即可正常运行:
- 方法名拼写错误导致逻辑中断
滑动完成后执行方块合并的代码中,方法名拼写错误:你写的是cell.merTiles(),正确方法名应为cell.mergeTiles(),少写了ge两个字符。JS执行到这行时会直接抛出「cell.merTiles is not a function」的类型错误,中断整个输入处理流程,不仅合并逻辑不执行,新方块生成、事件重新绑定的逻辑也全部不会跑,直接表现就是按键能打印日志但方块无响应。 - 提前return导致事件监听器只生效一次
你在游戏结束判断的代码块后错误地提前写了return语句,把重新绑定键盘事件的setupInput()挡在了return之后,属于永远不会执行的死代码。因为你绑定keydown事件时加了{once: true}配置,事件触发一次后浏览器会自动移除监听器,第一次按键后如果没有重新绑定,后续按键连日志都打不出来。
错误代码片段:
受JS自动分号插入规则影响,这里的if (!canMoveUp() && !canMoveDown() && !canMoveLeft() && !canMoveRight()) { newTile.waitForTransition(true).then(() => { alert("You lose!"); }); } return setupInput();return会被单独识别为返回语句,后面的setupInput()永远不会执行。
修复后的handleInput函数代码
直接替换原有的handleInput函数即可:
async function handleInput(e) { // 可选:阻止方向键默认滚动页面的行为 e.preventDefault(); console.log(e.key); switch (e.key) { case "ArrowUp": if(!canMoveUp()) { setupInput(); return; } await moveUp() break case "ArrowDown": if(!canMoveDown()) { setupInput(); return; } await moveDown() break case "ArrowLeft": if(!canMoveLeft()) { setupInput(); return; } await moveLeft() break case "ArrowRight": if(!canMoveRight()) { setupInput(); return; } await moveRight() break default: setupInput() return } // 修复方法名拼写 grid.cells.forEach(cell => cell.mergeTiles()); const newTile = new Tile(gameBoard); grid.randomEmptyCell().tile = newTile; if (!canMoveUp() && !canMoveDown() && !canMoveLeft() && !canMoveRight()) { newTile.waitForTransition(true).then(() => { alert("You lose!"); }); } // 移除错误的提前return,保证事件重新绑定 setupInput(); }
内容的提问来源于stack exchange,提问作者Patrik16
相关产品推荐
相关产品推荐

