栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

GUI贪吃蛇

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

GUI贪吃蛇

1.步骤顺序 1.1先准备好图片素材

背景图、蛇头、舍身、食物这几张图片;






1.2.设置游戏面板的基本属性
package snake;

import javax.swing.*;
import javax.swing.plaf.PanelUI;
import java.awt.*;

//游戏的面板
public class GamePanel extends JPanel {


    //定义蛇的数据结构
    int length;//蛇的长度
    int[] snakeX=new int[600];//蛇的坐标25*25
    int[] snakeY=new int[500];//蛇的坐标25*25

    //构造器
    public GamePanel(){
       init();
    }

    //初始化方法
    public void init(){
        length=3;
        snakeX[0]=100;snakeY[0]=100;//脑袋的坐标
        snakeX[1]=75;snakeY[1]=100;//第一个身体的坐标
        snakeX[2]=50;snakeY[2]=100;//第二个身体的坐标

    }





    //游戏中的所有画面都使用绘制面板进行制作
    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        //绘制静态的面板
        this.setBackground(Color.WHITE);
         Date.header.paintIcon(this,g,10,15);//当前这个画笔,g这个监听事件,25,11的位置,当前第一张的背景
        g.fillRect(25,75,500,500);//头部的画板的位置、大小

        //把小蛇画上去
        Date.right.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        Date.body.paintIcon(this,g,snakeX[1],snakeY[1]);
        Date.body.paintIcon(this,g,snakeX[2],snakeY[2]);


    }
}

1.3设置好游戏开始页面的属性
package snake;

import lesson04.JframeDemo;

import javax.swing.*;

//主游戏的启动类
public class StartGame {
    public static void main(String[] args) {
        Jframe jframe = new Jframe();
        jframe.add(new GamePanel());

        jframe.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        jframe.setVisible(true);
        jframe.setBounds(10,10,800,450);
        //jframe.setResizable(false);//设置成界面不能重新设置



    }
}

1.4设置一个数据存放中心(图片等等)
package snake;

import javax.swing.*;
import java.net.URL;

//数据中心
public class Date {
    //相对路径  tx.jpg
    //绝对路径  /    相当于当前的项目
    //头部图标
    public static URL headerURL=Date.class.getResource("static/header.png");
    public static ImageIcon header=new ImageIcon(headerURL);
    //上图标
    public static URL upURL=Date.class.getResource("static/up.png");
    public static ImageIcon up=new ImageIcon(upURL);
    //下图标
    public static URL downURL=Date.class.getResource("static/down.png");
    public static ImageIcon down=new ImageIcon(downURL);
    //左图标
    public static URL leftURL=Date.class.getResource("static/left.png");
    public static ImageIcon left=new ImageIcon(leftURL);
    //右图标
    public static URL rightURL=Date.class.getResource("static/right.png");
    public static ImageIcon right=new ImageIcon(rightURL);
    //身体
    public static URL bodyURL=Date.class.getResource("static/body1.png");
    public static ImageIcon body=new ImageIcon(bodyURL);
    //食物
    public static URL dianURL=Date.class.getResource("static/dian.png");
    public static ImageIcon dian=new ImageIcon(dianURL);
}

1.5在游戏面板设置监听事件设置开始蛇头的方向

设置一组数组,初始化蛇的身体位置,然后在画板监听事件里面调用Date数据,把xy轴上相对应的位置画上相应的图片图标,就会有蛇身出现

package snake;

import javax.swing.*;
import javax.swing.plaf.PanelUI;
import java.awt.*;

//游戏的面板
public class GamePanel extends JPanel {


    //定义蛇的数据结构
    int length;//蛇的长度
    int[] snakeX=new int[600];//蛇的坐标25*25
    int[] snakeY=new int[500];//蛇的坐标25*25
    String fx;//初始方向向右


    //初始化方法
    public void init(){
        length=3;
      snakeX[0]=100;snakeY[0]=100;//脑袋的坐标
       snakeX[1]=75;snakeY[1]=100;//第一个身体的坐标
        snakeX[2]=50;snakeY[2]=100;//第二个身体的坐标
        fx="R";//初始方向向右
    }

