Java实现经典游戏黄金矿工的示例代码

作者:小虚竹and掘金 时间:2022-01-09 16:35:41 

前言

《黄金矿工》游戏是一个经典的抓金子小游戏,它可以锻炼人的反应能力。。该游戏中,可以通过“挖矿”获得积分,游戏道具:有3瓶药水,在回收绳子抓金子的时候速度稍快点。

主要设计

  • 设计游戏界面,用swing实现

  • 随机创建金块算法

  • 随机创建石块算法

  • 计时系统设计

  • 积分系统设计

  • 设置鼠标事件,鼠标左键出钩子;鼠标右键开始游戏,确认吃药水等功能。

功能截图

游戏开始:

Java实现经典游戏黄金矿工的示例代码

Java实现经典游戏黄金矿工的示例代码

抓金子

Java实现经典游戏黄金矿工的示例代码

代码实现

游戏核心类

public class GameWin extends JFrame { //继承JFrame才能监听鼠标键盘事件的功能

//设置静态变量 表示游戏状态 0表示未开始 1运行中 2商店 3失败 4胜利
   static int state;
   //创建链表 存储金块 石块
   List<Object> objectList = new ArrayList<>();

Bg bg = new Bg();//背景
   Line line = new Line(this);//线

{
       //是否可以放置
       boolean isPlace = true;
       //循环创建金块
       for (int i = 0; i < 11; i++){
           double random = Math.random();
           Gold gold;//存放当前生成的金块

if (random<0.3){
               gold = new GoldMini();
           }else if(random<0.7){
               gold = new Gold();
           }else{
               gold = new GoldPlus();
           }

for (Object obj:objectList){
               if (gold.getRoc().intersects(obj.getRoc())) {
                   //发生重叠 不能放置 需要重新生成
                   isPlace=false;
               }
           }
           //循环完毕  判断是否可放置
           if (isPlace){
               objectList.add(gold);
           }else {
               isPlace=true;
               i--;
           }

}
       //循环创建石块
       for (int i = 0; i < 5; i++){
           Rock rock = new Rock();
           for (Object obj:objectList){
               if (rock.getRoc().intersects(obj.getRoc())) {
                   isPlace = false;
               }
           }
           if (isPlace){
               objectList.add(rock);
           }else {
               isPlace=true;
               i--;
           }
       }
   }

Image offScreenImage;

void launch(){ //launch方法初始化窗口信息
       this.setVisible(true);//设置窗口可见
       this.setSize(768,1000);
       this.setLocationRelativeTo(null);//窗口位置:居中
       this.setTitle("黄金矿工");
       setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);//关闭窗口的方法

//设置鼠标事件 改变状态
       addMouseListener(new MouseAdapter() {
           @Override
           public void mouseClicked(MouseEvent e) {
               super.mouseClicked(e);
               //不同状态 发出不同指令
               switch (state){
                   case 0:
                       if (e.getButton()==3){
                           state=1;
                           bg.startTime = System.currentTimeMillis();
                       }
                       break;
                   case 1:
                       //左右摇摆 点击左键
                       if(e.getButton() == 1 && line.state==0){
                           line.state = 1;
                       }
                       //抓取返回 点击右键
                       if (e.getButton()==3 && line.state==3 && Bg.waterNum>0){
                           Bg.waterFlag=true;
                           Bg.waterNum--;
                       }
                       break;
                   case 2:
                       if (e.getButton()==1){
                           bg.shop=true;
                       }
                       if (e.getButton()==3){
                           state=1;
                           bg.startTime = System.currentTimeMillis();
                       }
                       break;
                   case 3:
                   case 4:
                       if (e.getButton()==1){
                           state=0;
                           bg.reGame();
                           line.reGame();
                       }
                       break;
                   default:

}

}
       });

//使线不停摆动
       while (true){
           repaint();
           nextLevel();

try {
               Thread.sleep(10);
           } catch (InterruptedException e) {
               e.printStackTrace();
           }
       }
   }

//下一关
   public void nextLevel(){
       if (bg.gameTime() && state==1){
           if (Bg.count >= bg.goal){//如果当前积分大于等于目标积分
               if (Bg.level==1){
                   state=4;
               }else {
                   state=2;
                   Bg.level++;//关卡数加一
               }

}else {
               state=3;
           }
           dispose();//释放已过关窗体
           GameWin gameWin = new GameWin();
           gameWin.launch();//调用launch方法绘制新窗口

}

}
   @Override
   public void paint(Graphics g) {
       //画布与窗体大小相同
       offScreenImage = this.createImage(768,1000);
       //给画布添加画笔
       Graphics gImage = offScreenImage.getGraphics();

bg.paintSelf(gImage);
       if (state == 1){
           //先画物体
           for(Object obj:objectList){
               obj.paintSelf(gImage);
           }
           //后画线
           line.paintSelf(gImage);
       }
       //将画布绘制到窗口中
       g.drawImage(offScreenImage,0,0,null);
   }

public static void main(String[] args) {
       GameWin gameWin = new GameWin();
       gameWin.launch();

}
}

钩子类

