JAVA小游戏——飞机大战

游戏简介

还记得风靡一时的飞机大战游戏么,不如现在用Java上手写一个玩 :D
操作简易,鼠标控制英雄机的移动。
击毁不同种类的飞行物会得到相应分数,击落蜜蜂可能加命或者由单发子弹变为双发。
运行页面如图(单击页面开始游戏)

游戏素材:戳这里

游戏结构

World主类:包含游戏框架并在main方法中实现各种功能。
FlyingObject类:所有飞行物都继承于此类。
HeroPlane类:设计英雄机的属性和方法。
BigAirplane、SmallAirplane类:敌机的属性和方法。
Bee类:蜜蜂的属性和方法。
Sky类:游戏背景的移动。
Bullet类:子弹的属性和方法。

游戏源码

World类

import java.awt.Graphics;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.image.BufferedImage;
import java.util.Arrays;
import java.util.Random;
import java.util.Timer;
import java.util.TimerTask;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class World extends JPanel{
    public static final int WIDTH = 400;
    public static final int HEIGHT = 700;
    private Sky sky = new Sky();
    private HeroPlane hero = new HeroPlane();
    private FlyingObject[] enemies = {};
    private Bullet[] bullets = {};

    public static final int START = 0;
    public static final int RUNNING = 1;
    public static final int PAUSE = 2;
    public static final int GAME_OVER = 3;
    private int state = START;
    //状态页面图片初始化
    private static BufferedImage start;
    private static BufferedImage pause;
    private static BufferedImage gameover;
    static{
        start = FlyingObject.loadImage("start.png");
        pause = FlyingObject.loadImage("pause.png");
        gameover = FlyingObject.loadImage("gameover.png");
    }

    //创建随机敌人对象
    public FlyingObject nextOne(){
        Random rand = new Random();
        int type = rand.nextInt(20);
        if(type<4){
            return new Bee(60,50);
        }else if(type<15){
            return new SmallAirplane(49,36);
        }else{
            return new BigAirplane(66,99);
        }
    }

    //限定敌人入场间隔时间
    int enterIndex = 0;
    int shootIndex2 = 0;
    public void enterAction(){
        enterIndex++;
        if(enterIndex%40==0){
            FlyingObject obj = nextOne();

            enemies = Arrays.copyOf(enemies, enemies.length+1);
            enemies[enemies.length-1] = obj;
        }
    }

    //实现飞行物走步
    public void stepAction(){
        sky.step();
        for(int i=0;i<enemies.length;i++){
            enemies[i].step();
        }
        for(int i=0;i<bullets.length;i++){
            bullets[i].step();
        }
    }

    //实现子弹入场
    int shootIndex = 0;
    public void shootAction(){
        shootIndex++;
        if(shootIndex%30==0){
            Bullet[] bs = hero.shoot();
            bullets = Arrays.copyOf(bullets,bullets.length+bs.length);
            System.arraycopy(bs,0,bullets,bullets.length-bs.length,bs.length);
        }
    }

    //删除越界对象
    public void outOfBoundsAction(){
        int index = 0;
        FlyingObject[] enemyLives = new FlyingObject[enemies.length];
        for(int i=0;i<enemies.length;i++){
            FlyingObject e = enemies[i];
            if(!e.outOfBounds()&&!e.isRemove()){
                enemyLives[index++] = e;
            }
        }
        enemies = Arrays.copyOf(enemyLives, index);

        index = 0;
        Bullet[] bulletLives = new Bullet[bullets.length];
        for(int i=0;i<bullets.length;i++){
            Bullet b = bullets[i];
            if(!b.outOfBounds()&&!b.isRemove()){
                bulletLives[index++] = b;
            }
        }
        bullets = Arrays.copyOf(bulletLives, index);
    }

    //根据击中的敌人类型判断奖励类型
    int score = 0;
    public void bangAction(){
        for(int i=0;i<bullets.length;i++){
            Bullet b = bullets[i];
            for(int j=0;j<enemies.length;j++){
                FlyingObject f = enemies[j];
                if(b.isLife()&&f.isLife()&&b.hit(f)){
                    b.goDead();
                    f.goDead();
                    if(f instanceof SmallAirplane){
                        SmallAirplane e = (SmallAirplane)f;
                        score = score + e.getScore();
                    }else if(f instanceof BigAirplane){
                        BigAirplane e = (BigAirplane)f;
                        score = score + e.getScore();
                    }else if(f instanceof Bee){
                        Bee e = (Bee)f;
                        int type = e.getAwardType();
                        switch(type){
                        case Bee.ADD_FIRE:
                            hero.addFire();
                            break;
                        case Bee.ADD_LIFE:
                            hero.addLife();
                            break;
                        }
                    }
                }
            }

        }
    }

    //英雄机与敌人的碰撞
    public void hitAction(){
        for(int i=0;i<enemies.length;i++){
            FlyingObject f = enemies[i];
            if(f.isLife()&&hero.isLife()&&f.hit(hero)){
                f.goDead();
                hero.reduceLife();
                hero.clearFire();
                break;
            }
        }
    }

    //判断游戏是否结束
    public void checkGameOverAction(){
        if(hero.getLife()<=0){
            state = GAME_OVER;
        }
    }

    //设置定时器执行
    public void action(){
        //添加鼠标移动事件的侦听
        MouseAdapter m = new MouseAdapter(){
            public void mouseMoved(MouseEvent e){
                if(state==RUNNING){
                    int x = e.getX();
                    int y = e.getY();
                    hero.moveTo(x, y);
                }
            }
            //鼠标点击事件的侦听
            public void mouseClicked(MouseEvent e){
                switch(state){
                case START:
                    state = RUNNING;
                    break;
                case GAME_OVER:
                    score = 0;
                    hero = new HeroPlane();
                    enemies = new FlyingObject[0];
                    bullets = new Bullet[0];
                    state = START;
                    break;
                }
            }
            //鼠标移出事件的侦听
            public void mouseExited(MouseEvent e){
                if(state==RUNNING){
                    state = PAUSE;
                }
            }
            //鼠标移入事件的侦听
            public void mouseEntered(MouseEvent e){
                if(state==PAUSE){
                    state = RUNNING;
                }
            }
        };
        this.addMouseListener(m);
        this.addMouseMotionListener(m);

        Timer timer = new Timer();
        int interval = 10;
        timer.schedule(new TimerTask(){
            public void run(){
                if(state==RUNNING){
                    enterAction();
                    stepAction();
                    shootAction();
                    outOfBoundsAction();
                    bangAction();
                    hitAction();
                    checkGameOverAction();
                }
                repaint();
            }

        },interval,interval);

    }
    //画出对象
        public void paint(Graphics g){
            sky.paint(g);
            hero.paint(g);
            for(int i=0;i<enemies.length;i++){
                enemies[i].paint(g);
            }
            for(int i=0;i<bullets.length;i++){
                bullets[i].paint(g);
            }

            //画出score和life的值
            g.drawString("SCORE:"+score,10,20);
            g.drawString("LIFE:"+hero.getLife(),10,40);
            //画出状态图
            switch(state){
            case START:
                g.drawImage(start,-10,-30,null);
                break;
            case PAUSE:
                g.drawImage(pause,-10,0,null);
                break;
            case GAME_OVER:
                g.drawImage(gameover,-10,0,null);
                break;
            }
        }

    //主方法
    public static void main(String[] args) {
        JFrame frame = new JFrame();
        World world = new World();
        frame.add(world);

        frame.setSize(WIDTH, HEIGHT);
        frame.setVisible(true);
        frame.setLocationRelativeTo(null);
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        world.action();

    }   

}