    //构造器
    public GamePanel(){
        init();
    }


    //游戏中的所有画面都使用绘制面板进行制作
    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        //绘制静态的面板
        this.setBackground(Color.WHITE);
         Date.header.paintIcon(this,g,10,15);//当前这个画笔,g这个监听事件,25,11的位置,当前第一张的背景
        g.fillRect(25,75,500,500);//头部的画板的位置、大小
        //把小蛇画上去
        if (fx.equals("R")){
            Date.right.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("U")){
            Date.up.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("D")){
            Date.down.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("L")){
            Date.left.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }

      




    }
}

在游戏面板设置定时器,让蛇身动起来

设置一个timer,然后设置刷新频率

 Timer timer=new Timer(100,this);

构造器中添加timer的开始

        timer.start();//游戏一开始定时器就启动

重写事件监听

  //事件监听,需要通过特定的时间监听
    @Override
    public void actionPerformed(ActionEvent e) {
        if (isStart){               //如果是开始状态就让小蛇动起来
            for (int i = length-1; i >0; i--) {
                snakeX[i]=snakeX[i-1];//后一节移向前一节
                snakeY[i]=snakeY[i-1];
            }
            //身体走向
            if (fx.equals("R")){
                snakeX[0]=snakeX[0]+25;        //这里有一点不理解
                if (snakeX[0]>1000){snakeX[0]=25;}  //边界判断
            }
            else if (fx.equals("L")){
                snakeX[0]=snakeX[0]-25;
                if (snakeX[0]<25){snakeX[0]=1000;}  //边界判断
            }
            else if (fx.equals("U")){
                snakeY[0]=snakeY[0]-25;
                if (snakeY[0]<25){snakeY[0]=800;}  //边界判断
            }
            else if (fx.equals("D")){
                snakeY[0]=snakeY[0]+25;
                if (snakeY[0]>800){snakeY[0]=25;}  //边界判断
            }
            repaint();
        }
        timer.start();
    }

游戏面板总的代码:

package snake;

import javax.swing.*;
import javax.swing.plaf.PanelUI;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;

//游戏的面板

public class GamePanel extends JPanel implements KeyListener, ActionListener {//直接在这里继承借口就可以在内部类里面实现键盘监听
    //定义蛇的数据结构
    int length;//蛇的长度
    int[] snakeX=new int[600];//蛇的坐标25*25
    int[] snakeY=new int[500];//蛇的坐标25*25
    String fx;//初始方向向右
    //游戏开始的状态、停止的状态
    boolean isStart=false;//游戏默认是不开始
    //定时器,以毫秒为单位,1000ms=1s
    Timer timer=new Timer(100,this);//以毫秒为单位,100毫秒一次


    //初始化方法
    public void init(){
        length=3;
      snakeX[0]=100;snakeY[0]=100;//脑袋的坐标
       snakeX[1]=75;snakeY[1]=100;//第一个身体的坐标
        snakeX[2]=50;snakeY[2]=100;//第二个身体的坐标
        fx="R";//初始方向向右
    }
    
    //构造器
    public GamePanel(){
        init();
        //获得焦点和键盘事件
        this.setFocusable(true);//获得焦点事件
        this.addKeyListener(this);
        timer.start();//游戏一开始定时器就启动
    }


    //游戏中的所有画面都使用绘制面板进行制作
    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        //初始静态的面板
        this.setBackground(Color.WHITE);
        //Date.header.paintIcon(this,g,10,15);//当前这个画笔,g这个监听事件,25,11的位置,当前第一张的背景
        //g.fillRect(25,75,1000,800 );//头部的画板的位置、大小
        //开始的时候蛇头的位置
        if (fx.equals("R")){
            Date.right.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("U")){
            Date.up.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("D")){
            Date.down.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("L")){
            Date.left.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }
     //游戏刚开始的时候调用的Date数据画出的蛇身
        for (int i = 1; i < length; i++) {
            Date.body.paintIcon(this,g,snakeX[i],snakeY[i]);
        }


