zoukankan      html  css  js  c++  java
  • Java学习(8):贪吃蛇游戏

    根据视频编写的贪吃蛇游戏

    主方法

    public class Start {
    
        public static void main(String[] args) {
            new Yard().launch();
        }
    }
    import java.awt.Color;
    import java.awt.Font;
    import java.awt.Frame;
    import java.awt.Graphics;
    import java.awt.Image;
    import java.awt.Panel;
    import java.awt.event.KeyAdapter;
    import java.awt.event.KeyEvent;
    import java.awt.event.WindowAdapter;
    import java.awt.event.WindowEvent;
    
    /**
     *
     * @author xcx
     * @time 2017年7月28日下午3:44:48
     */
    public class Yard extends Frame {
        //设置游戏结束字体
        Font goFont = new Font("宋体",Font.ITALIC|Font.BOLD,50);
        //游戏开始的线程
        PaintThread paintThread = new PaintThread();
        //游戏得分
        public static int score = 0;
        //判断蛇是否死掉
        private static boolean flag = true;
        //行数与列数
        public static final int ROWS = 30;
        public static final int COLS = 30;
        // 每个格子的边长
        public static final int BLOCK_SIZE = 15;
    
        //定义一条蛇,一个蛋
        Snake s = new Snake();
        Egg e = new Egg();
    
        // 加入双缓冲
        Image offScreenImage = null;
    
        public void launch() {
            setLayout(null);
            setLocation(200, 200);
            setSize(COLS * BLOCK_SIZE, ROWS * BLOCK_SIZE);
            setVisible(true);
            addWindowListener(new WindowAdapter() {
                @Override
                public void windowClosing(WindowEvent arg0) {
                    setVisible(true);
                    System.exit(0);
                }
            });
    
            // 添加键盘控制事件
            addKeyListener(new KeyMonitor());
            // 运行线程
            paintThread.start();
    
        }
    
        @Override
        public void paint(Graphics g) {
            // 保存画笔额颜色
            Color color = g.getColor();
            // 设置画笔的颜色
            g.setColor(Color.gray);
            g.fillRect(0, 0, COLS * BLOCK_SIZE, ROWS * BLOCK_SIZE);
            g.setColor(Color.DARK_GRAY);
            // 画出横线
            for (int i = 0; i < ROWS; i++) {
                g.drawLine(0, BLOCK_SIZE * i, BLOCK_SIZE * COLS, BLOCK_SIZE * i);
            }
            // 画出竖线
            for (int i = 0; i < ROWS; i++) {
                g.drawLine(BLOCK_SIZE * i, 0, BLOCK_SIZE * i, BLOCK_SIZE * ROWS);
            }
            g.setColor(Color.yellow);
            g.drawString("score"+score, 10, 60);
            if(flag == false){
                g.setFont(goFont);
                g.drawString("game over", 100, 180);
                paintThread.gameOver();
            }
            // 还原画笔的颜色
            g.setColor(color);
            s.eat(e);
            e.draw(g);
            s.draw(g);
            
        }
    
        @Override
        public void update(Graphics g) {
            if (offScreenImage == null) {
                offScreenImage = this.createImage(COLS * BLOCK_SIZE, ROWS
                        * BLOCK_SIZE);
            }
            Graphics gOff = offScreenImage.getGraphics();
            paint(gOff);
            g.drawImage(offScreenImage, 0, 0, null);
    
        }
    
        //停止
        public static void stop(){
            flag = false;
        }
        // 不断刷新界面
        private class PaintThread extends Thread {
            private boolean running = true;
            @Override
            public void run() {
                while (running) {
                    repaint();
                    try {
                        Thread.sleep(200);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }
            
            public void gameOver(){
                running = false;
            }
        }
    
        //键盘监听事件
        private class KeyMonitor extends KeyAdapter {
            @Override
            public void keyPressed(KeyEvent e) {
                s.keyPressed(e);
            }
        }
    }
    import java.awt.Color;
    import java.awt.Graphics;
    import java.awt.Rectangle;
    import java.awt.event.KeyEvent;
    
    /**
     *
     * @author xcx
     * @time 2017年7月28日下午3:45:03
     */
    public class Snake {
        // 蛇的头结点和尾结点
        private Node head = null;
        private Node tail = null;
        private int size = 0;
    
        // 自己定义一个头
        private Node node = new Node(20, 30, Dir.L);
    
        public Snake() {
            head = node;
            tail = node;
            size = 1;
        }
    
        // 将一个结点添加到尾巴上
        public void addToTail() {
            Node node = null;
            switch (tail.dir) {
            case L:
                node = new Node(tail.row, tail.col + 1, tail.dir);
                break;
    
            case R:
                node = new Node(tail.row, tail.col - 1, tail.dir);
                break;
    
            case U:
                node = new Node(tail.row + 1, tail.col, tail.dir);
                break;
    
            case D:
                node = new Node(tail.row - 1, tail.col, tail.dir);
                break;
            }
            tail.next = node;
            node.prev = tail;
            tail = node;
            size++;
        }
    
        // 将一个结点添加到头上
        public void addToHead() {
            Node node = null;
            switch (head.dir) {
            case L:
                node = new Node(head.row, head.col - 1, head.dir);
                break;
    
            case R:
                node = new Node(head.row, head.col + 1, head.dir);
                break;
    
            case U:
                node = new Node(head.row - 1, head.col, head.dir);
                break;
    
            case D:
                node = new Node(head.row + 1, head.col, head.dir);
                break;
            }
            node.next = head;
            head.prev = node;
            head = node;
            size++;
        }
    
        // 从蛇的尾巴删除一个结点
        private void deleteFromTail() {
            if (size == 0)
                return;
            tail = tail.prev;
            tail.next = null;
    
        }
    
        // 将蛇画出
        public void draw(Graphics g) {
            if (size <= 0)
                return;
            move();
            for (Node node = head; node != null; node = node.next) {
                node.draw(g);
            }
        }
    
        // 蛇移动一下
        private void move() {
            addToHead();
            deleteFromTail();
            checkDead();
        }
    
        // 检查蛇是否死掉
        private void checkDead() {
            // 判断蛇是否撞在了墙上
            if (head.row < 0 || head.row > Yard.ROWS || head.col < 0
                    || head.col > Yard.COLS) {
                Yard.stop();
            }
            // 判断蛇是否撞在了自己的身上
            for (Node node = head.next; node != null; node = node.next) {
                if (this.getRect().intersects(node.getRect())) {
                    Yard.stop();
                }
            }
        }
    
        // 键盘按下后蛇头方向改变
        public void keyPressed(KeyEvent e) {
            int key = e.getKeyCode();
            switch (key) {
            case KeyEvent.VK_LEFT:
                if (head.dir != Dir.R)
                    head.dir = Dir.L;
                break;
            case KeyEvent.VK_RIGHT:
                if (head.dir != Dir.L)
                    head.dir = Dir.R;
                break;
            case KeyEvent.VK_UP:
                if (head.dir != Dir.D)
                    head.dir = Dir.U;
                break;
            case KeyEvent.VK_DOWN:
                if (head.dir != Dir.U)
                    head.dir = Dir.D;
                break;
            }
        }
    
        // 蛇吃蛋
        public void eat(Egg e) {
            if (this.getRect().intersects(e.getRect())) {
                e.reAppear();
                addToTail();
                Yard.score += 5;
            }
        }
    
        // 判断蛇头所在的格子
        private Rectangle getRect() {
            return new Rectangle(Yard.BLOCK_SIZE * head.col, Yard.BLOCK_SIZE
                    * head.row, head.w, head.h);
        }
    
        // 定义结点内部类
        private class Node {
            // 结点的高度与宽度
            int w = Yard.BLOCK_SIZE;
            int h = Yard.BLOCK_SIZE;
            // 所在的位置
            int row, col;
            // 结点的方向
            Dir dir = Dir.L;
            // 后一个结点
            Node next = null;
            // 前一个结点
            Node prev = null;
    
            Node(int row, int col, Dir dir) {
                this.row = row;
                this.col = col;
                this.dir = dir;
            }
    
            void draw(Graphics g) {
                Color color = g.getColor();
                g.setColor(Color.black);
                g.fillRect(Yard.BLOCK_SIZE * col, Yard.BLOCK_SIZE * row, w, h);
                g.setColor(color);
            }
    
            // 判断节点所在的格子
            private Rectangle getRect() {
                return new Rectangle(Yard.BLOCK_SIZE * col, Yard.BLOCK_SIZE * row,
                        w, h);
            }
        }
    }
    import java.awt.Color;
    import java.awt.Graphics;
    import java.awt.Rectangle;
    import java.util.Random;
    
    /**
     *
     * @author xcx
     * @time 2017年7月28日下午3:45:11
     */
    public class Egg {
        // 设置蛋的颜色
        Color color = Color.green;
        // 出现的坐标
        private int row, col;
        // 蛋的高与宽
        private int w = Yard.BLOCK_SIZE;
        private int h = Yard.BLOCK_SIZE;
    
        private static Random r = new Random();
    
        public Egg(int x, int y) {
            this.row = x;
            this.col = y;
        }
    
        public Egg() {
            this(r.nextInt(Yard.ROWS), r.nextInt(Yard.COLS));
    
        }
    
        public void reAppear() {        
            this.row = r.nextInt(Yard.ROWS) ;
            this.col = r.nextInt(Yard.COLS) ;
    
        }
    
        // 画出一个蛋
        public void draw(Graphics g) {
            Color c = g.getColor();
            g.setColor(color);
            g.fillOval(Yard.BLOCK_SIZE * row, Yard.BLOCK_SIZE * col, w, h);
            g.setColor(c);
            if (color == Color.green) {
                color = Color.red;
            } else {
                color = Color.green;
            }
        }
    
        // 得到蛋所在的格子
        public Rectangle getRect() {
            return new Rectangle(Yard.BLOCK_SIZE * row, Yard.BLOCK_SIZE * col, w, h);
        }
    }
    /**
     *
     *@author xcx 
     *@time 2017年7月28日下午4:14:38
     */
    public enum Dir {
        L,R,U,D
    
    }
  • 相关阅读:
    No-3.Linux 终端命令格式
    No-2.常用 Linux 命令的基本使用
    No-1.文件和目录
    No-7.运算符
    No-6.If语句
    No-5.变量的命名
    YOLOv4详细分析 | 细数当前最佳检测框架小细节(附论文及源码下载)
    案例】S7-200SMART 实时时钟如何在MCGS触摸屏上显示并写入
    卡尔曼滤波:从入门到精通
    mmdetection最小复刻版(七):anchor-base和anchor-free差异分析
  • 原文地址:https://www.cnblogs.com/xcxfuryit/p/7256170.html
Copyright © 2011-2022 走看看