FlyingObject类

import java.awt.Graphics;
import java.awt.image.BufferedImage;
import java.util.Random;
import javax.imageio.ImageIO;

public abstract class FlyingObject {
    protected int width;
    protected int height;
    protected int x;
    protected int y;

    public static final int LIFE = 0;
    public static final int DEAD = 1;
    public static final int REMOVE = 2;
    protected int state = LIFE;

    public FlyingObject(){}

    public FlyingObject(int width,int height){
        this.width = width;
        this.height = height;
        Random r = new Random();
        x = r.nextInt(World.WIDTH-this.width+1);
        y = -this.height;
    }
    //定义导入图片的方法
    public static BufferedImage loadImage(String fileName){
        try{
            BufferedImage img = ImageIO.read(FlyingObject.class.getResource(fileName));
            return img;
        }catch(Exception e){
            e.printStackTrace();
            throw new RuntimeException();
        }
    }
    //获取图像的抽象方法
    public abstract BufferedImage getImage();

    public void paint(Graphics g){
        g.drawImage(getImage(), x, y, null);
    }
    //判断飞行物状态
    public boolean isLife(){
        return state == LIFE;
    }
    public boolean isDead(){
        return state == DEAD;
    }
    public boolean isRemove(){
        return state == REMOVE;
    }