public class Line {
   //线的起点坐标
   int x = 380;
   int y = 180;

//终点坐标
   int endx = 500;
   int endy = 500;

//线的长度
   double length = 100;
   //线长最小值
   double MIN_length = 100;
   //线长最大值
   double MAX_length = 750;
   double n = 0;
   //方向参数
   int dir = 1;
   //状态0摇摆  状态1抓取  状态2收回  状态3抓取返回
   int state;

//钩爪图片
   Image hook = Toolkit.getDefaultToolkit().getImage("imgs/hook.png");

//抓取判定方法
   GameWin frame;

Line(GameWin frame){
       this.frame=frame;
   }

//钩爪碰撞检测 检测物体是否被抓取
   void logic(){
       for (Object obj:this.frame.objectList){
           if(endx>obj.x && endx<obj.x+obj.width
                   && endy>obj.y && endy<obj.y+obj.height){
               state=3;
               obj.flag=true;
           }
       }

}

//绘制方法
   void lines(Graphics g){
       //endx和endy的变化
       endx = (int) (x + length*Math.cos(n*Math.PI));
       endy = (int) (y + length*Math.sin(n*Math.PI));
       g.setColor(Color.red);
       //加粗红线
       g.drawLine(x-1,y,endx-1,endy);
       g.drawLine(x,y,endx,endy);
       g.drawLine(x+1,y,endx+1,endy);
       //让钩爪中间位置 放在红线顶点
       g.drawImage(hook,endx-36,endy-2,null);
   }

void paintSelf(Graphics g){

logic();
       //线的状态
       switch (state){
           case 0:
               if(n<0.1){
                   dir = 1;
               }else if(n>0.9){
                   dir = -1;
               }
               n = n + 0.005*dir;
               lines(g);
               break;
           case 1:
               //线的长度给一个范围
               if(length<MAX_length){
                   //状态为1 即鼠标左键 长度变化
                   length = length+5;
                   lines(g);
               }else {
                   state = 2;
               }

break;

case 2:
               //收回线长变短
               if(length>MIN_length){
                   //状态为1 即鼠标左键 长度变化
                   length = length-5;
                   lines(g);
               }else {
                   state = 0;
               }
               break;
           case 3:
               int m=1;
               //让红线返回
               if(length>MIN_length){
                   length = length-5;
                   lines(g);

for (Object obj:this.frame.objectList){
                       //判断能否移动
                       if (obj.flag){
                           m=obj.m;
                           obj.x = endx-obj.getWidth()/2;
                           obj.y = endy;
                           if (length<=MIN_length){
                               obj.x=-150;
                               obj.y=-150;
                               obj.flag=false;
                               Bg.waterFlag=false;
                               //加分
                               Bg.count+=obj.count;
                               state = 0;
                           }
                           //抓取时判断是否使用药水
                           if (Bg.waterFlag){
                               if (obj.type==1){//如果抓到的是金块
                                   m=1;
                               }
                               if (obj.type==2){//如果抓到的是石块
                                   obj.x=-150;
                                   obj.y=-150;
                                   obj.flag=false;
                                   Bg.waterFlag=false;
                                   state = 2;
                               }
                           }
                       }

}

}
               try {
                   Thread.sleep(m);
               } catch (InterruptedException e) {
                   e.printStackTrace();
               }
               break;

default:
       }

}
   //重置线元素
   void reGame(){
       n=0;
       length=100;
   }
}

来源:https://juejin.cn/post/7068239869213933604

标签:Java,黄金矿工,游戏
0
投稿

猜你喜欢

  • MyBatis-Plus多表联查的实现方法(动态查询和静态查询)

    2023-11-23 22:26:45
  • Mybatis延迟加载和缓存深入讲解

    2022-06-02 15:50:43
  • Tomcat 实现WebSocket详细介绍

    2023-08-12 21:22:11
  • JAVA ArrayList详细介绍(示例)

    2023-02-18 22:30:56
  • Mybatis 动态SQL的几种实现方法

    2023-11-10 12:15:15
  • Java常用内置注解用法分析

    2023-11-24 04:53:46
  • ZooKeeper入门教程一简介与核心概念

    2022-11-24 18:36:00
  • Java中两种基本的输入方式小结

    2023-02-06 18:37:24
  • java 同步、异步、阻塞和非阻塞分析

    2022-08-09 03:02:42
  • java金钱处理方法实例详解

    2023-05-29 10:38:29
  • C#将制定目录文件名转换成大写的方法

    2022-10-03 19:46:36
  • 关于java 图形验证码的解决方法

    2023-08-09 15:21:19
  • RocketMQ生产者调用start发送消息原理示例

    2022-07-05 20:13:04
  • SpringMVC源码解读之 HandlerMapping - AbstractDetectingUrlHandlerMapping系列初始化

    2023-02-12 16:14:21
  • Java Swing中JDialog实现用户登陆UI示例

    2021-10-12 13:58:00
  • OpenCV画任意圆弧曲线

    2023-06-22 19:28:44
  • MyBatis SpringMVC整合实现步骤详解

    2023-02-02 20:33:07
  • Spring MVC4.1服务器端推送实现过程解析

    2021-07-24 14:53:16
  • Java中的匿名内部类小结

    2021-05-29 06:29:38
  • SpringMVC入门实例

    2023-02-04 12:43:48
  • asp之家 软件编程 m.aspxhome.com