0

最終プロジェクト用の最初の小さな Java ゲームがほぼ完成しました。小惑星を撃ったり避けたりする横スクロールゲームです。私の最後の問題は、小惑星の配列をプレイヤーのレーザーと衝突させる方法を考え出すことです。137行目に「AWT-EventQueue-0」java.lang.NullPointerException」があり、対処できません。どんな助けも大歓迎です。

編集:他のクラスに追加しました。コードの出所を示さないと、コードの機能を判断するのが難しいことに気づきました。

package ShooterGame;

import java.applet.Applet;
import java.applet.AudioClip;
import java.awt.*;
import java.awt.event.*;
import java.util.ArrayList;
import java.util.Random;

import javax.swing.*;

public class Board extends JPanel implements ActionListener
{   
    Enemy[] baddies = new Enemy[10000];
    Player p;
    Image img;
    int y;
    Timer time;
    boolean lost = false;
    static Font font = new Font("SanSerif", Font.BOLD, 24);
    public AudioClip theme, bang, laser;    
    static ArrayList<Enemy> enemies;

    public static int score = 0;
    public static int lives = 5;

    public Board() 
    {           
        p = new Player();       
        addKeyListener(new ActionListener());
        setFocusable(true);
        ImageIcon i = new ImageIcon("images/background.png");
        img = i.getImage();

        time = new Timer(5, this);
        time.start();

        for(int j = 0; j < baddies.length; j++)
        {   
            Random ran = new Random();
            y = ran.nextInt(365)+1;
            baddies[j]= new Enemy((100*j + 700), y, "images/asteroid.gif");
        }

        theme = Applet.newAudioClip(getClass().getResource("theme.mid"));
        theme.play();

        bang = Applet.newAudioClip(getClass().getResource("bang.wav"));
    }

    public void actionPerformed(ActionEvent e)
    {
        checkCollisions();
        ArrayList<?> bullets = Player.getBullets();

        for(int i = 0; i < bullets.size(); i++)
        {
            Bullet b = (Bullet)bullets.get(i);

            if(b.isVisible() == true)
            {
                b.move();
            }
            else
            {
                bullets.remove(i);
            }
        }

        p.move();
        for(int i = 0; i < baddies.length; i++)
        {
            if(p.x > 400)
            {
                baddies[i].move(p.getdx());
            }
        }

        repaint();
    }

    public void paint(Graphics g)
    {   
        super.paint(g);
        Graphics2D g2d = (Graphics2D) g;

        if(lost)
        {
            g2d.drawString("You Lose!", 300, 300);
        }

        if((p.getX() - 590) % 2400 == 0 || (p.getX() - 590) % 2400 == 1)
        {
            p.nx = 0;
        }

        if((p.getX() - 1790) % 2400 == 0 ||(p.getX() - 1790) % 2400 == 1)
        {
            p.nx2 = 0;
        }

        g2d.drawImage(img, 685-p.nx2, 0, null);

        if(p.getX() >= 590)
        {
            g2d.drawImage(img, 685-p.nx, 0, null);
        }

        g2d.drawImage(p.getImage(), p.edge, p.getY(), null);

        ArrayList<?> bullets = Player.getBullets();
        for(int i = 0; i < bullets.size(); i++)
        {
            Bullet b = (Bullet)bullets.get(i);
            g2d.drawImage(b.getImg(), b.getX(), b.getY(), null);

        }
            for(int i = 0; i < baddies.length; i++)
            {
                if(baddies[i].isAlive == true)
                {
                    g2d.drawImage(baddies[i].getImg(), baddies[i].getX(), baddies[i].getY(), null);
                }
            }

        g2d.setColor(Color.white);
        g2d.drawString("Score: " + score, 0, 320);
        g2d.drawString("Lives: " + lives, 80, 320);
    }

    public void checkCollisions()
    {       
        Rectangle[] rect = new Rectangle[baddies.length];
        for(int i = 0; i < baddies.length; i++)
        {
            Enemy e = (Enemy)baddies[i];
            rect[i] = e.getBounds();
        }

        ArrayList<?> bullets = Player.getBullets();
        for (int i = 0; i < bullets.size(); i++)
        {
            Bullet b = (Bullet) bullets.get(i);
            Rectangle b1 = b.getBounds();

            if (rect[i].intersects(b1) && baddies[i].isAlive())
            {
                score++;
                baddies[i].isAlive = false;
                baddies[i].isVisible = false;
                bang.play();
             }

            Rectangle h = p.getBounds();
            if (h.intersects(rect[i]))
            {
                if(baddies[i].isAlive() == true)
                {
                    lives--;
                    if(lives < 0)
                    {
                        lost = true;
                        theme.stop();
                        System.exit(1);
                    }
                }
            }
        }
    }

    private class ActionListener extends KeyAdapter
    {
        public void keyReleased(KeyEvent e)
        {
            p.keyReleased(e);
        }

        public void keyPressed(KeyEvent e)
        {
            p.keyPressed(e);
        }
    }
}

package ShooterGame;

import java.awt.*;

import javax.swing.ImageIcon;

public class Enemy 
{
    int x, y;
    Image img;
    boolean isAlive = true;
    boolean isVisible = true;


    public Enemy(int startX, int startY, String location)
    {
        x = startX;
        y = startY;
        ImageIcon l = new ImageIcon(location);
        img = l.getImage();
    }

    public Rectangle getBounds()
    {
        return new Rectangle(x, y, 60, 60);
    }


    public int getX() 
    {
        return x;
    }

    public int getY() 
    {
        return y;
    }

    public boolean isAlive() 
    {
        return isAlive;
    }

    public boolean isVisible() 
    {
        return isVisible;
    }

    public Image getImg() 
    {
        return img;
    }   

