添加keylistener会返回空指针异常

时间:2016-01-05 11:33:24

标签: java nullpointerexception keyevent

我正在学习用Java编写2D游戏很长一段时间。在我最新的游戏中,我试图创建一个私有类来处理Player类中的关键事件,我这样做:

package game;

import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;

public class Player {

    final private int MOVEMENTSPEED = 4;
    final private int BOOST = 8;
    final private EventHandler HANDLER = new EventHandler();

    private int x, y;
    private int speedX, speedY;

    public Player(int x, int y){
        this.x = x;
        this.y = y;
    }

    public void update(){
        x += speedX;
        y += speedY;
    }

    public int getSpeedX() {
        return speedX;
    }

    public int getSpeedY() {
        return speedY;
    }

    public int getX() {
        return x;
    }

    public int getY() {
        return y;
    }

    public EventHandler getHandler(){
        return HANDLER;
    }

    private class EventHandler implements KeyListener{

        @Override
        public void keyPressed(KeyEvent e) {
            switch(e.getKeyCode()){
            case KeyEvent.VK_W: speedY = -MOVEMENTSPEED;
                break;
            case KeyEvent.VK_S: speedY = MOVEMENTSPEED;
                break;
            case KeyEvent.VK_A: speedX = -MOVEMENTSPEED;
                break;
            case KeyEvent.VK_D: speedX = MOVEMENTSPEED;
                break;
            }

        }

        @Override
        public void keyReleased(KeyEvent e) {
            switch(e.getKeyCode()){
            case KeyEvent.VK_W: speedY = 0;
            case KeyEvent.VK_S: 
                break;
            case KeyEvent.VK_A: speedX = 0;
            case KeyEvent.VK_D: 
                break;
            }   
        }

        @Override
        public void keyTyped(KeyEvent e) {
            // TODO Auto-generated method stub

        }
    }

这里是我尝试将eventHandler类添加到处理游戏循环,绘画等的类:

public class FrameWork extends Applet implements Runnable {

private URL base;
private Graphics second;

private Image image;

public static Player p;


@Override
public void start() {
    p = new Player(400, 400);
    Thread thread = new Thread(this);
    thread.start();
}

@Override
public void init() {
    setSize(1000, 600);
    setFocusable(true);
    Frame frame = (Frame) this.getParent().getParent();
    frame.setTitle("Assassin");
    frame.setResizable(false);
    **this.addKeyListener(p.getHandler());**
}

我已经使用了keylistener但是没有额外的类(在游戏循环的同一类中实现方法)或者创建一个完全不同的类并使用它的实例。

无论如何,我试图以不同的方式做,因为它看起来更舒服,但它总是返回错误java.lang.NullPointerException,我不明白为什么。

感谢您的帮助

2 个答案:

答案 0 :(得分:1)

Applet的生命周期以init开头,后来start被调用。 您在start之后调用了init中的播放器,因此p中的init为空。

使用init方法创建播放器。

请参阅Applet lifecycle: what's the practical difference between init() & start(), and destroy() & stop()?

答案 1 :(得分:0)

尝试进行这些更改:

  • 让您的播放器变量非静态。
  • 使用init()方法而不是start()方法初始化此变量。
  • public Player p; //changed this to be an instance variable (non-static)
    
    
    @Override
    public void start() {     
                    //moved initialization of player to init() method
        Thread thread = new Thread(this);
        thread.start();
    }
    
    @Override
    public void init() {
        setSize(1000, 600);
        setFocusable(true);
        Frame frame = (Frame) this.getParent().getParent();
        frame.setTitle("Assassin");
        frame.setResizable(false);
    
        p = new Player(400, 400); //initialize Player here
        this.addKeyListener(p.getHandler());
    }