一.游戏登陆界面
package TankFight; import javax.swing.*; import java.awt.*; public class GameUI { public void initUI() { JFrame jf = new JFrame(); jf.setSize(1100, 900);//设置窗口大小 jf.setTitle("坦克大战" );//设置窗口标题 jf.setLocationRelativeTo(null);//设置窗口居中 jf.setDefaultCloseOperation(3);//设置用户在此窗体上点击关闭按钮时默认执行的操作 //游戏面板 JPanel gamePanel = new JPanel(); gamePanel.setBackground(Color.black); jf.add(gamePanel,BorderLayout.CENTER); jf.setVisible(true); Graphics g = gamePanel.getGraphics();//画笔 //监听器 Threadlistener mouse = new Threadlistener(g,gamePanel); jf.addKeyListener(mouse); //让窗体获取焦点 jf.requestFocus(); } public static void main(String[] args) { GameUI ui = new GameUI(); ui.initUI(); } }
二.移动物体类(后面坦克类和子弹类的父类)
package TankFight; public class MoveObject { private int x, y, size = 100;//坐标,尺寸 private int speedX = 0, speedY = 0;//水平竖直方向速度 private int direction; //控制方向 public MoveObject(){ } public MoveObject(int x,int y){ this.x = x; this.y = y; } //移动方法 public void move(){ y += speedY; x += speedX; } //获取坐标方法 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 getSize() { return size; } public void setSize(int size) { this.size = size; } public int getSpeedX() { return speedX; } public void setSpeedX(int speedX) { this.speedX = speedX; } public int getSpeedY() { return speedY; } public void setSpeedY(int speedY) { this.speedY = speedY; } public int getDirection() { return direction; } public void setDirection(int direction) { this.direction = direction; } }
三.坦克类
在此之前我们首先搜素坦克上下左右四个方向的图片各一张,放入picture包下,分别命名tank1,tank2,tank3,tank4。
package TankFight; import javax.swing.*; import java.awt.*; public class MyTank extends MoveObject{ public JPanel gamePanel; public ImageIcon[] tankImage = new ImageIcon[4]; //地图1 砖块 2 石头 3 草地 4 水 public int[][] Barriersmap = {{ 1, 1, 1, 1, 0, 1, 1, 1, 1}, { 2, 2, 1, 1, 0, 1, 1, 2, 2}, { 0, 0, 0, 0, 0, 0, 0, 0, 0}, { 3, 3, 3, 3, 0, 3, 3, 3, 3}, { 1, 1, 1, 1, 0, 1, 1, 1, 1}, { 3, 3, 0, 0, 0, 0, 0, 3, 3}, { 1, 1, 0, 1, 1, 1, 0, 1, 1}, { 1, 1, 0, 1, 4, 1, 0, 1, 1}, { 1, 1, 0, 1, 1, 1, 0, 1, 1}}; public MyTank(int x, int y, JPanel gamePanel){ super(x,y); this.gamePanel = gamePanel; this.setSize(60); //加载图片 for(int i=0;i<4;i++){ tankImage[i] = new ImageIcon("picture//tank"+i+".jpg"); } //设置默认方法 } //画我方坦克 public void drawTank(Graphics g){ ImageIcon image = isDirection(); g.drawImage(image.getImage(),getX(),getY(),getSize(),getSize(),null); } //根据当前方法,选择合适的图片 public ImageIcon isDirection(){ if(getSpeedX() > 0 ){//向右移动 setDirection(3); } else if(getSpeedX() < 0 ){//向左移动 setDirection(2); }else if(getSpeedY() < 0 ){//向下移动 setDirection(0); }else if(getSpeedY() > 0 ){//向上移动 setDirection(1); } ImageIcon image = tankImage[getDirection()]; return image; } //移动方法 public void move(){ int xl=(getX())/100,yl=(getY())/100; int size=getSize(); int xdl=(getX())/100,ydl=(getY()+size)/100; int xr=(getX()+size)/100,yr=(getY())/100; int xdr=(getX()+size)/100,ydr=(getY()+size)/100; System.out.println(xl+" "+yl+" "+Barriersmap[yl][xl]); switch(getDirection())//判断方向,加载不同方向对应的坦克图片,设置速度 { case 0: if(Barriersmap[yl][xl]==1||Barriersmap[yr][xr]==1||Barriersmap[yl][xl]==2||Barriersmap[yr][xr]==2) { setSpeedY(0); } break; case 1: if(Barriersmap[ydl][xdl]==1||Barriersmap[ydr][xdr]==1||Barriersmap[ydl][xdl]==2||Barriersmap[ydr][xdr]==2) { setSpeedY(0); } break; case 2: if(Barriersmap[yl][xl]==1||Barriersmap[ydl][xdl]==1||Barriersmap[yl][xl]==2||Barriersmap[ydl][xdl]==2) { setSpeedX(0); } break; case 3: if(Barriersmap[yr][xr]==1||Barriersmap[ydr][xdr]==1||Barriersmap[yr][xr]==2||Barriersmap[ydr][xdr]==2) { setSpeedX(0); } break; } super.move();//移动 } }
四.子弹类
package TankFight; import java.awt.*; public class Bullet extends MoveObject { public int direc;//方向 public MyTank mt;//坦克 public boolean stop=false;//停止 public Bullet(int x, int y, MyTank mt) { super(x, y); this.direc = mt.getDirection(); this.mt = mt; setSize(10);//尺寸 setSpeedY(-3);//速度 } public void drawbullet(Graphics g) { g.setColor(Color.red); g.fillOval(getX(), getY(), getSize(), getSize()); } //按方向重写move @Override public void move() { if(!stop) { switch (direc) { case 0: setSpeedY(-4); setSpeedX(0); break; case 1: setSpeedY(4); setSpeedX(0); break; case 2: setSpeedY(0); setSpeedX(-4); break; case 3: setSpeedY(0); setSpeedX(4); break; } super.move(); } } }
五.音乐类
从外网下载音乐包导入(自行),并下载你想要的坦克大战背景音乐加入music包下命名为bg1.mp3
package TankFight; import javazoom.jl.player.Player; import java.io.File; import java.io.FileInputStream; public class Music { //播放音乐类 static Player player; public static void playMusic(){ //匿名内部类 new Thread( new Runnable() { @Override public void run() { String path = "music/bg1.mp3"; FileInputStream fis = null; try { //输入文件流 fis = new FileInputStream(new File(path)); player = new Player(fis); player.play(); } catch (Exception e) { throw new RuntimeException(e); } } } ).start(); } public static void close(){ player.close(); } }
六.线程启动页面类
package TankFight;
import javax.swing.*;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.util.ArrayList;
//线程启动页面
public class ThreadGame implements Runnable {
public Graphics g;//画笔
public boolean start = false;//启动
public MyTank mt;//坦克
public int mapsize =100;//地图尺寸
public int changeablemapsize=100;
public JPanel gamePanel;
public BufferedImage bufferedImage;
public ArrayList<MoveObject> listTank;//保存其他坦克
public ArrayList<Bullet> listBullet; //保存子弹
//地图素材
public Image[] mapArr = new Image[4];
public Image boom=new ImageIcon("picture/boom.jpg").getImage();
public int score=0;
public int[][] Barriersmap;
public int[][] countmap=new int[9][9];
//初始化属性
public ThreadGame(Graphics g,MyTank mt, ArrayList<Bullet> listBullet,JPanel gamePanel) {
this.g = g;
this.mt = mt;
this.gamePanel=gamePanel;
this.listBullet = listBullet;
this.Barriersmap=mt.Barriersmap;
//初始化图片素材
for (int i = 1; i <= 4; i++) {
mapArr[i-1] = new ImageIcon("picture//map" + i + ".png").getImage();
}
}
public void isStart(boolean start) {
this.start = start;
}
public void Drawmap(Graphics g){
//画出障碍物
for(int i = 0; i< Barriersmap.length; i++)
{
for(int j = 0; j< Barriersmap[0].length; j++)
{
if (Barriersmap[i][j] == 1) {
g.drawImage(mapArr[1], j * mapsize, i * mapsize, mapsize, mapsize, null);
} else if (Barriersmap[i][j] == 2) {
g.drawImage(mapArr[0], j * mapsize, i * mapsize, mapsize, mapsize, null);
} else if (Barriersmap[i][j] == 3) {
g.drawImage(mapArr[2], j * mapsize, i * changeablemapsize,changeablemapsize, changeablemapsize, null);
} else if (Barriersmap[i][j] == 4) {
g.drawImage(mapArr[3], j * mapsize, i * mapsize, mapsize, mapsize, null);
}
}
}
}
//启动线程后自动执行的方法
//run 执行完,该线程的内存被回收,不能再启动
public void run() {
System.out.println(Thread.currentThread().getName() + ":启动...");
//创建缓冲区
//作为容器,从中获取画笔绘画
bufferedImage = new BufferedImage(gamePanel.getWidth(),
gamePanel.getHeight(),BufferedImage.TYPE_INT_RGB);
Graphics bufferg =bufferedImage.getGraphics();
while (true) {
try {
Thread.sleep(10);
} catch (InterruptedException ex) {
throw new RuntimeException(ex);
}
if (!start) {
//绘制开始按钮
drawStr(bufferg,"按空格键开始游戏");
continue;
}
bufferg.setColor(Color.black);
bufferg.fillRect(0,0,gamePanel.getWidth(),gamePanel.getHeight());
Drawmap(bufferg);
//画控制方坦克
mt.drawTank(bufferg);
mt.move();
//分数区
drawScore(bufferg,"SCORE:"+score);
//子弹
for(int i=0;i<listBullet.size();i++){
Bullet bullet=listBullet.get(i);
bullet.drawbullet(bufferg);
bullet.move();
}
attack(bufferg);
//将缓冲区内绘画显示出来
g.drawImage(bufferedImage,0,0,null);
}
}
public void attack(Graphics bufferg){
//子弹攻击功能
for(int i=0;i<listBullet.size();i++){
Bullet bullet=listBullet.get(i);
bullet.drawbullet(bufferg);
bullet.move();
int x=bullet.getX()/100,y=bullet.getY()/100;
if(x>=0&&x<9&&y>=0&&y<9)
{
if((Barriersmap[y][x]==1||Barriersmap[y][x]==2)&&!bullet.stop)
{
bufferg.setColor(Color.black);
countmap[y][x]++;
System.out.println(countmap[y][x]);
bullet.setSize(0);
bullet.stop=true;
if(countmap[y][x]==10)
{
Barriersmap[y][x]=0;
score++;
}
}
}
}
g.drawImage(bufferedImage,0,0,null);
}
public void drawStr(Graphics bufferg,String s){//写文字
bufferg.setColor(Color.RED);
bufferg.setFont(new Font("楷体",0,50));
bufferg.drawString(s,400,400);
g.drawImage(bufferedImage,0,0,null);
}
public void drawScore(Graphics bufferg,String s){//写分数
bufferg.setColor(Color.RED);
bufferg.setFont(new Font("楷体",0,30));
bufferg.drawString(s,935,50);
g.drawImage(bufferedImage,0,0,null);
}
}
七.监听器类
主要是键盘监听器:1.↑↓←→键控制方向 2.j键发射子弹 3.空格键启动音乐
package TankFight;
import javax.swing.*;
import java.awt.*;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.ArrayList;
public class Threadlistener implements KeyListener {
public Graphics g;
public ThreadGame tg;
public int bu_small =25;
public int bu_big =55;
public JPanel gamePanel;
public MyTank mt;
public ArrayList<Bullet> listBullet = new ArrayList<>();
public Threadlistener(Graphics g,JPanel gamePanel){
this.g=g;
this.gamePanel=gamePanel;
//初始化的时候就创建线程
if (tg == null) {
//创建我方坦克
mt = new MyTank(210,700,gamePanel);
//限制线程只启动一次
//2.实现Runnable接口启动方式
tg = new ThreadGame(g,mt,listBullet,gamePanel);
new Thread(tg).start();
}
}
public void keyTyped(KeyEvent e){}
public void keyPressed(KeyEvent e){
int key = e.getKeyCode();
switch(key){
case KeyEvent.VK_UP:
if(mt.getSpeedX()==0)
mt.setSpeedY(-3);
break;
case KeyEvent.VK_LEFT:
if(mt.getSpeedY()==0)
mt.setSpeedX(-3);
break;
case KeyEvent.VK_RIGHT:
if(mt.getSpeedY()==0)
mt.setSpeedX(3);
break;
case KeyEvent.VK_DOWN:
if(mt.getSpeedX()==0)
mt.setSpeedY(3);
break;
case KeyEvent.VK_SPACE:
tg.start=true;
Music.playMusic();
break;
case KeyEvent.VK_J:
switch (mt.getDirection())
{
case 0:
Bullet bullet = new Bullet(mt.getX()+ bu_small, mt.getY(),mt);
listBullet.add(bullet);
break;
case 1:
bullet = new Bullet(mt.getX()+ bu_small, mt.getY()+ bu_big,mt);
listBullet.add(bullet);
break;
case 2:
bullet = new Bullet(mt.getX(), mt.getY()+ bu_small,mt);
listBullet.add(bullet);
break;
case 3:
bullet = new Bullet(mt.getX()+ bu_big, mt.getY()+ bu_small,mt);
listBullet.add(bullet);
break;
}
break;
}
}
public void keyReleased(KeyEvent e) {
int key = e.getKeyCode();
switch (key) {
case KeyEvent.VK_UP:
mt.setSpeedY(0);
break;
case KeyEvent.VK_LEFT:
mt.setSpeedX(0);
break;
case KeyEvent.VK_RIGHT:
mt.setSpeedX(0);
break;
case KeyEvent.VK_DOWN:
mt.setSpeedY(0);
break;
}
}
}
八.任务线程
package TankFight; import java.util.ArrayList; //任务线程 public class TimeThread extends Thread{ public long time =20; public ArrayList<MoveObject> listTank; public TimeThread(ArrayList<MoveObject> listTank){ this.listTank=listTank; } public void run(){ while(true){ try { Thread.sleep(time); } catch (InterruptedException e) { throw new RuntimeException(e); } MoveObject tank=new MoveObject(); listTank.add(tank); } } }