日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

java实现坦克大战

發布時間:2023/12/31 编程问答 23 豆豆
生活随笔 收集整理的這篇文章主要介紹了 java实现坦克大战 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

代碼總體上來說借鑒了尚學堂“手把手教你一小時寫出坦克大戰”(感謝),也從中加入了一些自己的想法(相對來說較少),子彈碰撞后消失,添加音效,隨機生成地形等;話不多說,直接上思維導圖(比較粗略)

目錄

?編輯

窗口初始化

準備工作

窗口初始化

游戲父類的編寫

方向類

?游戲父類

添加坦克類

Tank

四個方向的移動——玩家(鍵盤監聽)、人機(隨機移動)

射擊——玩家(鍵盤監聽)、人機(隨機移動)

總?

?Player

?鍵盤監聽器

?總

?人機

初始化子彈類

玩家子彈

?子彈射擊?

碰撞檢測

?總

?人機子彈

?擊中玩家

?總

添加圍墻、基地

Base

Wall

Grass

Fe

優化

爆炸

音樂

重寫GamePanel

?游戲最終成品


窗口初始化

準備工作

首先創建一個TankWar項目,在scr相同路徑下創建images、music文件夾,將需要使用的圖片、音樂分別放在images、music中。創建一個com.tankwar(包),注意命名規范

窗口初始化

在com.tankwar中創建GamePanel類

