You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java Applet图形初始化异常:按键控制矩形不显示求助

嘿,我来帮你排查这个Applet的问题~你的代码里有几个关键的小错误,导致矩形完全显示不出来,咱们一步步来修复:

核心问题分析

  1. 无效的Graphics对象:你在run方法里定义了Graphics g = null;,然后直接用这个空对象去调用绘图方法——这就像拿着一支不存在的笔画画,肯定啥也出不来。而且Applet的绘图上下文是由系统管理的,不能自己随便创建或拿null来用。
  2. 线程没正确执行:你创建线程的方式是loopThread = new Thread();,但你的类没实现Runnable接口,这个新线程的run方法是空的,你写的那堆循环代码根本没被执行到!
  3. 绘图逻辑不规范:你只在按键时尝试局部修改画面,但Applet初始化后没有初始绘制,而且系统触发重绘(比如窗口被遮挡后恢复)时,之前的内容会消失。

修复后的完整代码

import java.awt.*;
import java.applet.Applet;

// 类名首字母大写是Java规范,同时实现Runnable接口让线程能执行我们的run方法
public class Game extends Applet implements Runnable { 
    Thread loopThread;
    boolean left = false;
    boolean right = false;
    int platPos = 50;

    // Applet的标准初始化入口,在这里启动线程
    @Override
    public void init() { 
        loopThread = new Thread(this); // 把当前类实例传给Thread,让它执行我们的run方法
        loopThread.start();
    }

    @Override
    public void run() {
        Thread.currentThread().setPriority(Thread.MIN_PRIORITY);
        while (Thread.currentThread() == loopThread) {
            try {
                Thread.sleep(16); // 控制约60帧的帧率,避免CPU跑满
                repaint(); // 告诉系统需要重绘,会自动调用paint方法
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }

    // 所有绘图逻辑都放在这里,系统会传入有效的Graphics上下文
    @Override
    public void paint(Graphics g) {
        super.paint(g); // 先调用父类方法清除旧画面
        g.setColor(Color.WHITE);
        g.fillRect(0, 0, getWidth(), getHeight()); // 绘制白色背景覆盖之前的内容
        g.setColor(new Color(100, 100, 100));
        g.fillRect(50 + platPos, 200, 100, 20); // 绘制当前位置的灰色矩形
    }

    // 重写update避免默认的背景清除导致闪烁(可选优化)
    @Override
    public void update(Graphics g) {
        paint(g);
    }

    @Override
    public boolean keyDown(Event e, int key) {
        if (key == Event.LEFT) {
            platPos--; // 直接修改位置,paint会处理重绘
        }
        if (key == Event.RIGHT) {
            platPos++;
        }
        return true;
    }
}

关键修改说明

  • 让类实现Runnable接口,这样创建线程时传入this,线程才会执行我们写的run方法。
  • 用Applet的init方法启动线程,这是Applet的标准初始化时机。
  • run方法不再直接绘图,而是通过repaint()触发系统调用paint方法,确保拿到的是有效的Graphics对象。
  • 把所有绘图逻辑移到paint方法里:先画白色背景清除旧内容,再绘制当前位置的矩形,这样不管是初始显示还是按键移动,都能正确渲染。
  • 简化了按键处理逻辑,直接修改platPos,剩下的重绘交给paint方法。

测试注意事项

要运行这个Applet,你需要写一个简单的HTML文件(比如game.html):

<applet code="Game.class" width="400" height="300"></applet>

然后用JDK自带的appletviewer game.html命令来运行它,就能看到可以左右移动的灰色矩形啦~

内容的提问来源于stack exchange,提问作者Socks

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 07:58:26