        //请你开始游戏吧~文字监听,写上
        if (isStart==false){ //这里是判断,所以一定要写成“==”才可以,刚刚就是没注意到,找了半天bug,快崩了~
            g.setColor(Color.black);//颜色的大小写偶可以
            g.setFont(new Font("微软雅黑",Font.BOLD,40));//设置出来的字体
            g.drawString("请你开始游戏吧",350,400);//监听事件监听出来的文字字符串
        }
    }
    //键盘监听事件
    @Override
    public void keyTyped(KeyEvent e) {

    }


    //我们用的键盘监听是这个
    @Override
    public void keyPressed(KeyEvent e) {
        int keyCode = e.getKeyCode();//获得键盘按钮监听
        if(keyCode==KeyEvent.VK_SPACE){//如果按下的是空格键
             isStart=!isStart;
             repaint();
        }
        if (keyCode==KeyEvent.VK_UP){
                fx="U";
        }else if (keyCode==KeyEvent.VK_DOWN){
            fx="D";
        }else if (keyCode==KeyEvent.VK_LEFT){
            fx="L";
        }else if (keyCode==KeyEvent.VK_RIGHT){
            fx="R";
        }

    }



    @Override
    public void keyReleased(KeyEvent e) {

    }
    //事件监听,需要通过特定的时间监听
    @Override
    public void actionPerformed(ActionEvent e) {
        if (isStart){               //如果是开始状态就让小蛇动起来
            for (int i = length-1; i >0; i--) {
                snakeX[i]=snakeX[i-1];//后一节移向前一节
                snakeY[i]=snakeY[i-1];
            }
            //身体走向
            if (fx.equals("R")){
                snakeX[0]=snakeX[0]+25;        //这里有一点不理解
                if (snakeX[0]>1000){snakeX[0]=25;}  //边界判断
            }
            else if (fx.equals("L")){
                snakeX[0]=snakeX[0]-25;
                if (snakeX[0]<25){snakeX[0]=1000;}  //边界判断
            }
            else if (fx.equals("U")){
                snakeY[0]=snakeY[0]-25;
                if (snakeY[0]<25){snakeY[0]=800;}  //边界判断
            }
            else if (fx.equals("D")){
                snakeY[0]=snakeY[0]+25;
                if (snakeY[0]>=800){snakeY[0]=25;}  //边界判断
            }
            repaint();
        }
        timer.start();
    }
}

//键盘监听器
1.6设施随机食物

先在游戏面板里面定义

 int foodx;
    int foody;
    Random random=new Random();//随机

//初始化食物,34表示格子,把食物随机分布在屏幕上

        foodx=25+25*random.nextInt(34);
        foody=25+25*random.nextInt(24);

在重写的事件监听里面添加吃食物的过程

   if (snakeX[0]==foodx&&snakeY[0]==foody){
                length++;//吃到食物以后,长度+1
                foodx=25+25*random.nextInt(34);//吃完以后再次随机
                foody=25+25*random.nextInt(24);
            }
1.7失败判定
    boolean isFail=false;//游戏正确状态
  //吃食物
            if (snakeX[0]==foodx&&snakeY[0]==foody){
                //分数加1
                score+=1;  //失败了以后自动就回到init()直接分数就变成0了
                length++;//吃到食物以后,长度+1
                foodx=25+25*random.nextInt(34);//吃完以后再次随机
                foody=25+25*random.nextInt(24);

            }
     //失败判定:撞到自己就算失败
            for (int i = 1; i < length; i++) {
                    if (snakeX[0]==snakeX[i]&&snakeY[0]==snakeY[i]){
                        isFail=true;
                    }
            }
2总代码 2.1StartGame.java
package snake;

import lesson04.JframeDemo;

import javax.swing.*;

//主游戏的启动类
public class StartGame {
    public static void main(String[] args) {
        Jframe jframe = new Jframe();
        jframe.add(new GamePanel());

        jframe.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
        jframe.setVisible(true);
        jframe.setBounds(10,10,1000,800);
        //jframe.setResizable(false);//设置成界面不能重新设置



    }
}

