java游戏开发杂谈 - 实现游戏主菜单
经常玩游戏的同学,大家都知道,游戏都会有个主菜单,里面有多个菜单选项:开始游戏、游戏设置、关于游戏、退出游戏等等,这个菜单是怎么实现的呢。
有一定桌面软件开发基础的同学可能会想到,用JButton组件就可以实现,每个选项就是一个按钮嘛。 嗯,这样做是可以的。但是,系统自带的JButton按钮,样式是已经定义好的,虽然可以设置它的颜色、背景等属性,但终归是受限制的。
我们既然是学习游戏开发,那么时刻要记住台哥在之前的一个章节里所讲的,游戏里所有的东西都是计算机画出来的,程序员的工作就是,控制计算机在什么时间,画什么东西。
那么我们现在,就用这种思路,借用画笔API来实现一个游戏主菜单。 相信大家真正领悟了以后,会对GUI有了更深入的了解,你会明白,噢,原来我们用的JButton等组件,其实也就是这么实现的。
下面进入正题,先看一下最终的效果图:
好的,图片就是这么简单了,台哥的美感比较差,所以大家凑合着看吧。
这个要实现的就是:按上下方向键时,焦点是四个菜单上切换,焦点菜单用红色显示。
是不是很简单,自己可以想一下如何实现,然后复制下面的代码,放到Eclipse里执行。
package game4;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.JPanel;
/**
* java游戏开发杂谈
* ---demo4:实现一个简单的游戏菜单
*
* @author 台哥编程课堂
* https://blog.csdn.net/chaohi
*
* @date 2019-04-12
*/
public class GamePanel extends JPanel implements KeyListener{
/** 屏幕的宽和高 */
private int width,height;
public GamePanel(int width, int height) {
this.width = width;
this.height = height;
this.setSize(width, height);
//设置当前画布可以获得焦点。
this.setFocusable(true);
//设置自己为自己的按键事件监听器
this.addKeyListener(this);
}
/**要显示的菜单项*/
private String[] menus = new String[]{"开始游戏", "游戏设置", "帮助关于", "退出游戏"};
/**当前焦点在哪个菜单项*/
private int focusIndex;
/**菜单项位置的横坐标*/
private int menu_x = 260;
/**菜单项位置的纵坐标*/
private int[] menu_ys = new int[]{80, 110, 140, 170};
/**
* 覆盖paintComponent()方法
*/
public void paintComponent(Graphics g) {
super.paintComponent(g);
//画绿色背景
g.setColor(new Color(0x9391d6));
g.fillRect(0, 0, width, height);
//绘制菜单项。焦点所在的菜单用红色,其它为黑色。
for (int i = 0; i < menus.length; i++) {
int x = menu_x;
int y = menu_ys[i];
//如果是焦点按钮,用红色突出
if(i == focusIndex){
g.setColor(Color.red);
}else{
g.setColor(Color.black);
}
g.drawString(menus[i], x, y);
}
}
/**
* 当键盘上的键被按下,程序会调用这个方法,来处理这个按下事件
*/
@Override
public void keyPressed(KeyEvent e) {
int keyCode = e.getKeyCode(); //根据keyCode能知道按下的是哪个键
switch(keyCode)
{
case KeyEvent.VK_UP://往上的方向键
focusIndex = (focusIndex + menus.length - 1) % menus.length; //考虑%取余的意义。
this.repaint(); //刷新画布
break;
case KeyEvent.VK_DOWN://往下的方向键
focusIndex = (focusIndex + 1) % menus.length;
this.repaint();
break;
case KeyEvent.VK_ENTER: //如果是Enter键
//----------------这里就可以根据focusIndex知道按下的是哪个菜单项,从而进行对应操作
//----------------比如如果focusIndex为0,则转到游戏界面。如果focusIndex为2,则转到帮助关于的界面。
System.out.println(focusIndex + " , " + menus[focusIndex]);
break;
}
}
@Override
public void keyReleased(KeyEvent e) {
}
@Override
public void keyTyped(KeyEvent e) {
}
}
package game4;
import javax.swing.JFrame;
/**
* java游戏开发杂谈
* ---demo4:实现一个简单的游戏菜单
*
* @author 台哥编程课堂
* https://blog.csdn.net/chaohi
*
* @date 2019-04-12
*/
public class GameFrame extends JFrame{
private int width = 600, height = 400;
public GameFrame() {
//设置窗体标题
this.setTitle("java游戏开发杂谈-台哥出品");
//创建一个画布
GamePanel panel = new GamePanel(width, height);
//把画布加入到窗体中
getContentPane().add(panel, "Center");
//设置窗体大小
this.setSize(width, height);
//设置能否调整窗体大小
this.setResizable(false);
//这句会使得在屏幕上居中显示
this.setLocationRelativeTo(null);
//当关闭窗体的时候退出程序
this.setDefaultCloseOperation(EXIT_ON_CLOSE);
//把窗体显示出来
this.setVisible(true);
}
/**
* 主方法
*/
public static void main(String[] args) {
GameFrame frame = new GameFrame();
}
}
这是本系列的第七篇文章了,不知道有没有同学在跟着学呢。。
这里要特别声明的一点是:学习java游戏开发,可能没有完全对口的工作,所以如果你正准备找工作,那最好去学习JSP、Sevlet、Mysql等知识吧,对应聘web开发的工作更有直接好处。(我怕被骂误人子弟哇。。)
那么学习java游戏开发,有什么好处呢。我是这么看,第一是这个很好玩,能充分体验编程的乐趣。第二是游戏开发更有挑战性,对面向对象思想、数据结构、算法、设计模式等都有更高的要求,学习游戏编程,对这些知识能有更好的理解。
台哥十几年工作中,经常看到一些程序员,工作多年了,还是只会数据库的增删改查,只会套用各类框架,对面向对象没有深入的理解和思考,究其原因,就是因为做的项目,核心需求太单一,软件复杂度太简单了。
游戏,是学习编程最好的练手项目。走在路上、坐在车上,跑在操场,突然想到一个游戏玩法,回到宿舍就能实现出来,然后屁颠屁颠的送给女朋友玩,程序员的乐趣,不过如此吧。
台哥,一个混迹多年的老油条,猛然一天翻资料,发现自己以前写的代码,噢,才想起来我以前也是程序员嘛。这几年游走酒场饭局,编程知识都快忘光啦。赶紧翻出我的CSDN,匆匆写下java游戏开发杂谈,能写多少算多少,写到哪里算哪里。如果能讨几个拍砖的砖头,我就更开心了。
java游戏开发杂谈 - 实现游戏主菜单的更多相关文章
- java游戏开发杂谈 - 线程
线程,让游戏拥有了动态变化的能力. java的图形界面,在启动的时候,就开始了一个线程. 这个线程负责处理:JFrame.JPanel等的绘制.事件处理. 它是由操作系统调用的,在程序启动时开启,程序 ...
- java游戏开发杂谈 - 事件处理
大家都知道,游戏需要跟玩家交互,需要接收玩家的鼠标.键盘发出的命令,比如在地图上点击一下,人物就自动寻路走过去:键盘上按下某个键,就弹出一个背包界面. 这些逻辑是怎么处理的呢? 大家先不用深究太详细的 ...
- java游戏开发杂谈 - 画布和画笔
在Eclipse里,编写如下两个类: package game2; import java.awt.Color; import java.awt.Graphics; import javax.swin ...
- java游戏开发杂谈 - 创建一个窗体
package game1; import javax.swing.JFrame; /** * java游戏开发杂谈 * ---demo1:创建一个窗体 * * @author 台哥 * @date ...
- java游戏开发杂谈 - 游戏编程浅析
每个游戏,你所看到的它的一切,都是计算机画出来的! 地图是画出来,人物是画出来的,树木建筑是画出来的,菜单按钮是画出来的,滚动的文字.闪烁的图标.云雾烟火,都是画出来的. 游戏编程,所要做的,就是控制 ...
- java游戏开发杂谈 - 游戏物体
现实生活中,有很多物体,每个物体的长相.行为都不同. 物体存在于不同的空间内,它只在这个空间内发生作用. 物体没用了,空间就把它剔除,不然既占地方,又需要花精力管理. 需要它的时候,就把它造出来,不需 ...
- java游戏开发杂谈 - 有限状态机
在不同的阶段,游戏所运行的逻辑.所显示的界面,都是不同的. 以五子棋举例,游戏开始.游戏中.胜负已分,对应的界面和逻辑都不同. 在游戏中,又分为:自己下棋.对方下棋.游戏暂停.悔棋等多个状态. 再比如 ...
- 【读书笔记《Android游戏编程之从零开始》】19.游戏开发基础(游戏音乐与音效)
在一款游戏中,除了华丽的界面 UI 直接吸引玩家外,另外重要的就是游戏的背景音乐与音效:合适的背景音乐以及精彩的音效搭配会令整个游戏上升一个档次. 在 Android 中.常用于播放游戏背景音乐的类是 ...
- Unity 4.2.0 官方最新破解版(Unity3D 最新破解版,3D游戏开发工具和游戏引擎套件)
Unity是一款跨平台的游戏开发工具,从一开始就被设计成易于使用的产品.作为一个完全集成的专业级应用,Unity还包含了价值数百万美元的功能强大的游戏引擎.Unity作为一个游戏开发工具,它的设计主旨 ...
随机推荐
- Node笔记四
异步操作 -Node采用chrome v8 引擎处理javascript脚本 --v8最大特点就是单线程运行,一次只能运行一个任务 -Node大量采用异步操作 --任务不是马上执行,而是插在任务队列的 ...
- Python绘图之matplotlib基本语法
Matplotlib 是一个 Python 的 2D绘图库,通过 Matplotlib,开发者可以仅需要几行代码,便可以生成绘图,直方图,功率谱,条形图,错误图,散点图等.当然他也是可以画出3D图形的 ...
- mysqldump+系统计划任务定时备份MySql数据
MYSQL 数据库备份有很多种(cp.tar.lvm2.mysqldump.xtarbackup)等等,具体使用哪一个还要看你的数据规模.下面给出一个表 #摘自<学会用各种姿态备份Mysql数据 ...
- PHP入门小练习
1.编写字符串检查函数,判断一个字符串是否为有效电话号码.要求:手机号码的长度为11位的数字,固定电话为开头三或四个数字后跟一个短横线后接8位数字. <? function isTel($tel ...
- sql server 死锁排查
记得以前客户在使用软件时,有偶发出现死锁问题,因为发生的时间不确定,不好做问题的重现,当时解决问题有点棘手了. 现总结下查看死锁的常用二种方式: 第一种是图形化监听: sqlserver --> ...
- Springboot+JPA+Thymeleaf 校园博客完整小网站
本文所属[知识林]:http://www.zslin.com/web/article/detail/35 此项目是一个比较简易的校园博客.麻雀虽小五脏俱全,虽然是比较简易的但是涉及的知识点还是比较全面 ...
- Spring Cloud构建微服务架构(二)服务消费者
Netflix Ribbon is an Inter Process Communication (IPC) cloud library. Ribbon primarily provides clie ...
- HoloLens开发手记-实现3D应用启动器
一直有人问我,第三方应用在HoloLens上可以实现3D启动图标吗?就像微软官方出的应用那样.在不久之前,这个问题的答案还是No. 但是随着最新的Windows build 1803版本的发布,现在我 ...
- setInterval setTimeout 详解
JavaScript的setTimeout与setInterval是两个很容易欺骗别人感情的方法,因为我们开始常常以为调用了就会按既定的方式执行, 我想不少人都深有同感, 例如 setTimeout( ...
- JS 总结
加var与不加var的区别: 简单来说就是加了var是局部变量 不加是全局变量.只有加了var的情况下就能限定该变量的使用范围 这样在别的方法里面也可以命名同样的变量了