    public void move(int dx)
    {
        x = x - dx;
    }

}

銃弾

package ShooterGame;

import java.applet.Applet;
import java.awt.*;
import javax.swing.ImageIcon;
import java.applet.AudioClip;

public class Bullet 
{   
    int x, y;
    Image img;
    boolean visible;

    public Bullet(int startX, int startY)
    {
        x = startX;
        y = startY;

        ImageIcon newBullet = new ImageIcon("images/bullet.gif");
        img = newBullet.getImage();
        visible = true;
    }

    public Rectangle getBounds()
    {
        return new Rectangle(x, y, 9, 5);
    }

    public int getX() 
    {
        return x;
    }

    public int getY() 
    {
        return y;
    }

    public Image getImg() 
    {
        return img;
    }

    public boolean isVisible() 
    {
        return visible;
    }

    public void move()
    {
        x = x + 2;
        if(x > 700)
        {
            visible = false;
        }
    }

    public void setVisible(boolean isVisible)
    {
        visible = isVisible;
    }
}

プレーヤー

package ShooterGame;

import java.applet.Applet;
import java.applet.AudioClip;
import java.awt.*;
import java.awt.event.KeyEvent;
import java.util.ArrayList;

import javax.swing.ImageIcon;

public class Player 
{

    int x, dx, y, dy, nx2, nx, edge, ceiling; 
    Image player;
    ImageIcon ib = new ImageIcon("images/player1back.gif");
    ImageIcon i = new ImageIcon("images/playerstill.gif");
    ImageIcon f = new ImageIcon("images/playerforward.gif");
    ImageIcon up = new ImageIcon("images/playerup.gif");
    ImageIcon down = new ImageIcon("images/playerdown.gif");
    public AudioClip laser;
    static ArrayList<Bullet> bullets;

    public Player()
    {laser = Applet.newAudioClip(getClass().getResource("laser.wav"));
        player = ib.getImage();
        x = 75;
        nx = 0;
        nx2 = 685;
        y = 172;
        edge = 150;
        ceiling = 0;
        bullets = new ArrayList<Bullet>();
    }

    public static ArrayList<Bullet> getBullets()
    {
        return bullets;
    }

    public void fire()
    {
        Bullet z = new Bullet((edge + 60), (y+17));
        bullets.add(z); 
    }

    public Rectangle getBounds()
    {
        return new Rectangle(edge, y, 43, 39);
    }

    public void move()
    {
        y = y + dy;
        if(y < ceiling)
        {
            y = ceiling;
        }

        if(y > 290)
        {
            y = 290;
        }

        if(dx != -1)
        {
            if(edge + dx <= 151)
            {
                edge = edge + dx;
            }
            else
            {
                x = x + dx;
                nx2 = nx2 + dx;
                nx = nx + dx;
            }
        }
        else
            {
            if(edge + dx > 0)
            {
                edge = edge + dx;
            }
        }   

    }

    public int getX()
    {
        return x;
    }

    public int getdx()
    {
        return dx;
    }

    public int getY()
    {
        return y;
    }

    public Image getImage()
    {
        return player;
    }

    public void keyPressed(KeyEvent e)
    {
        int key = e.getKeyCode();

        if(key == KeyEvent.VK_RIGHT)
        {
            dx = 2;
            player = f.getImage();
        }
        if(key == KeyEvent.VK_UP)
        {
            dy = -1;
            player = up.getImage();
        }
        if(key == KeyEvent.VK_DOWN)
        {
            dy = 1;
            player = down.getImage();
        }
        if(key == KeyEvent.VK_SPACE)
        {
            fire();
            laser.play();
        }
    }

    public void keyReleased(KeyEvent e)
    {
        int key = e.getKeyCode();

        if(key == KeyEvent.VK_RIGHT)
        {
            dx = 1;
            player = ib.getImage();
        }

        if(key == KeyEvent.VK_UP)
        {
            dy = 0;
            player = ib.getImage();
        }

        if(key == KeyEvent.VK_DOWN)
        {
            dy = 0;
            player = ib.getImage();
        }
    }
}

フレーム

package ShooterGame;

import javax.swing.*;

public class Frame 
{
    public AudioClip theme;

        public Frame()
        {
                JFrame frame = new JFrame();
                frame.add(new Board());
                frame.setTitle("SideShooter");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.setSize(700,365);
                frame.setVisible(true);
                frame.setLocationRelativeTo(null);

        }

        public static void main(String[] args)
        {
                new Frame();

        }
}
4

2 に答える 2

0

さて、問題は他の回答で言及されている行ですが、衝突をチェックする前にすべての敵が初期化されていない可能性があると思います。最初に10000個作成しているので、アクション実行メソッドは、すべてが作成される前に衝突をチェックしている可能性があると思います。

試してみる1つのことは、持っている敵の数を減らして、それがまだ発生し続けるかどうかを確認することです。100または1000を試してください。ただし、それでも問題は解決しません。

自分のループで実行するようにゲームを変更したいのですが、現時点では、プレーヤーがアクションを実行したときにのみ衝突をチェックしています。したがって、プレーヤーが移動を停止した場合、衝突検出は行われません。

「Javaでのキラーゲームプログラミング」という本を見つけて、無料の電子ブックバージョンがあり、ゲームループの作成に関する最初の2つの章を読むことをお勧めします。この本は少し古いですが、ループの基本はとても良いです。

ここでのこの質問には、非常に単純なループと、それを改善する方法についてのコメントのいくつかの提案も含まれています。

于 2012-05-07T01:13:40.473 に答える
0

エラーは行にあります

rect[i] = e.getBounds();

クラスの境界をEnemy正しく初期化していませんか? または、配列から取り出した Enemy が null である可能性があります。

于 2012-05-07T00:32:41.273 に答える