    public void goDead(){
        state = DEAD;
    }
    //飞行物走步的抽象方法
    public abstract void step();

    //判断对象是否越界的抽象方法
    public abstract boolean outOfBounds();

    //判断飞行物之间是否发生碰撞
    public boolean hit(FlyingObject other){
        int x1 = this.x - other.width;
        int x2 = this.x + this.width;
        int y1 = this.y - other.height;
        int y2 = this.y + this.height;
        int x = other.x;
        int y = other.y;

        return x>=x1 && x<=x2 && y>=y1 && y<=y2;
    }
}

HeroPlane类

import java.awt.image.BufferedImage;
import java.util.Arrays;

public class HeroPlane extends FlyingObject{
    //导入英雄机的图像
    private static BufferedImage[] images;
    static{
        images = new BufferedImage[6];
        for(int i=0;i<images.length;i++){
            images[i] = loadImage("hero"+i+".png");
        }
    }
    private int life;
    private int fire;

    /*
     *构造方法 
     */
    public HeroPlane(){
        width = 97;
        height = 124;
        x = 140;
        y = 400;
        life = 3;
        fire = 0;
    }

    public void step(){

    }
    //英雄机随鼠标移动
    public void moveTo(int x,int y){
        this.x = x-this.width/2;
        this.y = y-this.height/2;
    }

    //获取英雄机在不同状态下的图像
    int index = 0;
    int deadIndex = 2;
    public BufferedImage getImage(){
        if(isLife()){
            return images[index++%2];
        }else if(isDead()){
            BufferedImage img = images[deadIndex++];
            if(deadIndex==images.length){
                state = REMOVE;
            }
            return img;
        }
        return null;
    }
    //控制子弹的位置和火力
    public Bullet[] shoot(){
        int xStep = this.width/4;
        int yStep = 20;
        if(fire>0){
            Bullet[] bs = new Bullet[2];
            bs[0] = new Bullet(this.x+1*xStep,this.y-yStep);
            bs[1] = new Bullet(this.x+3*xStep,this.y-yStep);
            fire-=2;
            return bs;
        }else{
            Bullet[] b = new Bullet[1];
            b[0] = new Bullet(this.x+2*xStep,this.y-yStep);
            return b;
        }
    }

    public boolean outOfBounds(){
        return false;
    }

    public void addLife(){
        life++;
    }

    public void addFire(){
        fire += 40;
    }

    public int getLife(){
        return life;
    }

    public void reduceLife(){
        life--;
    }

    public void clearFire(){
        fire = 0;
    }
}

BigAirplane类

import java.awt.image.BufferedImage;

public class BigAirplane extends FlyingObject{
    //导入大敌机的图像
    private static BufferedImage[] images;
    static{
        images = new BufferedImage[5];
        for(int i=0;i<images.length;i++){
            images[i]=loadImage("bigplane"+i+".png");
        }
    }
    private int speed;

    public BigAirplane(int width,int height){
        super(width,height);
        speed = 2;
    }

    //大敌机走步
    public void step(){
        y += speed;
    }

    //获取大敌机在不同状态下的图像
    int deadIndex = 1;
    public BufferedImage getImage(){
        if(isLife()){
            return images[0];
        }else if(isDead()){
            BufferedImage img = images[deadIndex++];
            if(deadIndex==images.length){
                state = REMOVE;
            }
            return img;
        }
        return null;
    }
    //判断大敌机是否已越界
    public boolean outOfBounds(){
        return this.y>=World.HEIGHT;
    }

    public int getScore(){
        return 3;
    }

    public Bullet[] shoot(){
        int yStep = 20;
        Bullet[] b = new Bullet[1];
        b[0] = new BulletFromEnemy(this.x+this.width/2,this.y+yStep);
        return b;
    }

}

