haslflafjl 2022-05-29 18:00 采纳率: 80%
浏览 103
已结题

java贪吃蛇游戏问题2

待解决疑问:
现在默认运行程序游戏直接开始,然后死亡后可以重新开始。有一个Menu类可以展示游戏欢迎界面,理想情况是:在欢迎界面按空格可以开始游戏,但是不知道如何实现。

程序入口

package Main;
public class Main extends GamePanel{
    public static void main(String[] args) {
        new GameFrame();
    }
}

创建游戏窗口

package Main;
import javax.swing.JFrame;
import javax.swing.JTextField;
public class GameFrame extends JFrame{
    public boolean menuclosed=false;
    JTextField text;

    GameFrame(){
        this.setTitle("Greedy Snake");
        this.setLocation(200,200);
        this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        this.setResizable(false);
        
        

        this.add(new GamePanel());
        this.pack();
        this.setVisible(true);

    }
}

在游戏窗口制作游戏内容

package Main;

import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.io.IOException;
import java.util.Random;

import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JPanel;
import javax.swing.Timer;

public class GamePanel extends JPanel implements ActionListener{

    static final int SCREEN_WIDTH=500;
    static final int SCREEN_HEIGHT=500;
    static final int UNIT_SIZE=20;
    static int GAME_GROUND=(SCREEN_WIDTH*SCREEN_HEIGHT)/UNIT_SIZE;
    static int DELAY=140;
    int x[]=new int[GAME_GROUND];
    int y[]=new int [GAME_GROUND];
    int snake=5;
    public int applesEaten;
    static int score;
    int appleX;
    int appleY;
    char direction='R';
    public boolean running=false;
    Timer timer;
    Random random;
    Image imgbox;
    
    GamePanel(){
        System.out.println("GamePanel");
        gameCreate();
    }
    private void gameCreate() {
        x=new int[GAME_GROUND];
        y=new int[GAME_GROUND];
        snake=5;
        applesEaten = 0;
        score=0;
        appleX = 0;
        appleY = 0;
        direction='R';
        running=false;
        this.setPreferredSize(new Dimension(SCREEN_WIDTH,SCREEN_HEIGHT));
        this.setFocusable(true);
        this.addKeyListener(new KAdapter());
        this.setBackground(Color.black);
        random=new Random();
        gameStart();
    }
    public void paintComponent(Graphics g) {
        super.paintComponent(g);
        draw(g);
    }
    
    public void draw(Graphics g) {
        if(running) {
            //Draw apple画苹果
            g.setColor(new Color(6,31,191));
            g.fillOval(appleX, appleY, UNIT_SIZE, UNIT_SIZE);
            
            //Draw Snake画出蛇
            for(int i=0;i<snake;i++) {
                //Head of Snake画出蛇头
                if(i==0) {
                    g.setColor(new Color(132,5,5));
                    g.fillRect(x[i], y[i], UNIT_SIZE, UNIT_SIZE);
                }
                //Body of Snake画出蛇身
                else {
                    g.setColor(Color.gray);
                    g.fillRect(x[i], y[i], UNIT_SIZE, UNIT_SIZE);
                }
            }
            scoreBoard(g);
        }
        else {
            gameEnd(g);//如果游戏还在运行就画,不然启动游戏结束界面
        }
    }
    
    public void gameStart() {
        running=true;
        createApple();
        if(timer==null) {
            timer=new Timer(DELAY,this);//重置timer,防止蛇死后重开再死再重开导致的速度越来越快
            timer.start();
        }
    }
    public void scoreBoard(Graphics g) {
        g.setColor(Color.gray);
        g.drawString("得分 "+score, 20, SCREEN_HEIGHT-g.getFont().getSize());
        g.drawString("吞噬的星球 "+applesEaten, 200, SCREEN_HEIGHT-g.getFont().getSize());
        g.drawString("坐标 "+x[0]+"|"+y[0], 300, SCREEN_HEIGHT-g.getFont().getSize());
    }
    
    
    public void createApple() {
        //Set apple random location
        appleX=random.nextInt((int)(SCREEN_WIDTH/UNIT_SIZE))*UNIT_SIZE;
        appleY=random.nextInt((int)(SCREEN_HEIGHT/UNIT_SIZE))*UNIT_SIZE;
    }
    
