package com.test1; import java.util.Vector; class EnemyTank extends tank implements Runnable { public Vector<EnemyTank> getEts() { return ets; } public void setEts(Vector<EnemyTank> ets) { this.ets = ets; } Vector<EnemyTank> ets=new Vector<EnemyTank>(); Vector<Shot> ss=new Vector<Shot>(); int times=0; //构造函数 public EnemyTank(int x,int y,int type) { super(x, y,type); } //得到坦克位置 public void dedaoentank(Vector<EnemyTank> vv) { this.ets=vv; } public boolean Pudao() { boolean b=false; switch(this.direct) { case 0://敌人当前坦克向上 //取出所有敌人坦克 for(int i=0;i<ets.size();i++) { //取出第一个坦克 EnemyTank et=ets.get(i); //如果不是当前的坦克 if(et!=this) { //如果敌人同伴的坦克向上或向下 if(et.direct==0||et.direct==1) { //判断敌人当前坦克左轮与同伴坦克(向上或向下)的位置比较 if(this.x>=et.x&&this.x<=et.x+20&&this.y>=et.y&&this.y<=et.y+30) { return true; } if(this.x+20>=et.x&&this.x+20<=et.x+20&&this.y>=et.y&&this.y<=et.y+30) { return true; } } //如果敌人同伴的坦克向左或向右 if(et.direct==2||et.direct==3) { //判断敌人当前坦克右轮与同伴坦克(向左或向右)的位置比较 if(this.x>=et.x&&this.x<=et.x+30&&this.y>=et.y&&this.y<=et.y+20) { return true; } if(this.x+20>=et.x&&this.x+20<=et.x+30&&this.y>=et.y&&this.y<=et.y+20) { return true; } } } } break; case 1://敌人当前坦克向下 for(int i=0;i<ets.size();i++) { EnemyTank et=ets.get(i); if(et!=this) { if(et.direct==0||et.direct==1) { if(this.x>=et.x&&this.x<=et.x+20&&this.y+30>=et.y&&this.y+30<=et.y+30) { return true; } if(this.x+20>=et.x&&this.x+20<=et.x+20&&this.y+30>=et.y&&this.y+30<=et.y+30) { return true; } } if(et.direct==2||et.direct==3) { if(this.x>=et.x&&this.x<=et.x+30&&this.y+30>=et.y&&this.y+30<=et.y+20) { return true; } if(this.x+20>=et.x&&this.x+20<=et.x+30&&this.y+30>=et.y&&this.y+30<=et.y+20) { return true; } } } } break; case 2://敌人当前坦克向左 for(int i=0;i<ets.size();i++) { EnemyTank et=ets.get(i); if(et!=this){ if(et.direct==0||et.direct==1) { if(this.x>=et.x&&this.x<=et.x+20&&this.y>=et.y&&this.y<=et.y+30) { return true; } if(this.x>=et.x&&this.x<=et.x+20&&this.y+20>=et.y&&this.y+20<=et.y+30) { return true; } } if(et.direct==2||et.direct==3) { if(this.x>=et.x&&this.x<=et.x+30&&this.y>=et.y&&this.y<=et.y+20) { return true; } if(this.x>=et.x&&this.x<=et.x+30&&this.y+20>=et.y&&this.y+20<=et.y+20) { return true; } } } } break; case 3://敌人当前坦克向右 for(int i=0;i<ets.size();i++) { EnemyTank et=ets.get(i); if(et!=this){ if(et.direct==0||et.direct==1) { if(this.x+30>=et.x&&this.x+30<=et.x+20&&this.y>=et.y&&this.y<=et.y+30) { return true; } if(this.x+30>=et.x&&this.x+30<=et.x+20&&this.y+20>=et.y&&this.y+20<=et.y+30) { return true; } } if(et.direct==2||et.direct==3) { if(this.x+30>=et.x&&this.x+30<=et.x+30&&this.y>=et.y&&this.y<=et.y+20) { return true; } if(this.x+30>=et.x&&this.x+30<=et.x+30&&this.y+20>=et.y&&this.y+20<=et.y+20) { return true; } } } } break; } return b; } @Override public void run() { while(true) { switch (this.direct) { case 0: for(int i=0;i<=50;i++) { if(y>0&&!this.Pudao()) { y-=speed; } try { Thread.sleep(50); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } break; case 1: for(int i=0;i<=50;i++) { if(x<500&&!this.Pudao()) { x+=speed; } try { Thread.sleep(50); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } break; case 2: for(int i=0;i<=50;i++) { if(y<500&&!this.Pudao()) { y+=speed; } try { Thread.sleep(50); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } break; case 3: for(int i=0;i<=50;i++) { if(x>0&&!this.Pudao()) { x-=speed; } try { Thread.sleep(50); } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } break; } this.times++; if(times%2==0) { if(islive) { if(ss.size()<5) { Shot s=null; //没有×××,添加××× switch(direct) { case 0: s=new Shot(x+10, y, 0); ss.add(s); break; case 1: s=new Shot(x+10, y+29, 1); ss.add(s); break; case 2: s=new Shot(x, y+10, 2); ss.add(s); break; case 3: s=new Shot(x+29, y+10, 3); ss.add(s); break; } //启动敌人×××线程 Thread t=new Thread(s); t.start(); } } } //随机生成方向 this.direct=(int)(Math.random()*4); if(this.islive==false) { break; } } } } package com.test1; import java.util.Vector; class Hero extends tank { Vector<Shot> ss=new Vector<Shot>(); Shot s=null; int speed=5; //构造方法 public Hero(int x,int y,int type) { super(x, y,type); } public void moveup() { y-=speed; } public void movedown() { y+=speed; } public void moveright() { x+=speed; } public void moveleft() { x-=speed; } public void Shotem() { switch (direct) { case 0://向上 //创建一颗××× s=new Shot(x+10, y, 0); //将×××加入到向量集中 ss.add(s); break; case 1://向下 s=new Shot(x+10, y+29, 1); ss.add(s); break; case 2://向左 s=new Shot(x, y+10, 2); ss.add(s); break; case 3://向右 s=new Shot(x+29, y+10, 3); ss.add(s); break; } //启动×××线程 Thread t=new Thread(s); t.start(); } }
package com.test1;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.Vector;
import javax.swing.JFrame;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
@SuppressWarnings("serial")
public class MyTank extends JFrame implements ActionListener {
// 定义组件
jpanel mp = null;
// 定义一个开始面板
MyStartPanel msp = null;
// 做出菜单
JMenuBar jmb = null;
// 开始游戏
JMenu jm1 = null;
JMenuItem jmi1 = null;
// 退出游戏
JMenuItem jmi2 = null;
// 存盘退出
JMenuItem jmi3 = null;
// 接上局
JMenuItem jmi4 = null;
// 构造函数
public MyTank() {
jmb = new JMenuBar();
jm1 = new JMenu("游戏(G)");
// 设置快捷方式
jm1.setMnemonic('G');
jmi1 = new JMenuItem("开始新游戏(N)");
jmi1.setMnemonic('N');
// 对jmi1相应
jmi1.addActionListener(this);
jmi1.setActionCommand("newgame");
jmi2 = new JMenuItem("退出游戏(E)");
jmi2.setMnemonic('E');
jmi2.addActionListener(this);
jmi2.setActionCommand("exit");
jmi3 = new JMenuItem("存盘退出(S)");
jmi3.setMnemonic('S');
jmi3.addActionListener(this);
jmi3.setActionCommand("save");
jmi4 = new JMenuItem("继续游戏(C)");
jmi4.setMnemonic('C');
jmi4.addActionListener(this);
jmi4.setActionCommand("congame");
jm1.add(jmi1);
jm1.add(jmi2);
jm1.add(jmi3);
jm1.add(jmi4);
jmb.add(jm1);
this.setJMenuBar(jmb);
msp = new MyStartPanel();
Thread t = new Thread(msp);
t.start();
// 添加组件
this.add(msp);
// 设置窗体
this.setTitle("坦克大战");// 窗体标签
this.setSize(600, 600);
this.setLocationRelativeTo(null);
this.setVisible(true);
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
public void actionPerformed(ActionEvent e) {
// 对用户不同的点击,做出不同的处理
if (e.getActionCommand().equals("newgame")) {
// 创建战场面板
mp = new jpanel("newgame");
// 启动mp线程
Thread ta = new Thread(mp);
ta.start();
// 先删除旧的开始面板
this.remove(msp);
// 加入组件
this.add(mp);
// 监听
this.addKeyListener(mp);
// 显示,刷新JFrame
this.setVisible(true);
} else if (e.getActionCommand().equals("exit")) {
// 用户点击了退出菜单
// 保存用户游戏记录数据
Record.keepRecorder();
System.exit(0);
} else if (e.getActionCommand().equals("save")) {
// 用户点击保存菜单
// 保存击毁敌人的数量和敌人的坐标
Record.setEts(mp.ets);
Record.keepRecAndEnemyTank();
Record.keepRecorder();
System.exit(0);
} else if (e.getActionCommand().equals("congame")) {
// 继续上次游戏
// 创建战场面板
mp = new jpanel("congame");
// 启动mp线程
Thread ta = new Thread(mp);
ta.start();
// 先删除旧的开始面板
this.remove(msp);
// 加入组件
this.add(mp);
// 监听
this.addKeyListener(mp);
// 显示,刷新JFrame
this.setVisible(true);
}
}
@SuppressWarnings("unused")
public static void main(String[] args) {
MyTank win = new MyTank();
}
}
// 开始面板--起提示作用
@SuppressWarnings("serial")
class MyStartPanel extends JPanel implements Runnable {
int times = 0;
public void paint(Graphics g) {
super.paint(g);
g.setColor(Color.black);
g.fillRect(0, 0, 500, 500);
// 提示信息
if (times % 2 == 0) {
g.setColor(Color.red);
// 开关信息的字体
Font myFont = new Font("宋体", Font.CENTER_BASELINE, 30);
g.setFont(myFont);
g.drawString("Stage: 1", 200, 250);
}
}
public void run() {
while (true) {
// 休眠
try {
Thread.sleep(500);
} catch (Exception e) {
e.printStackTrace();
}
times++;
// 重画
this.repaint();
}
}
}
@SuppressWarnings("serial")
class jpanel extends JPanel implements KeyListener, Runnable {
// 创建英雄
Hero hero = null;
Vector<EnemyTank> ets = new Vector<EnemyTank>();
Vector<Node> nodes=new Vector<Node>();
int enside = 3;
// 构造函数
@SuppressWarnings("static-access")
public jpanel(String flag) {
Record.GetRecord();
// 初始化位置
hero = new Hero(10, 10, 2);
if(flag.equals("newgame")){
// 初始化敌人坦克
for (int i = 0; i < enside; i++) {
EnemyTank et = new EnemyTank((i + 1) * 50, 0, 1);
et.dedaoentank(ets);
Thread t1 = new Thread(et);
t1.start();
// ×××
Shot enshot = new Shot(et.x + 10, et.y + 10, 2);
et.ss.add(enshot);
Thread t2 = new Thread(enshot);
t2.start();
ets.add(et);
}
}
else if(flag.equals("congame")){
nodes=new Record().getNodesAndEnNums();
//初始化敌人的坦克
for(int i=0;i<nodes.size();i++){
Node node=nodes.get(i);
//创建一辆敌人的坦克对象
EnemyTank et=new EnemyTank(node.x, node.y,node.direct);
//将MyPanel的敌人向量交给该敌人坦克
et.setEts(ets);
et.setType(1);
//启动敌人坦克进程
Thread t=new Thread(et);
t.start();
//给敌人坦克添加一颗×××
Shot s=new Shot(et.x+10, et.y+30, 1);
//把×××加入给敌人
et.ss.add(s);
Thread t2=new Thread(s);
t2.start();
//加入敌人坦克
ets.add(et);
}
}
}
// 绘制
public void paint(Graphics g) {
super.paint(g);
g.fillRect(0, 0, 530, 530);
// 画出提示信息
ShowInfo(g);
// 画出我的坦克
if (hero.islive) {
this.drawTank(hero.getX(), hero.getY(), g, this.hero.direct,this.hero.type);
}
// 画出敌人坦克
for (int i = 0; i <ets.size(); i++) {
EnemyTank et = ets.get(i);
if (et.islive) {
this.drawTank(et.getX(), et.getY(), g, et.direct, et.type);
for (int j = 0; j < et.ss.size(); j++) {
Shot enShot = et.ss.get(j);
if (enShot.isLive) {
g.draw3DRect(enShot.x, enShot.y, 1, 1, false);
} else {
// 如果敌人的坦克死亡了就从向量Vector中去掉
et.ss.remove(enShot);
}
}
}
}
// 画出×××
for (int i = 0; i < hero.ss.size(); i++) {
Shot myShot = hero.ss.get(i);
if (myShot != null && myShot.isLive == true) {
g.draw3DRect(myShot.x, myShot.y, 1, 1, false);
}
if (myShot.isLive == false) {
hero.ss.remove(myShot);
}
}
}
// 画出提示坦克
public void ShowInfo(Graphics g) {
// 画出提示坦克
this.drawTank(530, 500, g, 0, 1);
g.drawString(Record.getEnnum() + "", 550, 520);
this.drawTank(530, 460, g, 0, 2);
g.drawString(Record.getMynum() + "", 550, 480);
// 画出玩家的总成绩
g.setColor(Color.black);
g.setFont(new Font("宋体", Font.BOLD, 20));
g.drawString("成绩", 530, 20);
this.drawTank(530, 30, g, 1, 0);
g.setColor(Color.black);
g.setFont(new Font("宋体", Font.BOLD, 20));
g.drawString(Record.getAllEnNum() + "", 560, 50);
}
// 打到我的坦克
public void hitmytank() {
for (int i = 0; i < this.ets.size(); i++) {
EnemyTank eTank = ets.get(i);
for (int j = 0; j < eTank.ss.size(); j++) {
Shot enShot = eTank.ss.get(j);
if (this.hittank(hero, enShot)) {
Record.reducemyNum();
}
}
}
}
// 毁灭敌人坦克
public void hitentank() {
for (int i = 0; i < hero.ss.size(); i++) {
Shot myShot = hero.ss.get(i);
if (myShot.isLive) {
for (int j = 0; j < ets.size(); j++) {
EnemyTank et = ets.get(j);
if (et.islive) {
if (this.hittank(et, myShot)) {
Record.reduceEnNum();
Record.addEnNumRec();
}
}
}
}
}
}
public boolean hittank(tank et, Shot s) {
boolean b = false;
switch (et.direct) {
case 0:
case 2:
if (s.x > et.x && s.x < et.x + 20 && s.y > et.y && s.y < et.y + 30) {
s.isLive = false;
et.islive = false;
b = true;
}
break;
case 1:
case 3:
if (s.x > et.x && s.x < et.x + 30 && s.y > et.y && s.y < et.y + 20) {
s.isLive = false;
et.islive = false;
b = true;
}
break;
}
return b;
}
// keyPressed代表键被按下,控制函数方向
public void keyPressed(KeyEvent e) {
System.out.println("按下了" + e.getKeyChar() + "键");
if (e.getKeyCode() == KeyEvent.VK_DOWN) {
System.out.println("向下");
this.hero.setDirect(1);
this.hero.movedown();
} else if (e.getKeyCode() == KeyEvent.VK_UP) {
System.out.println("向上");
this.hero.setDirect(0);
this.hero.moveup();
} else if (e.getKeyCode() == KeyEvent.VK_LEFT) {
System.out.println("向左");
this.hero.setDirect(2);
this.hero.moveleft();
} else if (e.getKeyCode() == KeyEvent.VK_RIGHT) {
System.out.println("向右");
this.hero.setDirect(3);
this.hero.moveright();
}
if (e.getKeyCode() == KeyEvent.VK_SPACE) {
if (this.hero.ss.size() < 5) {
this.hero.Shotem();
}
}
// 调用repaint()函数,来重绘界面
this.repaint();
}
// 绘制坦克函数
public void drawTank(int x, int y, Graphics g, int direct, int type) {
// 设置类型
switch (type) {
case 1:
g.setColor(Color.cyan);
break;
case 0:
g.setColor(Color.red);
break;
case 2:
g.setColor(Color.yellow);
break;
}
// 设置方向
switch (direct) {
case 0:
g.fill3DRect(x, y, 5, 30, false);
g.fill3DRect(x + 15, y, 5, 30, false);
g.fill3DRect(x + 5, y + 5, 10, 20, false);
g.fillOval(x + 5, y + 10, 10, 10);
g.drawLine(x + 5, y + 15, x + 10, y);
break;
case 1:
g.fill3DRect(x, y, 5, 30, false);
g.fill3DRect(x + 15, y, 5, 30, false);
g.fill3DRect(x + 5, y + 5, 10, 20, false);
g.fillOval(x + 5, y + 10, 10, 10);
g.drawLine(x + 10, y + 15, x + 10, y + 29);
break;
case 2:
g.fill3DRect(x, y, 30, 5, false);
g.fill3DRect(x, y + 15, 30, 5, false);
g.fill3DRect(x + 5, y + 5, 20, 10, false);
g.fillOval(x + 10, y + 5, 10, 10);
g.drawLine(x + 15, y + 10, x, y + 10);
break;
case 3:
g.fill3DRect(x, y, 30, 5, false);
g.fill3DRect(x, y + 15, 30, 5, false);
g.fill3DRect(x + 5, y + 5, 20, 10, false);
g.fillOval(x + 10, y + 5, 10, 10);
g.drawLine(x + 15, y + 10, x + 29, y + 10);
break;
}
}
@Override
public void keyTyped(KeyEvent e) {
// TODO Auto-generated method stub
}
@Override
public void keyReleased(KeyEvent e) {
// TODO Auto-generated method stub
}
public void run() {
while (true) {
try {
Thread.sleep(10);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
this.hitmytank();
this.hitentank();
this.repaint();
}
}
}
package com.test1;
public class Node {
int x;
int y;
int direct;
public Node(int x, int y, int direct) {
// TODO Auto-generated constructor stub
this.x = x;
this.y = y;
this.direct = direct;
}
}
package com.test1;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.Vector;
class Record {
private static int ennum = 20;
private static int mynum = 3;
private static int allEnNum = 0;
private static FileReader fr = null;
private static FileWriter fw = null;
private static BufferedReader br = null;
private static BufferedWriter bw = null;
private static Vector<EnemyTank> ets = new Vector<EnemyTank>();
// 从文件中恢复记录点
private static Vector<Node> nodes = new Vector<Node>();
public static Vector<EnemyTank> getEts() {
return ets;
}
public static void setEts(Vector<EnemyTank> ets) {
Record.ets = ets;
}
// 保存击毁敌人的数量和敌人坦克坐标、方向
public static void keepRecAndEnemyTank() {
try {
// 创建
fw = new FileWriter("e:\\tanksave1.txt");
bw = new BufferedWriter(fw);
// 保存当前还活着的敌人坦克坐标、方向
for (int i = 0; i < ets.size(); i++) {
// 取出第一个坦克
EnemyTank et = ets.get(i);
if (et.islive) {
// 活的保存
String recode = et.getX() + " " + et.getY() + " "
+ et.getDirect();// 得到坐标x,y和方向direct
// 写入到文件
bw.write(recode + "\r\n");
}
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
// 关闭流,先开后关,后开先关
try {
bw.close();
fw.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
// 保存击中坦克数量
public static void keepRecorder() {
try {
fw = new FileWriter("e:\\tanksave.txt");
bw = new BufferedWriter(fw);
bw.write(allEnNum + "");
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
bw.close();
fw.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
//完成读取任务点任务
public static Vector<Node> getNodesAndEnNums(){
try {
fr=new FileReader("e:\\tanksave1.txt");
br=new BufferedReader(fr);
String n;
while((n=br.readLine())!=null){
String []Recovery=n.split(" ");//split方法可以按一行字符中有多少个空间来返回数组
Node node=new Node(Integer.parseInt(Recovery[0]),Integer.parseInt(Recovery[1]),Integer.parseInt(Recovery[2]));
nodes.add(node);
}
} catch (Exception e) {
e.printStackTrace();
}finally{
try {
br.close();
fr.close();
} catch (Exception e2) {
e2.printStackTrace();
}
}
return nodes;
}
// 读取记录
public static void GetRecord() {
try {
fr = new FileReader("e:\\tanksave.txt");
br = new BufferedReader(fr);
String n=br.readLine();
// while (br.readLine()!=null)
// {
allEnNum = Integer.parseInt(n);
//}
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
br.close();
fr.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
public static int getAllEnNum() {
return allEnNum;
}
public static void setAllEnNum(int allEnNum) {
Record.allEnNum = allEnNum;
}
public static int getEnnum() {
return ennum;
}
public static void setEnnum(int ennum) {
Record.ennum = ennum;
}
public static int getMynum() {
return mynum;
}
public static void setMynum(int mynum) {
Record.mynum = mynum;
}
// 敌人坦克死亡就减少坦克数
public static void reduceEnNum() {
ennum--;
}
public static void reducemyNum() {
mynum--;
}
// 当消灭敌人的时候
public static void addEnNumRec() {
allEnNum++;
}
}
package com.test1;
class Shot implements Runnable {
int x;
int y;
// 速度
int speed = 1;
int direct;
boolean isLive = true;
public Shot(int x, int y, int direct) {
this.x = x;
this.y = y;
this.direct = direct;
}
public void run() {
try {
Thread.sleep(100);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
while (true) {
switch (direct) {
case 0:// 向上
y -= speed;
break;
case 1:// 向下
y += speed;
break;
case 2:// 向 左
x -= speed;
break;
case 3:// 向右
x += speed;
break;
}
if (x < 0 || x > 500 || y < 0 || y > 500) {
this.isLive = false;
break;
}
System.out.println("×××坐标(" + x + "," + y + ")");
}
}
}
package com.test1;
class tank {
int x;
int y;
Shot s = null;
// 坦克的速度
int speed = 1;
boolean islive = true;
// 设置类型
int type = 0;
// 0表示上2表示左
int direct = 0;
public int getType() {
return type;
}
public void setType(int type) {
this.type = type;
}
public int getSpeed() {
return speed;
}
public void setSpeed(int speed) {
this.speed = speed;
}
public int getDirect() {
return direct;
}
public void setDirect(int direct) {
this.direct = direct;
}
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 tank(int x, int y, int type) {
this.x = x;
this.y = y;
this.type = type;
}
}