Java游戏开发:JOptionPane弹窗打开时如何暂停当前线程?
嘿,这个需求其实很好实现,核心就是让游戏循环在弹窗弹出时暂停,等用户操作完弹窗再恢复(或者退出)。我给你梳理下具体步骤和代码调整方案:
1. 先准备线程安全的暂停标记
首先,我们需要一个线程可见的暂停开关,用来控制游戏循环的运行状态。用volatile修饰可以保证多线程之间的变量可见性,避免出现线程缓存导致的逻辑错误:
// 定义在游戏类中的成员变量 private volatile boolean isGamePaused = false; // 如果你的游戏循环是单独的线程,也要把它作为成员变量保存 private Thread gameLoopThread;
2. 改造游戏循环线程
如果你的游戏是在单独的线程里跑循环(这是推荐的做法,避免阻塞UI线程),需要在循环里加入暂停检查逻辑,当标记为暂停时,让线程进入等待状态:
// 初始化并启动游戏循环线程 gameLoopThread = new Thread(() -> { while (!Thread.currentThread().isInterrupted()) { // 循环检查是否暂停,若暂停则进入等待 while (isGamePaused) { synchronized (this) { try { wait(); // 线程进入等待,直到被唤醒 } catch (InterruptedException e) { // 如果线程被中断,直接退出循环 Thread.currentThread().interrupt(); break; } } } // 游戏核心逻辑:更新状态 + 渲染画面 updateGameState(); // 比如角色移动、碰撞检测等 renderGame(); // 绘制游戏画面 // 控制帧率,比如每秒60帧,约16ms一帧 try { Thread.sleep(16); } catch (InterruptedException e) { Thread.currentThread().interrupt(); break; } } }); gameLoopThread.start();
3. 在弹窗触发时控制游戏暂停/恢复
接下来修改你的windowClosing方法,在弹出JOptionPane之前先暂停游戏,等用户做出选择后再处理:
window.addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent event) { // 第一步:暂停游戏 isGamePaused = true; // 第二步:弹出确认弹窗(模态对话框,会阻塞当前UI线程) int dialogResult = JOptionPane.showConfirmDialog( null, "Would You Like to exit this game? Your progress will not be saved!", "Warning", JOptionPane.YES_NO_OPTION ); // 第三步:根据用户选择处理 if (dialogResult == JOptionPane.YES_OPTION) { // 用户选择退出:终止游戏线程,关闭窗口 gameLoopThread.interrupt(); window.dispose(); System.exit(0); } else { // 用户选择返回:恢复游戏运行 synchronized (this) { isGamePaused = false; notifyAll(); // 唤醒等待的游戏循环线程 } } } });
额外注意事项
- 如果你的游戏是直接在主线程运行的(不推荐,会导致UI卡顿),那JOptionPane本身是模态对话框,会自动阻塞主线程,游戏自然就暂停了,但这种方式体验很差,建议尽快改成单独的游戏循环线程。
wait()和notifyAll()必须在同步块中调用,确保线程安全,避免出现线程状态异常。volatile关键字不能少,否则游戏循环线程可能无法及时感知到isGamePaused的变化。
内容的提问来源于stack exchange,提问作者Danedesta
相关产品推荐
相关产品推荐