    public void checkApple() {
        //Make apple Edible
        if((x[0]==appleX)&&(y[0]==appleY)){
            snake++;
            applesEaten++;
            createApple();
        }
    }
    
    public void move() {
        for(int i=snake;i>0;i--) {
            x[i]=x[i-1];
            y[i]=y[i-1];
        }
        switch(direction) {
        case 'U':
            y[0]=y[0]-UNIT_SIZE;
            break;
        case 'D':
            y[0]=y[0]+UNIT_SIZE;
            break;
        case 'L':
            x[0]=x[0]-UNIT_SIZE;
            break;
        case 'R':
            x[0]=x[0]+UNIT_SIZE;
            break;
        }
    }
    
    public void checkCollision() {
        for(int i=snake;i>0;i--) {
            //Game end when head touching body
            if((x[0]==x[i])&&(y[0]==y[i])){
                running=false;
            }
            //Game end when head spanned the game field
            if((x[0]<0)||(x[0]>SCREEN_WIDTH)||(y[0]<0)||(y[0]>SCREEN_HEIGHT)) {
                running=false;
            }
        }
        
    }
    
    public void gameEnd(Graphics g) {
        this.setBackground(Color.darkGray);
        
        String speaker=null;
        if(applesEaten==0) {speaker=text[0];}
        if(applesEaten==2) {speaker=text[1];}
        if(applesEaten==5) {speaker=text[2];}
        if(applesEaten==12) {speaker=text[3];}
        if(applesEaten>200) {speaker=text[4];}
        else {speaker=text[7];}
        
        g.setColor(Color.lightGray);
        //"Greedy Snake"
        g.setFont(new Font("Impact",Font.PLAIN,50));
        g.drawString("Greedy Snake",SCREEN_WIDTH/4, g.getFont().getSize());
        //"Score - "
        g.setFont(new Font(null,Font.BOLD,25));
        g.drawString("Score - "+score,SCREEN_WIDTH/6, 100);
        //Other text
        g.setFont(new Font(null,Font.ROMAN_BASELINE,15));
        g.drawString("你吞噬了"+applesEaten+"个星球. "+speaker,SCREEN_WIDTH/6, 145);
        g.drawString("R-重新开始", SCREEN_WIDTH/6, 180);
        g.drawString("Esc-退出游戏", SCREEN_WIDTH/6,205);
        
        //Prevent timer
        if(timer!=null) {
            timer.stop();
            timer=null;
        }
    }
    
    @Override
    public void actionPerformed(ActionEvent e) {
        
        if(running) {move();checkApple();checkCollision();}
        repaint();
    }
    
    public class KAdapter extends KeyAdapter{
        @Override
        public void keyPressed(KeyEvent e) {
            switch(e.getKeyCode()) {
                case KeyEvent.VK_LEFT:
                    if(direction!='R') {
                        direction='L';
                    }
                    break;
                case KeyEvent.VK_RIGHT:
                    if(direction!='L') {
                        direction='R';
                    }
                    break;
                case KeyEvent.VK_UP:
                    if(direction!='D') {
                        direction='U';
                    }
                    break;
                case KeyEvent.VK_DOWN:
                    if(direction!='U') {
                        direction='D';
                    }
                    break;
                case KeyEvent.VK_R:
                    if(!running) {
                        gameCreate();
                    }
                case KeyEvent.VK_ESCAPE:
                    if(!running) {
                        System.exit(0);
                    }
            }
        }
    }

//结算界面台词
    final public String []text= {
            "(T_T)",
            "我们的地球和火星消失了.",
            "这些加起来或许比得上木星.",
            "相当于整个太阳系!",
            "你和黑洞有血缘关系?",
            "你啃腹自尽了.",
            "真是可笑至极...",
            "[返航中]"};
}