SmallAirplane类

import java.awt.image.BufferedImage;

public class SmallAirplane extends FlyingObject{
    //导入小敌机的图像
    private static BufferedImage[] images;
    static{
        images = new BufferedImage[5];
        for(int i=0;i<images.length;i++){
            images[i] = loadImage("airplane"+i+".png");
        }
    }
    int speed;

    SmallAirplane(int width,int height){
        super(width,height);
        speed = 2;
    }
    //小敌机走步
    public void step(){
        y += speed;
    }

    //获取小敌机在不同状态下的图像
    int deadIndex = 1;
    public BufferedImage getImage(){
        if(isLife()){
            return images[0];
        }else if(isDead()){
            BufferedImage img = images[deadIndex++];
            if(deadIndex==images.length){
                state = REMOVE;
            }
            return img;
        }
        return null;
    }
    //判断小敌机是否已越界
    public boolean outOfBounds(){
        return this.y>=World.HEIGHT;
    }

    public int getScore(){
        return 5;
    }
}

Bee类

import java.awt.image.BufferedImage;
import java.util.Random;

public class Bee extends FlyingObject{
    //导入小蜜蜂的图像
    private static BufferedImage[] images;
    static{
        images = new BufferedImage[5];
        for(int i=0;i<images.length;i++){
            images[i] = loadImage("bee"+i+".png");
        }
    }
    private int xSpeed;
    private int ySpeed;
    private int awardType;
    public static final int ADD_FIRE = 0;
    public static final int ADD_LIFE = 1;

    public Bee(int width,int height){
        super(width,height);
        xSpeed = 1;
        ySpeed = 2;
        Random r = new Random();
        awardType = r.nextInt(2);
    }

    //小蜜蜂走步
    public void step(){
        x += xSpeed;
        y += ySpeed;
        if(x>=World.WIDTH-this.width||x<=0){
            xSpeed = (-1)*xSpeed;
        }
    }

    //获取小蜜蜂在不同状态下的图像
    int deadIndex = 1;
    public BufferedImage getImage(){
        if(isLife()){
            return images[0];
        }else if(isDead()){
            BufferedImage img = images[deadIndex++];
            if(deadIndex==images.length){
                state = REMOVE;
            }
            return img;
        }
        return null;
    }
    //判断小蜜蜂是否已越界
    public boolean outOfBounds(){
        return this.y>=World.HEIGHT;
    }

    public int getAwardType(){
        return this.awardType;
    }
}

Sky类

import java.awt.Graphics;
import java.awt.image.BufferedImage;

public class Sky extends FlyingObject{
    //导入天空的图像
    private static BufferedImage image;
    static{
        image = loadImage("background.png");
    }
    private int speed;
    private int y1;

    public Sky(){
        width = World.WIDTH;
        height = World.HEIGHT;
        x = 0;
        y = 0;
        y1 = -this.height;
        speed = 1;
    }
    //天空走步
    public void step(){
        y += speed;
        y1 += speed;
        if(y>=this.height){
            y = -this.height;
        }
        if(y1>=this.height){
            y1 = -this.height;
        }
    }
    //获取天空的图像
    public BufferedImage getImage(){
        return image;
    }

    public void paint(Graphics g){
        g.drawImage(getImage(), x, y, null);
        g.drawImage(getImage(), x, y1, null);
    }

    public boolean outOfBounds(){
        return false;
    }
}

Bullet类

import java.awt.image.BufferedImage;

public class Bullet extends FlyingObject{
    //导入子弹的图像
    private static BufferedImage image;
    static{
        image = loadImage("bullet.png");
    }
    private int speed;