2.2Date.java
package snake;

import javax.swing.*;
import java.net.URL;

//数据中心
public class Date {
    //相对路径  tx.jpg
    //绝对路径  /    相当于当前的项目
    //头部图标
    public static URL headerURL=Date.class.getResource("static/header.png");
    public static ImageIcon header=new ImageIcon(headerURL);
    //上图标
    public static URL upURL=Date.class.getResource("static/up.png");
    public static ImageIcon up=new ImageIcon(upURL);
    //下图标
    public static URL downURL=Date.class.getResource("static/down.png");
    public static ImageIcon down=new ImageIcon(downURL);
    //左图标
    public static URL leftURL=Date.class.getResource("static/left.png");
    public static ImageIcon left=new ImageIcon(leftURL);
    //右图标
    public static URL rightURL=Date.class.getResource("static/right.png");
    public static ImageIcon right=new ImageIcon(rightURL);
    //身体
    public static URL bodyURL=Date.class.getResource("static/body1.png");
    public static ImageIcon body=new ImageIcon(bodyURL);
    //食物
    public static URL dianURL=Date.class.getResource("static/dian.png");
    public static ImageIcon dian=new ImageIcon(dianURL);




}

2.3GamePanel.java
package snake;

import javax.swing.*;
import javax.swing.plaf.PanelUI;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.Random;

//游戏的面板

public class GamePanel extends JPanel implements KeyListener, ActionListener {//直接在这里继承借口就可以在内部类里面实现键盘监听
    //定义蛇的数据结构
    int length;//蛇的长度
    int[] snakeX=new int[600];//蛇的坐标25*25
    int[] snakeY=new int[500];//蛇的坐标25*25
    String fx;//初始方向向右
    //游戏开始的状态、停止的状态
    boolean isStart=false;//游戏默认是不开始
    boolean isFail=false;//游戏正确状态
    //定时器,以毫秒为单位,1000ms=1s
    Timer timer=new Timer(100,this);//以毫秒为单位,100毫秒一次
    //食物的坐标
    int foodx;
    int foody;
    Random random=new Random();
    int score;

    //初始化方法
    public void init(){
        length=3;
      snakeX[0]=100;snakeY[0]=100;//脑袋的坐标
       snakeX[1]=75;snakeY[1]=100;//第一个身体的坐标
        snakeX[2]=50;snakeY[2]=100;//第二个身体的坐标
        fx="R";//初始方向向右
        //初始化食物,34表示格子,把食物随机分布在屏幕上
        foodx=25+25*random.nextInt(34);
        foody=25+25*random.nextInt(24);

        score = 0;
    }

    //构造器
    public GamePanel(){
        init();
        //获得焦点和键盘事件
        this.setFocusable(true);//获得焦点事件
        this.addKeyListener(this);
        timer.start();//游戏一开始定时器就启动
    }





