用 Timer 控制帧刷新,每次触发时更新蛇头坐标、检测边界/自身/食物碰撞、调用 repaint();蛇身用整数二维数组按格子存储,方向仅存 currentDirection,paintComponent 中必须调用 super.paintComponent(g) 清背景。

怎么用Java和Swing开发一个贪吃蛇游戏_坐标移动、碰撞检测与定时器刷新

Swing 里怎么让蛇动起来:用 Timer 控制帧刷新

贪吃蛇不是靠“一直跑”动的,而是靠定时触发位置更新。Swing 提供的 javax.swing.Timer 是最稳妥的选择——它自动在事件调度线程(EDT)中执行,避免了多线程绘图冲突。

别用 Thread.sleep()java.util.Timer,前者会卡死 UI,后者回调不在 EDT,调 repaint() 可能无效或抛 IllegalStateException

坐标移动怎么写才不出错:用二维整数数组存蛇身,别用浮点或像素偏移

蛇的移动本质是“头进一格、尾退一格”。用 Listint[][] 存每节身体的行列索引(比如 [row, col]),格子大小统一设为 20px,所有坐标都按格子对齐。

常见错误是直接操作像素坐标加减速度值,结果导致蛇头“漂移”,和食物/边界对不齐,碰撞永远判不准。

碰撞检测为什么总漏判:边界、自身、食物必须分三步独立检查

很多人把所有碰撞塞在一个 if 里,结果食物刚被吃掉,下一帧蛇头还在老位置,边界检测却已经触发 Game Over。顺序和时机错了。

正确做法是在每次 Timer 触发后,按固定顺序检查:

漏判最多的情况是:食物生成后没校验是否落在蛇身上,结果一刷出来就 Game Over;或者自身碰撞用了 contains(head),但没排除头自己。

重绘闪烁或残影?paintComponent 里必须清背景 + 双缓冲默认开启

Swing 的 JPanel 默认启用双缓冲,所以不用手动开。但很多人在 paintComponent 里忘了调 super.paintComponent(g),导致旧画面残留。

另一个坑是用 getGraphics() 直接绘图——那是临时画布,下一帧就被擦掉,而且线程不安全。

真正麻烦的是输入响应延迟和计时器精度——Timer 在高负载下可能丢帧,如果靠它计分或存档,得额外加时间戳校准。不过单机小游戏,先跑通再说。

本文转载于:互联网 如有侵犯,请联系zhengruancom@outlook.com删除。
免责声明:正软商城发布此文仅为传递信息,不代表正软商城认同其观点或证实其描述。