• JAVA 多线程制作大球吃小球 一、实现球的自动生成及运动 生产消费模型


    前几天用多线程实现了创建小球并移动,想到大鱼吃小鱼,便突发奇想要写一个大球吃小球。首先第一步自然是先把界面弄好啦

     1 public class BallUI extends JPanel {
     2 
     3     private ArrayList<Ball> li = new ArrayList<Ball>();
     4 
     5     public static void main(String[] args) {
     6         BallUI bu = new BallUI();
     7         bu.UI();
     8     }
     9 
    10     public void UI() {
    11         JFrame jf = new JFrame();
    12         jf.setLocationRelativeTo(null);
    13         jf.setResizable(false);
    14         jf.setSize(700, 700);
    15         this.setSize(jf.getWidth(),jf.getHeight());
    16         jf.setTitle("大球吃小球");
    17 
    18         this.setPreferredSize(new Dimension(jf.getWidth(), jf.getHeight()));
    19         jf.add(this);
    20 
    21         
    22 
    23         jf.setVisible(true);
    24     }
    25     
    26 
    27 }

    界面写好后想想要怎么做呢?既然是大球吃小球还利用线程,那肯定需要一个队列,然后呢?既然要队列,那队列里存什么?肯定存小球啊,那自然要创建一个小球类了,那小球有什么属性呢?坐标、移动速度、大小、颜色,除了这些在创建时还需不需要传些什么参数呢?既然传了颜色,那肯定需要画小球,我们在哪画?是调用方法还是在线程中获取小球属性然后画?我觉得调用方法会更好,所以我们要在这里传入一个画布。同样在后面我们还需要检测小球是否碰撞,因此我们还需要传入一个队列。下面便是Ball类的构造了

    public class Ball {
        private int size;
        private int x;
        private int y;
        private int speedX;
        private int speedY;
        private Color c;
        private JPanel jf;
        private ArrayList<Ball> li;
    
        public Ball(int size, int x, int y, int speedX, int speedY, Color c, JPanel jf, ArrayList<Ball> li) {
            this.size = size;
            this.x = x;
            this.y = y;
            this.speedX = speedX;
            this.speedY = speedY;
            this.c = c;
            this.jf = jf;
            this.li = li;
        }
      //画球
        public void draw(Graphics g) {
        }
      //移动球
        public void move() {
        }
      //清除上次留下的痕迹
        public void clear(Graphics g) {
        }
      //碰撞检测
        public void crash(Graphics g) {
                    
        }
    }

    创建好小球类后,我们便需要线程来创建小球、改变小球,那这里也有一个问题,我们是用一个线程还是两个还是多个?这样看,如果只用一个线程,那么我们每次改变小球得在创建了一个小球后进行,如果小球数量少还没问题,但是当小球数量多了之后,每便利一次就会用上一段时间,那么肯定会有延时,所以我们需要把这里分成两个线程,一个线程创建小球,一个线程改变小球。这里其实就利用了生产者消费者模型: 生产者负责生产数据并存入缓冲区,消费者从缓冲区中取出数据并且处理并输出。

     1 public class ThreadBall extends Thread {
     2 
     3     private ArrayList<Ball> li;
     4     private JPanel jp;
     5     private Graphics g;
     6 
     7     public ThreadBall(ArrayList<Ball> li,JPanel jp) {
     8         this.li = li;
     9         this.jp=jp;
    10     }
    11 
    12     public void run() {
    13         g=jp.getGraphics();
    14         while(true) {
    15             for(int i=0;i<li.size();i++) {
    16                 Ball ball=li.get(i);
    17                 ball.clear(g);
    18                 ball.crash(g);
    19                 ball.move();
    20                 ball.draw(g);
    21             }
    22             try {
    23                 Thread.sleep(100);
    24             } catch (InterruptedException e) {
    25                 e.printStackTrace();
    26             }
    27         }
    28     }
    29     
    30 }
    public class BallLis extends Thread {
        private ArrayList<Ball> li = new ArrayList<Ball>();
        private JPanel jp;
    
        public BallLis(ArrayList<Ball> li,JPanel jp) {
            this.li = li;
            this.jp = jp;
        }
    
        public void run() {
            while (true) {
                int size = new Random().nextInt(30) + 10;
                int x = new Random().nextInt(jp.getWidth());
                int y = 0;
                int speedX = new Random().nextInt(10) + 10;
                int speedY = new Random().nextInt(10) + 5;
                Color c=new Color(new Random().nextInt(256),new Random().nextInt(256),new Random().nextInt(256));
                
                Ball bl=new Ball(size,x,y,speedX,speedY,c,jp,li);
                li.add(bl);
                
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                
            }
        }
    
    }

    创建好线程后肯定需要在BallUI类中创建对象啦

            BallLis ball = new BallLis(li,this);
            ball.start();
            ThreadBall tb=new ThreadBall(li,this);
            tb.start();

    那么,剩下的任务就是实现小球类中的方法了,就留给你们去实现了。

    注:代码已上传至github:https://github.com/leo6033/Java_Project

  • 相关阅读:
    观察者(Observer)模式
    Stragety Pattern(策略模式)
    数据库设计范式深入浅出
    建造者(Builder)模式
    吉杰,以及快乐男声
    言情小说通用情节[转]
    过年的任务
    将一家创业公司三年之内推动上市是1999年的思维方式
    修改系统时间格式?解决now()
    经济类吴晓波的《大败局》,韩德强的《碰撞》。几年前看的了,现在还很有印象。
  • 原文地址:https://www.cnblogs.com/csu-lmw/p/9314532.html
Copyright © 2020-2023  润新知