Java NullPointerException,即使变量具有值

时间:2017-07-18 16:53:19

标签: java swing nullpointerexception jbutton

我目前正在开发一个用Java编写的游戏。 为此,我使用JFrames,JPanels和JButtons。

要选择要播放的等级,您必须选择一个世界,然后选择一个等级。

启动游戏后,我的WorldSelection的新实例会被创建,按下按钮后,所选的世界就会被设置,并创建一个新的LevelSelection实例。

当按下按钮时,等级会被设定。

这是我的问题:

Game类中,update方法每秒检查所选世界和级别60次,如果两者都选择了值,则会创建Stage的新实例/ Level

当我按下按钮设置Level时,我得到NullPointerException,即使它检查的值有值。

这不会一直发生;一半的工作时间(没有抛出异常),另外50%抛出异常。

Exception in thread "main" java.lang.NullPointerException
at Game.update(Game.java:41)
at Game.run(Game.java:23)
at Game.start(Game.java:34)
at Game.<init>(Game.java:10)
at Game.main(Game.java:77)

这是我的代码:

游戏课程:

public class Game {
private boolean running;
private WorldSelection ws;
private boolean chosen = false;

public Game() {
    ws = new WorldSelection();
    start();
}

public void run() {             // game loop
    long lastTime = System.nanoTime();
    long timer = System.currentTimeMillis();
    final double ns = 1000000000.0 / 60.0;
    double delta = 0;
    while (running) {
        long now = System.nanoTime();
        delta += (now - lastTime) / ns;
        lastTime = now;
        while (delta >= 1) {
            update();
            delta--;
        }
        if (System.currentTimeMillis() - timer == 1000) {
            timer += 1000;
        }
    }
}

public void start() {
    running = true;
    run();
}

private void update() {

    if (!chosen) {
        if (ws.getWorld() == 1) {
            if (ws.ls.getLevel() == 1) {
                chosen = true;
                //creates new stage here
            }
            if (ws.ls.getLevel() == 2) {
                chosen = true;
                //creates new stage here
            }
            if (ws.ls.getLevel() == 3) {
                chosen = true;
                //creates new stage here
            }
        }

        else if (ws.getWorld() == 2) {
            if (ws.ls.getLevel() == 1) {
                chosen = true;
                //creates new stage here
            }
            if (ws.ls.getLevel() == 2) {
                chosen = true;
                //creates new stage here
            }
            if (ws.ls.getLevel() == 3) {
                chosen = true;
                //creates new stage here
            }
        }
    }
    else {
        //game updates here
    }

}

public static void main(String[] args) {
    Game game = new Game();
}

}

WorldSelection课程:

import java.awt.Color;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class WorldSelection implements ActionListener {
public JFrame frame;
private int width, height;
private int world = 0;
private JButton button1;
public LevelSelection ls;
private JPanel panel; 

public WorldSelection() {

    this.width = 900;
    this.height = 506;
    frame = new JFrame();
    frame.setSize(width, height);
    frame.setResizable(false);
    frame.setTitle("Quentins Adventure");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.setLocationRelativeTo(null);

    panel = new JPanel();
    panel.setBackground(Color.black);

    button1 = new JButton("World 1");
    button1.setBackground(Color.LIGHT_GRAY);
    button1.setSize(120, 44);
    button1.setLocation(80, 350);
    button1.addActionListener(this);

    panel.add(button1);

    frame.add(panel);

    frame.setVisible(true);
}

public void actionPerformed(ActionEvent e) {
    if(e.getSource() == button1){
        setWorld(1);
        ls = new LevelSelection(235,268);
        frame.setVisible(false);
    }
}

public int getWorld() {
    return world;
}

public void setWorld(int world) {
    this.world = world;
}
}

LevelSelection类:

import java.awt.Color;
import java.awt.Font;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class LevelSelection implements ActionListener {
    public JFrame frame;
    private int width, height, buttonSize = 50;
    private int level = 0;
    private JButton button1;
    private Font font;
    private JPanel panel;


public LevelSelection(int bPosX,int bPosY) {


        this.width = 900;
        this.height = 506;
        frame = new JFrame();
        frame.setSize(width, height);
        frame.setResizable(false);
        frame.setTitle("Quentins Adventure - Wold Selection");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setLocationRelativeTo(null);

        panel = new JPanel();
        panel.setBackground(Color.black);

        button1 = new JButton("1");
        button1.setBackground(Color.LIGHT_GRAY);
        button1.setFont(font);
        button1.setSize(buttonSize, buttonSize);
        button1.setLocation(bPosX, bPosY);
        button1.addActionListener(this);

        panel.add(button1);

        frame.add(panel);
        frame.setVisible(true);
    }


@Override
public void actionPerformed(ActionEvent e) {
    if(e.getSource() == button1){
        setLevel(1);
        frame.dispose();
    }
    }


public int getLevel() {
    return level;
}


public void setLevel(int level) {
    this.level = level;
}

}

2 个答案:

答案 0 :(得分:7)

setWorld然后执行ls = new LevelSelection(235, 268);

这意味着ws.getWorld() == 1为真,但ws.lsnull

但这不仅是您的代码问题。你的代码不是线程安全的,这可能会导致很多错误,而这些错误很难找到。

答案 1 :(得分:1)

在您的班级$scope.orders = [{ "item": "DELL", "quantity": 6, "price": 144 }, { "item": "Samsung", "quantity": 3, "price": 3131 }, { "item": "222222", "quantity": 1, "price": 31 }, { "item": "111111111", "quantity": 1, "price": 13 }] 中,创建了类WorldSelection的引用,但是 在LevelSelection中初始化。因此在此参考之前 ActionPerformed()指向null。