    //游戏中的所有画面都使用绘制面板进行制作
    @Override
    protected void paintComponent(Graphics g) {
        super.paintComponent(g);
        //初始静态的面板
        this.setBackground(Color.WHITE);
        //Date.header.paintIcon(this,g,10,15);//当前这个画笔,g这个监听事件,25,11的位置,当前第一张的背景
        //g.fillRect(25,75,1000,800 );//头部的画板的位置、大小
        Date.dian.paintIcon(this,g,foodx,foody);//画食物
        //开始的时候蛇头的位置
        if (fx.equals("R")){
            Date.right.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("U")){
            Date.up.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("D")){
            Date.down.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }else  if (fx.equals("L")){
            Date.left.paintIcon(this,g,snakeX[0],snakeY[0]);//蛇头初始化向右
        }

        for (int i = 1; i < length; i++) {                      //游戏刚开始的时候调用的Date数据画出的蛇身
            Date.body.paintIcon(this,g,snakeX[i],snakeY[i]);
        }


        //请你开始游戏吧~文字监听,写上
        if (isStart==false){ //这里是判断,所以一定要写成“==”才可以,刚刚就是没注意到,找了半天bug,快崩了~
            g.setColor(Color.black);//颜色的大小写偶可以
            g.setFont(new Font("微软雅黑",Font.BOLD,40));//设置出来的字体
            g.drawString("请你开始游戏吧",350,400);//监听事件监听出来的文字字符串
        }
        if (isFail){
            g.setColor(Color.red);//颜色的大小写偶可以
            g.setFont(new Font("微软雅黑",Font.BOLD,40));//设置出来的字体
            g.drawString("小可爱你输了哦~",350,400);//监听事件监听出来的文字字符串
        }

        //画积分
        g.setColor(Color.red);//颜色的大小写偶可以
        g.setFont(new Font("微软雅黑",Font.BOLD,18));//设置出来的字体
        g.drawString("长度"+score,750,35);//监听事件监听出来的文字字符串
        g.drawString("分数"+score,750,50);//监听事件监听出来的文字字符串


    }
    //键盘监听事件
    @Override
    public void keyTyped(KeyEvent e) {

    }


    //我们用的键盘监听是这个
    @Override
    public void keyPressed(KeyEvent e) {
        int keyCode = e.getKeyCode();//获得键盘按钮监听
        if(keyCode==KeyEvent.VK_SPACE){//如果按下的是空格键
            //判断游戏是否重新开始
            if (isFail) {
                isFail = false;
                init();//在这里游戏重新开始
            }else{
                isStart=!isStart;
            }
        }
        if (keyCode==KeyEvent.VK_UP){
                fx="U";
        }else if (keyCode==KeyEvent.VK_DOWN){
            fx="D";
        }else if (keyCode==KeyEvent.VK_LEFT){
            fx="L";
        }else if (keyCode==KeyEvent.VK_RIGHT){
            fx="R";
        }

    }



    @Override
    public void keyReleased(KeyEvent e) {

    }
    //事件监听,需要通过特定的时间监听
    @Override
    public void actionPerformed(ActionEvent e) {
        if (isStart&&isFail==false){               //如果是开始状态就让小蛇动起来

            //吃食物
            if (snakeX[0]==foodx&&snakeY[0]==foody){
                //分数加1
                score+=1;  //失败了以后自动就回到init()直接分数就变成0了
                length++;//吃到食物以后,长度+1
                foodx=25+25*random.nextInt(34);//吃完以后再次随机
                foody=25+25*random.nextInt(24);

            }


            for (int i = length-1; i >0; i--) {
                snakeX[i]=snakeX[i-1];//后一节移向前一节
                snakeY[i]=snakeY[i-1];
            }
            //身体走向
            if (fx.equals("R")){
                snakeX[0]=snakeX[0]+25;        //这里有一点不理解
                if (snakeX[0]>1000){snakeX[0]=25;}  //边界判断
            }
            else if (fx.equals("L")){
                snakeX[0]=snakeX[0]-25;
                if (snakeX[0]<25){snakeX[0]=1000;}  //边界判断
            }
            else if (fx.equals("U")){
                snakeY[0]=snakeY[0]-25;
                if (snakeY[0]<25){snakeY[0]=800;}  //边界判断
            }
            else if (fx.equals("D")){
                snakeY[0]=snakeY[0]+25;
                if (snakeY[0]>=800){snakeY[0]=25;}  //边界判断
            }
            //失败判定:撞到自己就算失败
            for (int i = 1; i < length; i++) {
                    if (snakeX[0]==snakeX[i]&&snakeY[0]==snakeY[i]){
                        isFail=true;
                    }
            }
            repaint();
        }
        timer.start();
    }
}

//键盘监听器


2.3补充:

1.数据Date包要创建一个放在snake目录下
2.自己界面需要优化的自己可以设置好监听事件等等
例如:吃完一个食物越来越快,碰到自己以后会爆炸等等

代码能完全无误运行,就是有需要改进,拿走不谢~

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/694765.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号