import javax.swing.JFrame; public class GamePanel extends JFrame{//窗口大小private int width=1260;private int height=800;//窗口初始化public void launch() {//標題setTitle("坦克大戰");//初始化窗口大小setSize(width,height);//使屏幕居中setLocationRelativeTo(null);//添加關閉事件setDefaultCloseOperation(3);//用戶不能調整setResizable(false);//使窗口可見setVisible(true);}public static void main(String[]args) {GamePanel gamePanel=new GamePanel();gamePanel.launch();} }

?運行結果

?導入窗口圖片與屏幕刷新

程序在運行時屏幕的每,對象的位置以及圖像的每一次改變都需要屏幕的一次刷新,而屏幕的每一次刷新都需要重新繪制屏幕,所以會出現閃屏現象。如果想要解決這種問題,需要運用雙緩存技術

(2條消息) Java雙緩沖技術_kkvveeerer的博客-CSDN博客_java雙緩沖

import java.awt.Graphics; import java.awt.Image; import java.awt.Toolkit;import javax.swing.JFrame; public class GamePanel extends JFrame{//窗口大小private int width=1260;private int height=800;//定義雙緩存圖片Image offScreenImage=null;//臨時變量private int a=1;//游戲狀態 0 未開始,1 開始,2 暫停,3 失敗,4 勝利private int state=0;//游戲是否開始private boolean start=false;//窗口初始化public void launch() {//標題setTitle("坦克大戰");//初始化窗口大小setSize(width,height);//使屏幕居中setLocationRelativeTo(null);//添加關閉事件setDefaultCloseOperation(3);//用戶不能調整setResizable(false);//使窗口可見setVisible(true);/** 控制屏幕刷新時間*/while(true) {repaint();try {Thread.sleep(25);//刷新休眠時間} catch (Exception e) {e.printStackTrace();// TODO: handle exception}}}public void paint(Graphics g) {//創建和容器一樣大小的imageif(offScreenImage==null) {offScreenImage=this.createImage(width,height);}//獲得該圖片的畫布Graphics gImage=offScreenImage.getGraphics();//填充整個畫布gImage.fillRect(0,0,width,height);if(state==0) {//游戲未開始gImage.drawImage(Toolkit.getDefaultToolkit().getImage("images/interface.png"),0,0,this);}else if(state==1) {//游戲開始}else if(state==2) {//游戲暫停}else if(state==3) {//游戲失敗}else if(state==4) {//游戲勝利}g.drawImage(offScreenImage,0,0,null);}public static void main(String[]args) {GamePanel gamePanel=new GamePanel();gamePanel.launch();} }

?程序運行結果

?添加鼠標監聽器

在游戲中點擊“PLAYER”方可進入游戲,需要加入鼠標監聽器

import java.awt.Graphics; import java.awt.Image; import java.awt.Point; import java.awt.Toolkit; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent;import javax.swing.JFrame; public class GamePanel extends JFrame{//窗口大小private int width=1260;private int height=800;//定義雙緩存圖片Image offScreenImage=null;//臨時變量private int a=1;//游戲狀態 0 未開始,1 開始,2 暫停,3 失敗,4 勝利private int state=0;//游戲是否開始private boolean start=false;//窗口初始化public void launch() {//標題setTitle("坦克大戰");//初始化窗口大小setSize(width,height);//使屏幕居中setLocationRelativeTo(null);//添加關閉事件setDefaultCloseOperation(3);//用戶不能調整setResizable(false);//使窗口可見setVisible(true);/** 控制屏幕刷新時間*/while(true) {repaint();try {Thread.sleep(25);} catch (Exception e) {e.printStackTrace();// TODO: handle exception}}}public void paint(Graphics g) {//創建和容器一樣大小的imageif(offScreenImage==null) {offScreenImage=this.createImage(width,height);}//獲得該圖片的畫布Graphics gImage=offScreenImage.getGraphics();//填充整個畫布gImage.fillRect(0,0,width,height);if(state==0) {//游戲未開始gImage.drawImage(Toolkit.getDefaultToolkit().getImage("images/interface.png"),0,0,this);//添加鼠標事件this.addMouseListener(new GamePanel.MouseMonitor());}else if(state==1) {//游戲開始}else if(state==2) {//游戲暫停}else if(state==3) {//游戲失敗}else if(state==4) {//游戲勝利}g.drawImage(offScreenImage,0,0,null);}/** 添加鼠標監聽*/private class MouseMonitor extends MouseAdapter{@Overridepublic void mouseClicked(MouseEvent e) {Point p=new Point(e.getX(),e.getY());if(!start&&state==0) {if(p.x>450&&p.x<750&&p.y>400&&p.y<480) {//“PLAYER X,Y坐標范圍”state=1;start=true;}}else if(state==3||state==4) {}}}public static void main(String[]args) {GamePanel gamePanel=new GamePanel();gamePanel.launch();} }

游戲父類的編寫

方向類

游戲中坦克需要運用到“方向”,可以單獨創建一個枚舉類,或者在坦克類中定義“方向”成員變量。

/** 首先枚舉是一個特殊的class* 這個class相當于final static 修飾,不能被繼承* 他的構造方法強制被私有化* 所有的枚舉都繼承自java.lang.Enum類。由于java不支持多繼承,所以枚舉對象不能再繼承其他類*/ public enum Direction {//每個成員變量都是final static 修飾UP,LEFT,RIGHT,DOWN }

?游戲父類

游戲中的坦克、子彈、基地、墻體、爆炸圖片等元素,在繪畫到面板上的過程中,需要運用到坐標,大小、移動速度、主界面畫板。將其抽取出來,創建游戲父類

import java.awt.Graphics; import java.awt.Image; import java.awt.Rectangle; import java.awt.Toolkit;public abstract class GameObject {//游戲元素圖片Image img;//游戲元素的橫縱坐標int x;int y;//游戲元素的寬,高int width;int height;//游戲元素的移動速度int speed;//游戲元素的移動方向Direction direction;//引入主界面GamePanel gamePanel;public GameObject() {}public GameObject(String img,int x,int y,GamePanel gamePanel) {this.img=Toolkit.getDefaultToolkit().getImage(img);this.x=x;this.y=y;this.gamePanel=gamePanel;}public Image getImag() {return img;}public void setImg(String img) {this.img=Toolkit.getDefaultToolkit().getImage(img);}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 void setHeight(int height) {this.height = height;}public double getSpeed() {return speed;}public void setSpeed(int speed) {this.speed = speed;}public Direction getDirection() {return direction;}public void setDirection(Direction direction) {this.direction = direction;}public GamePanel getGamePanel() {return gamePanel;}public void setGamePanel(GamePanel gamepanel) {this.gamePanel = gamePanel;}//繼承元素繪制自己的方法public abstract void paintSelf(Graphics g);//獲取當前游戲元素的矩形,是為碰撞檢測而寫public abstract Rectangle getRec(); }

添加坦克類

Tank

注:藍色字體的寫在子類中

坦克具有哪些特有屬性?

四個方向移動的圖片

//向上移動時的圖片private String upImage;//向下移動時的圖片private String downImage;//向右移動時的圖片private String rightImage;//向左移動時的圖片private String leftImage;

四個方向的移動——玩家(鍵盤監聽)、人機(隨機移動

1、墻體碰撞檢測

2、邊界碰撞檢測

3、人機碰撞檢測

4、移動


1、墻體碰撞檢測

/** 坦克與墻碰撞檢測*/public boolean hitWall(int x,int y) {//假設玩家坦克前進,下一個位置形成的矩形Rectangle next=new Rectangle(x,y,width,height);//地圖里所有的墻體List<Wall>walls=this.gamePanel.wallList;List<Fe>fes=this.gamePanel.feList;//判斷兩個矩形是否相交for(Wall w:walls) {if(w.getRec().intersects(next)) {return true;}}for(Fe f:fes) {if(f.getRec().intersects(next)) {return true;}}return false;}

2、邊界碰撞檢測

/** 邊界與坦克碰撞檢測*/public boolean moveToBorder(int x,int y) {if(x<10) {return true;}else if(x>this.gamePanel.getWidth()-width) {return true;}if(y<30) {return true;}else if(y>this.gamePanel.getHeight()-height) {return true;}return false;}

?3、人機碰撞檢測

/** 人機碰撞檢測*/public boolean hitTank(int x,int y) {int a=0;//假設人機坦克前進,下一個位置形成的矩形Rectangle next=new Rectangle(x,y,width,height);//地圖里所有的人機List<Bot>bots=this.gamePanel.botList;//判斷兩個矩形是否相交for(Bot b:bots) {if(b.getRec().intersects(next)) {a++;if(a==2) {return true;}}}return false;}

?4、移動

/** 坦克移動*/public void leftWard() {direction=Direction.LEFT;setImg(leftImage);if(!hitWall(x-speed,y)&&!moveToBorder(x-speed,y)&&alive&&!hitTank(x-speed,y)) {this.x-=speed;}}public void rightWard() {direction=Direction.RIGHT;setImg(rightImage);if(!hitWall(x+speed,y)&&!moveToBorder(x+speed,y)&&alive&&!hitTank(x+speed,y)) {this.x+=speed;}}public void upWard() {direction=Direction.UP;setImg(upImage);if(!hitWall(x,y-speed)&&!moveToBorder(x,y-speed)&&alive&&!hitTank(x,y-speed)) {this.y-=speed;}}public void downWard() {direction=Direction.DOWN;setImg(downImage);if(!hitWall(x,y+speed)&&!moveToBorder(x,y+speed)&&alive&&!hitTank(x-speed,y+speed)) {this.y+=speed;}}

射擊——玩家(鍵盤監聽)、人機(隨機移動)

1、子彈射擊方向應與坦克移動方向一致

2、射擊子彈CD

3、射擊


?1、子彈射擊方向應與坦克移動方向一致

坦克坐標點為坦克圖片左上角,所以子彈初始坐標應該為坦克的坐標加上坦克高度或寬度的一半。

/** 根據方向確定頭部位置,x和y是左上角的點*/public Point getHeadPoint() {switch(direction) {case UP:return new Point(x+width/2,y);case LEFT:return new Point(x,y+height/2);case DOWN:return new Point(x+width/2,y+height);case RIGHT:return new Point(x+width,y+height/2);default:return null;}}

?2、射擊子彈CD

/** 坦克射擊cd*/public class AttackCD extends Thread{public void run() {attackCoolDown=false;try {//休眠1秒Thread.sleep(attackCoolDownTime);//attackCoolDownTime為定義的成員變量單位為ms}catch (InterruptedException e) {e.printStackTrace();}//將攻擊功能解除冷卻狀態attackCoolDown=true;this.stop();//不是很理解}}

?3、射擊

/** 射擊*/public void attack() {Point p=getHeadPoint();if(attackCoolDown&&alive) {Bullet bullet=new Bullet("images/bullet/bulletGreen.gif",p.x-10,p.y-10, direction, this.gamePanel);this.gamePanel.bulletList.add(bullet);//將子彈添加至子彈集合attackCoolDown=false;new AttackCD().start();}}

總?

這里由于還未創建其他類所以會報錯,在后續會添加上的(博主偷個懶直接把源碼粘貼過來了)

import java.awt.Graphics; import java.awt.Point; import java.awt.Rectangle; import java.util.List;public class Tank extends GameObject{//向上移動時的圖片private String upImage;//向下移動時的圖片private String downImage;//向右移動時的圖片private String rightImage;//向左移動時的圖片private String leftImage;//坦克sizeint width=54;int height=54;//坦克初始方向Direction direction=Direction.UP;//坦克速度private int speed=3;//攻擊冷卻private boolean attackCoolDown=true;//攻擊冷卻事件毫秒間隔1000ms發射子彈private int attackCoolDownTime=100;//坦克是否活著public boolean alive=true;/** 坦克坐標,方向,圖片,方向,面板*/public Tank(String img,int x,int y,String upImage,String downImage,String leftImage,String rightImage,GamePanel gamePanel) {super(img,x,y,gamePanel);this.upImage=upImage;this.leftImage=leftImage;this.downImage=downImage;this.rightImage=rightImage; }/** 坦克移動*/public void leftWard() {direction=Direction.LEFT;setImg(leftImage);if(!hitWall(x-speed,y)&&!moveToBorder(x-speed,y)&&alive&&!hitTank(x-speed,y)) {this.x-=speed;}}public void rightWard() {direction=Direction.RIGHT;setImg(rightImage);if(!hitWall(x+speed,y)&&!moveToBorder(x+speed,y)&&alive&&!hitTank(x+speed,y)) {this.x+=speed;}}public void upWard() {direction=Direction.UP;setImg(upImage);if(!hitWall(x,y-speed)&&!moveToBorder(x,y-speed)&&alive&&!hitTank(x,y-speed)) {this.y-=speed;}}public void downWard() {direction=Direction.DOWN;setImg(downImage);if(!hitWall(x,y+speed)&&!moveToBorder(x,y+speed)&&alive&&!hitTank(x-speed,y+speed)) {this.y+=speed;}}/** 射擊*/public void attack() {Point p=getHeadPoint();if(attackCoolDown&&alive) {Bullet bullet=new Bullet("images/bullet/bulletGreen.gif",p.x-10,p.y-10, direction, this.gamePanel);this.gamePanel.bulletList.add(bullet);//將子彈添加至子彈集合attackCoolDown=false;new AttackCD().start();}}/** 坦克射擊cd*/public class AttackCD extends Thread{public void run() {attackCoolDown=false;try {//休眠1秒Thread.sleep(attackCoolDownTime);}catch (InterruptedException e) {e.printStackTrace();}//將攻擊功能解除冷卻狀態attackCoolDown=true;this.stop();//不是很理解}}/** 根據方向確定頭部位置,x和y是左上角的點*/public Point getHeadPoint() {switch(direction) {case UP:return new Point(x+width/2,y);case LEFT:return new Point(x,y+height/2);case DOWN:return new Point(x+width/2,y+height);case RIGHT:return new Point(x+width,y+height/2);default:return null;}}/** 坦克與墻碰撞檢測*/public boolean hitWall(int x,int y) {//假設玩家坦克前進,下一個位置形成的矩形Rectangle next=new Rectangle(x,y,width,height);//地圖里所有的墻體List<Wall>walls=this.gamePanel.wallList;List<Fe>fes=this.gamePanel.feList;//判斷兩個矩形是否相交for(Wall w:walls) {if(w.getRec().intersects(next)) {return true;}}for(Fe f:fes) {if(f.getRec().intersects(next)) {return true;}}return false;}/** 人機碰撞檢測*/public boolean hitTank(int x,int y) {int a=0;//假設人機坦克前進,下一個位置形成的矩形Rectangle next=new Rectangle(x,y,width,height);//地圖里所有的人機List<Bot>bots=this.gamePanel.botList;//判斷兩個矩形是否相交for(Bot b:bots) {if(b.getRec().intersects(next)) {a++;if(a==2) {return true;}}}return false;}/** 邊界與坦克碰撞檢測*/public boolean moveToBorder(int x,int y) {if(x<10) {return true;}else if(x>this.gamePanel.getWidth()-width) {return true;}if(y<30) {return true;}else if(y>this.gamePanel.getHeight()-height) {return true;}return false;}@Overridepublic Rectangle getRec(){return new Rectangle(x,y,width,height);}@Overridepublic void paintSelf(Graphics g) {g.drawImage(img, x, y, null);} }

?Player

玩家類繼承坦克類,在父類的基礎上只需要添加鍵盤監聽器即可


?鍵盤監聽器

/** 按下鍵盤時坦克持續運動*/public void keyPressed(KeyEvent e) {int key=e.getKeyCode();switch(key) {case KeyEvent.VK_A:left=true;Music.playBackground();break;case KeyEvent.VK_D:right=true;Music.playBackground();break;case KeyEvent.VK_W:up=true;Music.playBackground();break;case KeyEvent.VK_S:down=true;Music.playBackground();break;case KeyEvent.VK_SPACE:Music.attackPlay();this.attack();break;default:break;} }/** 松開鍵盤時,坦克停止運動*/public void keyReleased(KeyEvent e) {int key = e.getKeyCode();switch (key){case KeyEvent.VK_A:left = false;Music.moveStop();break;case KeyEvent.VK_S:down = false;Music.moveStop();break;case KeyEvent.VK_D:right = false;Music.moveStop();break;case KeyEvent.VK_W:up = false;Music.moveStop();break;default:break;} }

?總

import java.awt.Graphics; import java.awt.Rectangle; import java.awt.event.KeyEvent;public class PlayerOne extends Tank{private boolean up=false;private boolean down=false;private boolean left=false;private boolean right=false;public PlayerOne(String img, int x, int y, String upImage, String downImage, String leftImage, String rightImage,GamePanel gamePanel) {super(img, x, y, upImage, downImage, leftImage, rightImage, gamePanel);// TODO Auto-generated constructor stub}/** 按下鍵盤時坦克持續運動*/public void keyPressed(KeyEvent e) {int key=e.getKeyCode();switch(key) {case KeyEvent.VK_A:left=true;Music.playBackground();break;case KeyEvent.VK_D:right=true;Music.playBackground();break;case KeyEvent.VK_W:up=true;Music.playBackground();break;case KeyEvent.VK_S:down=true;Music.playBackground();break;case KeyEvent.VK_SPACE:Music.attackPlay();this.attack();break;default:break;} }/** 松開鍵盤時,坦克停止運動*/public void keyReleased(KeyEvent e) {int key = e.getKeyCode();switch (key){case KeyEvent.VK_A:left = false;Music.moveStop();break;case KeyEvent.VK_S:down = false;Music.moveStop();break;case KeyEvent.VK_D:right = false;Music.moveStop();break;case KeyEvent.VK_W:up = false;Music.moveStop();break;default:break;} }/** 坦克移動*/public void move() {if(left) {leftWard();}else if(right) {rightWard();}else if (up) {upWard();}else if (down) {downWard();}else {return;}}@Overridepublic void paintSelf(Graphics g) {g.drawImage(img,x,y,null);move();}public Rectangle getRec() {return new Rectangle(x,y,width,height);}}

?人機

人機具有哪些屬性呢?

隨機、隨機、隨機還是隨機!

1、隨機移動?

2、隨機射擊


1、隨機移動?

/** 人機移動*/public void go() {attack();if(moveTime>=20) {direction=randomDirection();moveTime=0;}else{moveTime+=1;}switch(direction) {case UP:upWard();break;case DOWN:downWard();break;case RIGHT:rightWard();break;case LEFT:leftWard();break;}}/** 人機移動隨機方向*/public Direction randomDirection() {Random r=new Random();int rnum=r.nextInt(4);switch(rnum) {case 0:return Direction.UP;case 1:return Direction.RIGHT;case 2:return Direction.LEFT;default:return Direction.DOWN;}}

2、隨機射擊

隨機射擊寫在人機子彈類里

import java.awt.Graphics; import java.awt.Point; import java.awt.Rectangle; import java.util.Random;public class Bot extends Tank{//人機朝一個方向運動時間int moveTime=0;public Bot(String img, int x, int y, String upImage, String downImage, String leftImage, String rightImage,GamePanel gamePanel) {super(img, x, y, upImage, downImage, leftImage, rightImage, gamePanel);} /** 人機移動*/public void go() {attack();if(moveTime>=20) {direction=randomDirection();moveTime=0;}else{moveTime+=1;}switch(direction) {case UP:upWard();break;case DOWN:downWard();break;case RIGHT:rightWard();break;case LEFT:leftWard();break;}}/** 人機移動隨機方向*/public Direction randomDirection() {Random r=new Random();int rnum=r.nextInt(4);switch(rnum) {case 0:return Direction.UP;case 1:return Direction.RIGHT;case 2:return Direction.LEFT;default:return Direction.DOWN;}}/** 隨機攻擊*/public void attack() {Point p=getHeadPoint();Random r=new Random();int rnum=r.nextInt(100);if(rnum<2) {EnemyBullet enemyBullet=new EnemyBullet("images/bullet/bulletYellow.gif",p.x,p.y,direction,gamePanel);this.gamePanel.enemyBulletsList.add(enemyBullet);}}/** 繪制人機*/@Overridepublic void paintSelf(Graphics g) {g.drawImage(img,x,y,null);go();}@Overridepublic Rectangle getRec() {return new Rectangle(x,y,width,height);}}

初始化子彈類

玩家子彈

  • 子彈射擊
  • 子彈碰撞檢測

  • ?子彈射擊?

  • 子彈運動方向與坦克一致

  • /** 子彈運動方向*/public void go() {switch(direction) {case UP:upWard();break;case DOWN:downWard();break;case LEFT:leftWard();break;case RIGHT:rightWard();break;}} /** 子彈運動坐標改變*/private void rightWard() {// TODO Auto-generated method stubx+=speed;}private void downWard() {// TODO Auto-generated method stuby+=speed;}private void leftWard() {// TODO Auto-generated method stubx-=speed;}private void upWard() {// TODO Auto-generated method stuby-=speed;}

    碰撞檢測

  • 子彈與土墻

  • 子彈與鐵墻

  • 子彈與基地

  • 子彈與邊界

  • 子彈與子彈


  • ?1、子彈與土墻

    /** 子彈和土墻碰撞*/public void hitWall() {Rectangle next=this.getRec();List<Wall>walls=this.gamePanel.wallList;for(Wall w:walls) {if(w.getRec().intersects(next)) {Music.wallPlay();this.gamePanel.wallList.remove(w);this.gamePanel.removeList.add(this);break;}}}

    ?2、子彈與鐵墻

    /** 子彈與Fe*/public void hitFe() {Rectangle next=this.getRec();List<Fe>fes=this.gamePanel.feList;for(Fe f:fes) {if(f.getRec().intersects(next)) {Music.wallPlay();this.gamePanel.removeList.add(this);break;}}}

    ?3、子彈與基地

    /** 擊中基地*/public void hitBase() {Rectangle next=this.getRec();for(Base base:gamePanel.baseList) {if(base.getRec().intersects(next)) {this.gamePanel.baseList.remove(base);this.gamePanel.removeList.add(this);this.gamePanel.state=3;break;}}}

    ?4、子彈與邊界

    /** 移動到邊界*/public void moveToBorder() {if(x<0||x>this.gamePanel.getWidth()) {this.gamePanel.removeList.add(this);}if(y<0||y>this.gamePanel.getHeight()) {this.gamePanel.removeList.add(this);}}

    ?5、子彈與子彈

    /** 子彈與子彈碰撞檢測*/public void hitEnemyBullet() {Rectangle next=this.getRec();List<EnemyBullet>enemyBullets=this.gamePanel.enemyBulletsList;for(EnemyBullet enemyBullet:enemyBullets) {if(enemyBullet.getRec().intersects(next)) {Music.wallPlay();this.gamePanel.removeList2.add(enemyBullet);this.gamePanel.removeList.add(this);break;}}}

    ?總

    import java.awt.Graphics; import java.awt.Rectangle; import java.util.List;public class Bullet extends GameObject{//長寬private int width=10;private int height=10;//速度private int speed=7;//方向Direction direction;//初始化子彈public Bullet(String img,int x,int y,Direction direction,GamePanel gamePanel) {super(img,x,y,gamePanel);this.direction=direction; }/** 子彈運動方向*/public void go() {switch(direction) {case UP:upWard();break;case DOWN:downWard();break;case LEFT:leftWard();break;case RIGHT:rightWard();break;}}/** 子彈運動坐標改變*/private void rightWard() {// TODO Auto-generated method stubx+=speed;}private void downWard() {// TODO Auto-generated method stuby+=speed;}private void leftWard() {// TODO Auto-generated method stubx-=speed;}private void upWard() {// TODO Auto-generated method stuby-=speed;}/** 子彈與坦克碰撞檢測*/public void hitBot() {//矩形類Rectangle next=this.getRec();List<Bot>bots=this.gamePanel.botList;//子彈和人機for(Bot bot:bots) {if(bot.getRec().intersects(next)) {Explode[]arr=new Explode[7];for(int i=0;i<7;i++) {Explode explode=new Explode("images/explode/"+(i+1)+".gif", x, y, this.gamePanel);this.gamePanel.explodeList.add(explode);}Music.explodePlay();this.gamePanel.botList.remove(bot);this.gamePanel.removeList.add(this);break;}}}/** 子彈與子彈碰撞檢測*/public void hitEnemyBullet() {Rectangle next=this.getRec();List<EnemyBullet>enemyBullets=this.gamePanel.enemyBulletsList;for(EnemyBullet enemyBullet:enemyBullets) {if(enemyBullet.getRec().intersects(next)) {Music.wallPlay();this.gamePanel.removeList2.add(enemyBullet);this.gamePanel.removeList.add(this);break;}}}/** 子彈和土墻碰撞*/public void hitWall() {Rectangle next=this.getRec();List<Wall>walls=this.gamePanel.wallList;for(Wall w:walls) {if(w.getRec().intersects(next)) {Music.wallPlay();this.gamePanel.wallList.remove(w);this.gamePanel.removeList.add(this);break;}}}/** 子彈與Fe*/public void hitFe() {Rectangle next=this.getRec();List<Fe>fes=this.gamePanel.feList;for(Fe f:fes) {if(f.getRec().intersects(next)) {Music.wallPlay();this.gamePanel.removeList.add(this);break;}}}/** 移動到邊界*/public void moveToBorder() {if(x<0||x>this.gamePanel.getWidth()) {this.gamePanel.removeList.add(this);}if(y<0||y>this.gamePanel.getHeight()) {this.gamePanel.removeList.add(this);}}/** 擊中基地*/public void hitBase() {Rectangle next=this.getRec();for(Base base:gamePanel.baseList) {if(base.getRec().intersects(next)) {this.gamePanel.baseList.remove(base);this.gamePanel.removeList.add(this);this.gamePanel.state=3;break;}}}@Overridepublic void paintSelf(Graphics g) {// TODO Auto-generated method stubg.drawImage(img,x,y,null);go();//碰撞檢測hitBot();hitWall();hitBase();hitFe();hitEnemyBullet();}@Overridepublic Rectangle getRec() {return new Rectangle(x,y,width,height);}}

    ?人機子彈

    人機與玩家的子彈有什么差別呢??

  • 可以擊中玩家,不能擊中坦克?

  • ?擊中玩家

    /** 擊中玩家*/public void hitPlayer() {Rectangle next=this.getRec();List<Tank>tanks=this.gamePanel.tankList;//子彈和坦克for(Tank tank:tanks) {if(tank.getRec().intersects(next)) {tank.alive=false;this.gamePanel.tankList.remove(tank);this.gamePanel.removeList.add(this);break;}}}

    ?總

    import java.awt.Graphics; import java.awt.Rectangle; import java.util.List; /** 人機子彈*/ public class EnemyBullet extends Bullet{public EnemyBullet(String img, int x, int y, Direction direction, GamePanel gamePanel) {super(img, x, y, direction, gamePanel);}public void hitPlayer() {//攻擊到玩家,玩家死亡Rectangle next=this.getRec();List<Tank>tanks=this.gamePanel.tankList;//子彈和坦克for(Tank tank:tanks) {if(tank.getRec().intersects(next)) {tank.alive=false;this.gamePanel.tankList.remove(tank);this.gamePanel.removeList.add(this);break;}}}@Overridepublic void hitBase() {//攻擊到基地,游戲結束Rectangle next=this.getRec();for(Base base:gamePanel.baseList) {if(base.getRec().intersects(next)) {this.gamePanel.baseList.remove(base);this.gamePanel.removeList2.add(this);this.gamePanel.state=3;break;}}}public void hitWall() {//攻擊到土墻,子彈與土均消失Rectangle next=this.getRec();List<Wall>walls=this.gamePanel.wallList;for(Wall w:walls) {if(w.getRec().intersects(next)) {this.gamePanel.wallList.remove(w);this.gamePanel.removeList2.add(this);break;}}}public void hitFe() {//攻擊到鐵墻,墻不變,子彈消失Rectangle next=this.getRec();List<Fe>fes=this.gamePanel.feList;for(Fe f:fes) {if(f.getRec().intersects(next)) {this.gamePanel.removeList2.add(this);break;}}}public void paintSelf(Graphics g) {g.drawImage(img,x,y,null);go();hitBase();hitWall();hitFe();hitPlayer();} }

    添加圍墻、基地

    剩下的就是間的添加圍墻、基地等對象了。

    Base

    import java.awt.Graphics; import java.awt.Rectangle;public class Base extends GameObject{public int width=60;public int height=60;public Base(String img,int x,int y,GamePanel gamePanel) {super(img,x,y,gamePanel);}@Overridepublic void paintSelf(Graphics g) {g.drawImage(img,x,y,null);// TODO Auto-generated method stub}@Overridepublic Rectangle getRec() {return new Rectangle(x,y,width,height);} }

    Wall

    import java.awt.Graphics; import java.awt.Rectangle;public class Wall extends GameObject{private int width=60;private int height=60;public Wall(String img,int x,int y,GamePanel gamePanel) {super(img,x,y,gamePanel);}@Overridepublic void paintSelf(Graphics g) {g.drawImage(img,x,y,null);}@Overridepublic Rectangle getRec() { return new Rectangle(x,y,width,height);} }

    Grass

    import java.awt.Graphics; import java.awt.Rectangle;public class Grass extends GameObject{public Grass(String img,int x,int y,GamePanel gamePanel) {super(img,x,y,gamePanel);}@Overridepublic void paintSelf(Graphics g) {g.drawImage(img,x,y,null);}@Overridepublic Rectangle getRec() {return null;}}

    Fe

    import java.awt.Graphics; import java.awt.Rectangle;public class Fe extends GameObject{private int width=60;private int height=60;public Fe(String img,int x,int y,GamePanel gamePanel) {super(img,x,y,gamePanel);}@Overridepublic void paintSelf(Graphics g) {g.drawImage(img,x,y,null);}@Overridepublic Rectangle getRec() {return new Rectangle(x,y,width,height);}}

    優化

    爆炸

    import java.awt.Graphics; import java.awt.Rectangle;public class Explode extends GameObject{public Explode(String img,int x,int y,GamePanel gamePanel) {super(img,x,y,gamePanel);}@Overridepublic void paintSelf(Graphics g) {g.drawImage(img,x-25,y-30,null);//x,y為圖片左上角的坐標,調整圖片位置,使圖片居中}@Overridepublic Rectangle getRec() {// TODO Auto-generated method stubreturn null;} }

    音樂

    import java.io.File;import javax.sound.sampled.AudioInputStream; import javax.sound.sampled.AudioSystem; import javax.sound.sampled.Clip;public class Music{private static Clip start;//剛進入游戲的音樂private static Clip move;//玩家移動音樂private static Clip attack;//玩家射擊音樂private static Clip explode;//爆炸音效private static Clip wall;//擊中墻體音效static {File bgMusicStartFile = new File("D:\\JAVA\\eclipse\\TankWar\\musics\\bgm.wav");File bgMusicAttackFile = new File("D:\\JAVA\\eclipse\\TankWar\\musics\\attack.wav");File bgMusicMoveFile = new File("D:\\JAVA\\eclipse\\TankWar\\musics\\move.wav");File bgMusicExplodeFile = new File("D:\\JAVA\\eclipse\\TankWar\\musics\\explode.wav");File bgMusicWallFile = new File("D:\\JAVA\\eclipse\\TankWar\\musics\\wall.wav");try {AudioInputStream audioInputStreamStart = AudioSystem.getAudioInputStream(bgMusicStartFile);start = AudioSystem.getClip();start.open(audioInputStreamStart);AudioInputStream audioInputStreamAttack = AudioSystem.getAudioInputStream(bgMusicAttackFile);attack = AudioSystem.getClip();attack.open(audioInputStreamAttack);AudioInputStream audioInputStreamStartMove = AudioSystem.getAudioInputStream(bgMusicMoveFile);move = AudioSystem.getClip();move.open(audioInputStreamStartMove);AudioInputStream audioInputStreamStartExplode = AudioSystem.getAudioInputStream(bgMusicExplodeFile);explode = AudioSystem.getClip();explode.open(audioInputStreamStartExplode); AudioInputStream audioInputStreamStartWall = AudioSystem.getAudioInputStream(bgMusicWallFile);wall = AudioSystem.getClip();wall.open(audioInputStreamStartWall); } catch (Exception e) {e.printStackTrace();}}public static void playBackground(){//循環播放move.setFramePosition(0);move.loop(Clip.LOOP_CONTINUOUSLY); }public static void startPlay(){start.start();start.setFramePosition(0);}public static void attackPlay(){attack.start();//將進度條調為0attack.setFramePosition(0);}public static void movePlay(){move.start();move.setFramePosition(0);}public static void moveStop(){move.stop();}public static void explodePlay(){explode.start();explode.setFramePosition(0);}public static void wallPlay() {wall.start();wall.setFramePosition(0);} }

    重寫GamePanel

    import java.awt.Graphics; import java.awt.Image; import java.awt.Point; import java.awt.Toolkit; import java.awt.event.KeyAdapter; import java.awt.event.KeyEvent; import java.awt.event.MouseAdapter; import java.awt.event.MouseEvent; import java.util.ArrayList; import java.util.List; import java.util.Random;import javax.swing.JFrame;public class GamePanel extends JFrame{boolean one=true;boolean run=true;//關卡private int level=1;//定義雙緩存圖片Image offScreenImage=null;/** //游戲狀態* 0 未開始,1 單人模式,* 2 游戲暫停,3 游戲失敗,4 游戲勝利*/public int state =0;//游戲是否開始private boolean start=false;//臨時變量private int a=1;//窗口長寬private int width=1260;private int height=800;//指針初始縱坐標private int y=260;//基地private Base base=new Base("images/base.gif",660,740,this);//重繪次數public int count=0;//敵人數量private int enemyCount=0;///隨機生成的墻體數量private int wallCount=100;private boolean d=true;private int[]xrr=new int[wallCount];private int[]yrr=new int[wallCount];//物體集合public List<Bullet>bulletList=new ArrayList<>();public List<Tank>tankList=new ArrayList<>();public List<Bot>botList=new ArrayList<>();public List<Bullet>removeList=new ArrayList<>();public List<Wall>wallList=new ArrayList<>();public List<Grass>grassList=new ArrayList<>();public List<Fe>feList=new ArrayList<>();public List<Base> baseList = new ArrayList<>();public List<EnemyBullet>enemyBulletsList=new ArrayList<>();public List<EnemyBullet>removeList2=new ArrayList<>();public List<Explode>explodeList=new ArrayList<>();//玩家private PlayerOne playerOne = new PlayerOne("images/player1/p1tankU.gif", 500, 700,"images/player1/p1tankU.gif","images/player1/p1tankD.gif","images/player1/p1tankL.gif","images/player1/p1tankR.gif", this);public void random() {Random r=new Random(); for(int i=0;i<wallCount;) {int x=r.nextInt(20);int y=r.nextInt(8)+3;if(i>0) {boolean repeat=false;for(int j=0;j<i;j++) {if(xrr[j]==x*60&&yrr[j]==y*60) {repeat=true;}}if(!repeat) {xrr[i]=x*60;yrr[i]=y*60;i++;}else {continue;}}else {xrr[i]=x*60;yrr[i]=y*60;i++;}}}/** 重置*/public void reset() {count=0;enemyCount=0;playerOne = new PlayerOne("images/player1/p1tankU.gif", 500, 700,"images/player1/p1tankU.gif","images/player1/p1tankD.gif","images/player1/p1tankL.gif","images/player1/p1tankR.gif", this);feList.clear();bulletList.clear();tankList.clear();botList.clear();removeList.clear();wallList.clear();grassList.clear();baseList.clear();enemyBulletsList.clear();removeList2.clear();explodeList.clear();}/** 添加墻,基地*/public void add() {random();//添加圍墻for(int i=0;i<21;i++) {wallList.add(new Wall("images/walls.gif",i*60,120,this));}wallList.add(new Wall("images/walls.gif",600,740,this));wallList.add(new Wall("images/walls.gif",600,680,this));wallList.add(new Wall("images/walls.gif",660,680,this));wallList.add(new Wall("images/walls.gif",720,680,this));wallList.add(new Wall("images/walls.gif",720,740,this));for(int i=0;i<wallCount;i++) {Random a=new Random();int num=a.nextInt(4);if(num<2) {Wall wall=new Wall("images/walls.gif",xrr[i], yrr[i], null);wallList.add(wall);}else if(num<3){Grass g=new Grass("images/cao.gif",xrr[i], yrr[i], null);grassList.add(g);}else {Fe f=new Fe("images/fe.gif",xrr[i], yrr[i], null);feList.add(f);}}//添加基地baseList.add(base);}/** 窗口的啟動方法*/public void launch() {//標題setTitle("坦克大戰無盡版");//窗口初始化大小setSize(width,height);//使屏幕居中setLocationRelativeTo(null);//添加關閉事件setDefaultCloseOperation(3);//用戶不能調整大小setResizable(false);//使窗口可見setVisible(true);//初始化基地圍墻;add();//添加鍵盤事件this.addKeyListener(new GamePanel.KeyMonitor());while(true) {if(botList.size()==0&&enemyCount==10) {state=4;}if(tankList.size()==0&&(state==1)) {state=3;}if(state==1) {if(count%50==1&&enemyCount<10) {boolean a=true;Random r=new Random();int rnum=r.nextInt(19)+1;if(enemyCount>0) {for(Bot b:botList) {if(Math.abs(rnum*60-b.getX())<60) {a=false;}}if(a) {botList.add(new Bot("images/enemy/enemy1U.gif", rnum*60, 60,"images/enemy/enemy1U.gif","images/enemy/enemy1D.gif","images/enemy/enemy1L.gif","images/enemy/enemy1R.gif", this));enemyCount++;}}else {botList.add(new Bot("images/enemy/enemy1U.gif", rnum*60, 60,"images/enemy/enemy1U.gif","images/enemy/enemy1D.gif","images/enemy/enemy1L.gif","images/enemy/enemy1R.gif", this));enemyCount++;}}if(count%2==1) {if(!explodeList.isEmpty()) {explodeList.remove(0);}}}if(run) {repaint();}try {Thread.sleep(25);}catch (Exception e) {e.printStackTrace();// TODO: handle exception}}}@Overridepublic void paint(Graphics g) {//創建和容器一樣大小的Image圖片if(offScreenImage==null) {offScreenImage=this.createImage(width,height);}//獲得該圖片的畫布Graphics gImage=offScreenImage.getGraphics();//填充整個畫布gImage.fillRect(0,0,width,height);if(state==0) {//添加圖片gImage.drawImage(Toolkit.getDefaultToolkit().getImage("images/interface.png"),0,0,this);//添加鼠標事件this.addMouseListener(new GamePanel.MouseMonitor());}else if(state==1) {//paint重繪游戲元素for(Tank player:tankList) {player.paintSelf(gImage);}for(Bullet bullet:bulletList) {bullet.paintSelf(gImage);}bulletList.removeAll(removeList);for(EnemyBullet enemyBullet:enemyBulletsList) {enemyBullet.paintSelf(gImage);}enemyBulletsList.removeAll(removeList2);for(Explode explode:explodeList) {explode.paintSelf(gImage);}for(Bot bot:botList) {bot.paintSelf(gImage);}for(Wall wall:wallList) {wall.paintSelf(gImage);}for(Fe fe:feList) {fe.paintSelf(gImage);}for(Grass grass:grassList) {grass.paintSelf(gImage);}for(Base base:baseList) {base.paintSelf(gImage);}//重繪次數+1count++;}else if(state==2) {}else if(state==3) {gImage.drawImage(Toolkit.getDefaultToolkit().getImage("images/shibai.png"),315,200,this);//添加鼠標事件this.addMouseListener(new GamePanel.MouseMonitor());}else if(state==4) {gImage.drawImage(Toolkit.getDefaultToolkit().getImage("images/win.png"),(width-322)/2,(height-84)/2,this);this.addMouseListener(new GamePanel.MouseMonitor());}//將緩沖區繪制好的圖形整個繪制到容器的畫布中g.drawImage(offScreenImage,0,0,null);}/** 添加鍵盤監聽*/private class KeyMonitor extends KeyAdapter{@Overridepublic void keyPressed(KeyEvent e) {int key=e.getKeyCode();switch(key) {case KeyEvent.VK_ENTER:if(!start) {tankList.add(playerOne);//將坦克添加至坦克集合state=a;start=true;}break;case KeyEvent.VK_P:if(state!=2) {a=state;state=2;run=false;}else {state=a;run=true;if(a==0) {a=1;}}break; default:playerOne.keyPressed(e);break;}}@Overridepublic void keyReleased(KeyEvent e) {playerOne.keyReleased(e);}}//添加鼠標監聽private class MouseMonitor extends MouseAdapter{@Overridepublic void mouseClicked(MouseEvent e) {Point p=new Point(e.getX(),e.getY());if(!start&&state==0) {if(p.x>450&&p.x<750&&p.y>400&&p.y<480) {tankList.add(playerOne);state=1;start=true;Music.startPlay();}}else if(state==3||state==4) {reset();start=false;state=0;add();}}} public static void main(String[]args) {GamePanel gamePanel=new GamePanel();gamePanel.launch();} }

    ?游戲最終成品

    ?

    ?

    ?

    總結

    以上是生活随笔為你收集整理的java实现坦克大战的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。