    public Bullet(int x,int y){
        width = 8;
        height = 14;
        this.x = x;
        this.y = y;
        speed = 3;
    }
    //子弹走步
    public void step(){
        y -= speed;
    }
    //获取子弹的图像
    public BufferedImage getImage(){
        if(isLife()){
            return image;
        }
        if(isDead()){
            state = REMOVE;
        }
        return null;
    }
    //判断子弹是否已越界
    public boolean outOfBounds(){
        return this.y<=-this.height;
    }
}
  • 3
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
飞机大战游戏中,血量和胜负是非常重要的元素。我们可以通过以下步骤来实现它们: 1. 定义玩家飞机和敌机的血量属性,可以将其定义为成员变量。 2. 在玩家飞机和敌机被击中时,减少对应的血量。 3. 当玩家飞机或敌机的血量为0时,判断游戏胜负。 4. 在游戏结束时,显示胜负信息并提示是否重新开始游戏。 下面是具体的实现步骤: 1. 定义玩家飞机和敌机的血量属性 在Plane类中添加以下成员变量: ```java private int hp; // 飞机血量 ``` 在EnemyPlane类和PlayerPlane类中分别初始化血量: ```java public class EnemyPlane extends Plane { // 构造方法 public EnemyPlane(int x, int y, BufferedImage image) { super(x, y, image); this.hp = 3; // 初始化敌机血量为3 } } public class PlayerPlane extends Plane { // 构造方法 public PlayerPlane(int x, int y, BufferedImage image) { super(x, y, image); this.hp = 5; // 初始化玩家飞机血量为5 } } ``` 2. 减少血量 在Plane类中添加以下方法: ```java public void decreaseHp() { hp--; // 血量减1 } ``` 在Bullet类中,击中敌机时调用敌机的decreaseHp()方法: ```java public void hitEnemy(EnemyPlane enemy) { enemy.decreaseHp(); // 减少敌机血量 // 判断敌机是否被击败 if (enemy.getHp() == 0) { enemy.setAlive(false); // 敌机死亡 score += 10; // 得分加10分 } } ``` 在GameFrame类的paint()方法中,绘制玩家飞机和敌机的血条: ```java // 绘制玩家飞机血条 g.setColor(Color.RED); g.fillRect(20, 30, playerPlane.getHp() * 20, 10); // 绘制敌机血条 for (EnemyPlane enemy : enemies) { if (enemy.isAlive()) { // 只绘制存活的敌机血条 g.setColor(Color.RED); g.fillRect(enemy.getX(), enemy.getY() - 10, enemy.getHp() * 20, 5); } } ``` 3. 判断游戏胜负 在GameFrame类中添加以下方法: ```java // 判断游戏是否结束 public boolean isGameOver() { // 玩家飞机血量为0,游戏失败 if (playerPlane.getHp() == 0) { return true; } // 所有敌机均被击败,游戏胜利 for (EnemyPlane enemy : enemies) { if (enemy.isAlive()) { return false; // 还有存活的敌机,游戏继续 } } return true; // 没有存活的敌机,游戏胜利 } ``` 在GameFrame类的run()方法中,判断游戏是否结束: ```java // 游戏主循环 public void run() { while (true) { // 更新游戏状态 update(); // 绘制游戏界面 repaint(); // 线程休眠 try { Thread.sleep(10); } catch (InterruptedException e) { e.printStackTrace(); } // 判断游戏是否结束 if (isGameOver()) { // 显示游戏结束信息 String message; if (playerPlane.getHp() == 0) { message = "Game Over! You Lose!"; } else { message = "Game Over! You Win! Score: " + score; } int option = JOptionPane.showConfirmDialog(this, message + " Restart?", "Game Over", JOptionPane.YES_NO_OPTION); if (option == JOptionPane.YES_OPTION) { restart(); // 重新开始游戏 } else { System.exit(0); // 退出游戏 } } } } ``` 4. 显示胜负信息并提示是否重新开始游戏游戏结束时,使用JOptionPane显示游戏胜负信息,并提示是否重新开始游戏。如果玩家选择重新开始游戏,则调用restart()方法重新初始化游戏状态。 ```java // 显示游戏结束信息 String message; if (playerPlane.getHp() == 0) { message = "Game Over! You Lose!"; } else { message = "Game Over! You Win! Score: " + score; } int option = JOptionPane.showConfirmDialog(this, message + " Restart?", "Game Over", JOptionPane.YES_NO_OPTION); if (option == JOptionPane.YES_OPTION) { restart(); // 重新开始游戏 } else { System.exit(0); // 退出游戏 } ``` 至此,我们已经成功地实现了飞机大战游戏中的血量和胜负功能,玩家可以享受更加丰富的游戏体验。
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值