待解决,下面是游戏欢迎界面Menu,在GameFrame游戏窗口可以添加显示,跟着游戏界面指示“按space开始游戏”,GameFrame没法加载GamePanel游戏制作界面,我不知道为什么没法达成没法从欢迎界面进入游玩界面的效果。

package Main;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import javax.swing.JLabel;
import javax.swing.JPanel;

public class Menu extends JPanel implements ActionListener{
    static final int SCREEN_WIDTH=500;
    static final int SCREEN_HEIGHT=500;
    public JLabel title;
    public JLabel text1,text2;
    public boolean menuenable=true;//用来表示欢迎页面是否展示,默认展示
    public int operator;
    
    Menu(){
        
        if(menuenable) {
            System.out.println("Menu");
            this.setPreferredSize(new Dimension(SCREEN_WIDTH,SCREEN_HEIGHT));
            this.setBackground(Color.black);
            this.addKeyListener(new KAdapter());
            this.setFocusable(true);
            
            title=new JLabel("Greddy Snake");
            title.setFont(new Font("Impact",Font.BOLD,50));
            title.setForeground(Color.white);
            
            this.add(title);
        }
    }
    public void paintComponent(Graphics g) {
        super.paintComponent(g);
        draw(g);
    }
    public void draw(Graphics g) {//画游戏提示语和logo
        if(menuenable) {
            g.setColor(Color.gray);
            g.setFont(new Font(null,Font.ROMAN_BASELINE,20));
            g.drawString("Space - start game",20,SCREEN_HEIGHT-g.getFont().getSize());
            
            Toolkit tool=this.getToolkit();
            Image logoimg=tool.getImage("LOGO.png");
            g.drawImage(logoimg,90,90,(logoimg.getWidth(this))*3,(logoimg.getHeight(this))*3,this);
        }
    }

    @Override
    public void actionPerformed(ActionEvent e) {
        
    }
    public class KAdapter extends KeyAdapter{
    @Override
    //按空格开始游戏,按K更改难度。(暂时不配置K)
        public void keyPressed(KeyEvent k) {
            if(menuenable) {
                switch(k.getKeyCode()) {
                case KeyEvent.VK_SPACE:
                    System.out.println("spcace");
                    menuenable=false;
                    break;
                case KeyEvent.VK_F:
                    System.out.println("f");
                    menuenable=false;
                    break;
                }
            }

        }
    }
}
  • 写回答

1条回答 默认 最新

  • 太空眼睛 Java领域新星创作者 2022-05-29 18:16
    关注

    我可以实现,一行一行源代码断点调试,终于解决了你的问题!

    img

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论 编辑记录

报告相同问题?

问题事件

  • 系统已结题 6月7日
  • 已采纳回答 5月30日
  • 赞助了问题酬金10元 5月30日
  • 创建了问题 5月29日

悬赏问题

  • ¥15 关于#Mybatis#的问题:怎么办重复数据如下"KSDM":37,"KSMC":"呼吸内科门诊","ksdm":37,"ksmc":"呼吸内科门诊"xml文件填写
  • ¥40 servlet的web程序部署出错
  • ¥50 activiti 新建流程系列问题
  • ¥50 为什么我版本升级之后运行速度变慢5倍??
  • ¥15 如何在gazebo中加载机械臂和机械手
  • ¥15 纯运放实现隔离采样方案设计
  • ¥20 easyconnect无法连接后缀带.com的网站,一直显示找不到服务器ip地址,但是带有数字的网站又是可以连接上的,如何解决
  • ¥15 电脑开机过商标后就直接这样,求解各位
  • ¥15 mysql , 用自己创建的本地主机和用户名 登录不上
  • ¥15 关于#web项目#的问题,请各位专家解答!