【Java】 面对对象阶段练手项目【飞机大战】
飞机大战
一共八个类,分为Hero,Airplane,Enemy,Bee,Award,Bullet,FlyingObject,ShootGame.
下面是代码:
Hero
package planeWar;
import java.awt.image.BufferedImage;
public class Hero extends FlyingObject {
protected BufferedImage[] images = {};
protected int index = 0;
private int doubleFire;
private int life;
public Hero() {
life = 3;
doubleFire = 0;
this.image = ShootGame.hero1;
images = new BufferedImage[] {ShootGame.hero1,ShootGame.hero2};
width = image.getWidth();
height = image.getHeight();
x = 150;
y = 400;
}
@Override
public void step() {
// TODO Auto-generated method stub
if(images.length>0) {
image = images[index++/10%images.length];
}
}
public Bullet[] shoot() {
int xStep = width/4;
int yStep = 20;
if(doubleFire>0) {
Bullet[] bullets = new Bullet[2];
bullets[0] = new Bullet(x+xStep,y-yStep);
bullets[1] = new Bullet(x+3*xStep,y-yStep);
doubleFire-=2;
return bullets;
}else {
Bullet[] bullets = new Bullet[1];
bullets[0] = new Bullet(x+2*xStep,y-yStep);
return bullets;
}
}
public void moveTo(int x,int y) {
this.x = x-width/2;
this.y = y-height/2;
}
public void addDoubleFire() {
doubleFire+=40;
}
public void addLife() {
life++;
}
public int getLife() {
return life;
}
@Override
public boolean outOfBounds() {
// TODO Auto-generated method stub
return false;
}
public void subtractLife() {
life--;
}
public void setDoubleFire(int doubleFire) {
this.doubleFire = doubleFire;
}
public boolean hit(FlyingObject other) {
int x1 = other.x-this.width/2;
int x2 = other.x+other.width+this.width/2;
int y1 = other.y-this.height/2;
int y2 = other.y+other.height+this.height/2;
return this.x+this.width/2>x1&&this.x+this.width/2<x2&&this.y+this.height/2>y1&&this.y+this.width/2<y2;
}
}
Airplane
package planeWar;
import planeWar.ShootGame;
public class Airplane extends FlyingObject implements Enemy {
private int speed = 2;
@Override
public int getScore() {
// TODO Auto-generated method stub
return 5;
}
public Airplane() {
this.image = ShootGame.airplane;
width = image.getWidth();
height = image.getHeight();
y = -height;
x = (int)(Math.random()*(ShootGame.WIDTH-width));
//x=100;
//y=100;
}
@Override
public void step() {
// TODO Auto-generated method stub
y+=speed;
}
@Override
public boolean outOfBounds() {
// TODO Auto-generated method stub
return y>ShootGame.HEIGHT;
}
}
Enemy
package planeWar;
public interface Enemy {
int getScore();
}
Bee
package planeWar;
import planeWar.ShootGame;
import java.util.Random;
public class Bee extends FlyingObject implements Award {
private int xSpeed = 1;
private int ySpeed = 1;
private int awardType;
@Override
public int getType() {
// TODO Auto-generated method stub
return awardType;
}
public Bee() {
this.image = ShootGame.bee;
width = image.getWidth();
height = image.getHeight();
y = -height;
Random rand = new Random();
x = rand.nextInt(ShootGame.WIDTH-width);
//x=100;
//y=200;
awardType = rand.nextInt(2);
}
@Override
public void step() {
// TODO Auto-generated method stub
x+=xSpeed;
y+=ySpeed;
if(x>ShootGame.WIDTH-width) {
xSpeed=-1;
}
if(x>0) {
xSpeed=1;
}
}
@Override
public boolean outOfBounds() {
// TODO Auto-generated method stub
return y>ShootGame.HEIGHT;
}
}
Award
package planeWar;
public interface Award {
int DOUBLE_FIRE = 0;
int LIFE = 1;
int getType();
}
Bullet
package planeWar;
public class Bullet extends FlyingObject {
private int speed = 3;
public Bullet(int x,int y) {
this.x = x;
this.y = y;
this.image = ShootGame.bullet;
}
@Override
public void step() {
// TODO Auto-generated method stub
y-=speed;
}
public boolean outOfBounds() {
// TODO Auto-generated method stub
return y<-height;
}
}
FlyingObject
package planeWar;
import java.awt.image.BufferedImage;
public abstract class FlyingObject {
protected int x;
protected int y;
protected int width;
protected int height;
protected BufferedImage image;
public int getX() {
return x;
}
public void setX(int x) {
this.x = x;
}
public int getY() {
return y;
}
public void setY(int y) {
this.y = y;
}
public int getwidth() {
return width;
}
public void setWidth(int width) {
this.width = width;
}
public int getHeight() {
return height;
}
public BufferedImage getImage() {
return image;
}
public void setImage(BufferedImage image) {
this.image = image;
}
/**
* 飞行物移动一步
*/
public abstract void step();
public boolean shootBy(Bullet bullet) {
int x = bullet.x;
int y = bullet.y;
return this.x<x&&x<this.x+width&&this.y<y&&y<this.y+height;
}
public abstract boolean outOfBounds();
}
ShootGame
package planeWar;
import java.awt.Color;
import java.awt.Font;
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.imageio.ImageIO;
import javax.swing.JFrame;
import javax.swing.JPanel;
public class ShootGame extends JPanel{
/**
*
*/
private static final long serialVersionUID = 1L;
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;
public static final int WIDTH = 400;
public static final int HEIGHT = 654;
public static BufferedImage background;
public static BufferedImage start;
public static BufferedImage airplane;
public static BufferedImage bee;
public static BufferedImage bullet;
public static BufferedImage hero1;
public static BufferedImage hero2;
public static BufferedImage pause;
public static BufferedImage gameover;
private FlyingObject[] flyings = {};
private Bullet[] bullets = {};
private Hero hero = new Hero();
private Timer timer;
private int intervel = 1000/100;
private int score = 0;
private int state;
public ShootGame() {
//flyings = new FlyingObject[2];
//flyings[0] = new Airplane();
//flyings[1] = new Bee();
//bullets = new Bullet[1];
//bullets[0] = new Bullet(200,350);
}
static {
try {
background = ImageIO.read(ShootGame.class.getResource("background.png"));
airplane = ImageIO.read(ShootGame.class.getResource("airplane.png"));
bee = ImageIO.read(ShootGame.class.getResource("bee.png"));
bullet = ImageIO.read(ShootGame.class.getResource("bullet.png"));
hero1 = ImageIO.read(ShootGame.class.getResource("hero1.png"));
hero2 = ImageIO.read(ShootGame.class.getResource("hero2.png"));
pause = ImageIO.read(ShootGame.class.getResource("pause.png"));
gameover = ImageIO.read(ShootGame.class.getResource("gameover.png"));
start = ImageIO.read(ShootGame.class.getResource("start.png"));
}catch(Exception e) {
e.printStackTrace();
}
}
public void paint(Graphics g) {
g.drawImage(background, 0, 0, null);
paintHero(g);
paintBullets(g);
paintFlyingObjects(g);
paintScore(g);
paintState(g);
}
public void paintHero(Graphics g) {
for(int i = 0;i<bullets.length;i++)
{
g.drawImage(hero.getImage(), hero.getX(), hero.getY(), null);
}
}
public void paintBullets(Graphics g) {
for(int i = 0;i<bullets.length;i++)
{
Bullet b = bullets[i];
g.drawImage(b.getImage(), b.getX(), b.getY(), null);
}
}
public void paintFlyingObjects(Graphics g) {
for(int i = 0;i<flyings.length;i++)
{
FlyingObject f = flyings[i];
g.drawImage(f.getImage(), f.getX(), f.getY(), null);
}
}
public static FlyingObject nextOne() {
Random random = new Random();
int type = random.nextInt(20);
if(type == 0) {
return new Bee();
}else {
return new Airplane();
}
}
int flyEnteredIndex = 0;
public void enterAction() {
flyEnteredIndex++;
if(flyEnteredIndex%40==0) {
FlyingObject obj = nextOne();
flyings = Arrays.copyOf(flyings, flyings.length+1);
flyings[flyings.length-1] = obj;
}
}
public void stepAction() {
for(int i = 0;i<flyings.length;i++) {
FlyingObject f = flyings[i];
f.step();
}
for(int i = 0;i<bullets.length;i++) {
Bullet b = bullets[i];
b.step();
}
hero.step();
}
public void action() {
MouseAdapter l = new MouseAdapter() {
public void mouseMoved(MouseEvent e) {
if(state==RUNNING) {
int x = e.getX();
int y = e.getY();
hero.moveTo(x, y);
}
}
public void mouseEntered(MouseEvent e) {
if(state == PAUSE) {
state = RUNNING;
}
}
public void mouseExited(MouseEvent e) {
if(state != GAME_OVER) {
state = PAUSE;
}
}
public void mouseClicked(MouseEvent e) {
switch(state) {
case START:
state = RUNNING;
break;
case GAME_OVER:
flyings = new FlyingObject[0];
bullets = new Bullet[0];
hero = new Hero();
score = 0;
state = START;
break;
}
}
};
this.addMouseListener(l);
this.addMouseMotionListener(l);
timer = new Timer();
timer.schedule(new TimerTask() {
public void run() {
if(state == RUNNING) {
enterAction();
stepAction();
shootAction();
bangAction();
outOfBoundsAction();
checkGameOverAction();
}
repaint();
}
},intervel,intervel);
}
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 bangAction() {
for(int i=0;i<bullets.length;i++) {
Bullet b = bullets[i];
bang(b);
}
}
public void bang(Bullet bullet) {
int index = -1;
for(int i=0;i<flyings.length;i++) {
FlyingObject obj = flyings[i];
if(obj.shootBy(bullet)) {
index = i;
break;
}
}
if(index != -1) {
FlyingObject one = flyings[index];
FlyingObject temp = flyings[index];
flyings[index] = flyings[flyings.length-1];
flyings[flyings.length-1] = temp;
flyings = Arrays.copyOf(flyings,flyings.length-1);
if(one instanceof Enemy) {
Enemy e = (Enemy)one;
score+=e.getScore();
}
if(one instanceof Award) {
Award a = (Award)one;
int type = a.getType();
switch(type) {
case Award.DOUBLE_FIRE:
hero.addDoubleFire();
break;
case Award.LIFE:
hero.addLife();
break;
}
}
}
}
public void paintScore(Graphics g) {
int x = 10;
int y = 25;
Font font = new Font(Font.SANS_SERIF,Font.BOLD,14);
g.setColor(new Color(0x3A3B3B));
g.setFont(font);
g.drawString("SCORE:"+score, x, y);
y+=20;
g.drawString("LIFE:"+hero.getLife(), x, y);
}
public void outOfBoundsAction() {
int index = 0;
FlyingObject[] flyingLives = new FlyingObject[flyings.length];
for(int i = 0;i<flyings.length;i++) {
FlyingObject f = flyings[i];
if(!f.outOfBounds()) {
flyingLives[index++] = f;
}
}
flyings = Arrays.copyOf(flyingLives, index);
index = 0;
/*Bullet[] bulletLives = new Bullet[bullets.length];
for(int i = 0;i<bullets.length;i++) {
Bullet b = bullets[i];
if(!b.outOfBounds()) {
bulletLives[index++] = b;
}
bullets = Arrays.copyOf(bulletLives, index);
}*/
}
public boolean isGameOver() {
for(int i=0;i<flyings.length;i++) {
int index = -1;
FlyingObject obj = flyings[i];
if(hero.hit(obj)) {
hero.subtractLife();
hero.setDoubleFire(0);
index = i;
}
if(index!=-1) {
FlyingObject t = flyings[index];
flyings[index] = flyings[flyings.length-1];
flyings[flyings.length-1] = t;
flyings = Arrays.copyOf(flyings, flyings.length-1);
}
}
return hero.getLife()<=0;
}
public void checkGameOverAction() {
if(isGameOver()) {
state = GAME_OVER;
}
}
public void paintState(Graphics g) {
switch(state) {
case START:
g.drawImage(start, 168, 275, null);
break;
case PAUSE:
g.drawImage(pause, 168, 275, null);
break;
case GAME_OVER:
g.drawImage(gameover, 40, 265, null);
break;
}
}
public static void main(String[] args) {
JFrame frame = new JFrame("Fly");
ShootGame game = new ShootGame();
frame.add(game);
frame.setSize(WIDTH,HEIGHT);
frame.setAlwaysOnTop(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLocationRelativeTo(null);
frame.setVisible(true);
game.action();
}
}
效果图: