2013年5月20日 21:24:12

我这是...你看你看,都5天没写这个了..[网页继续是白板类型,字体调不了,自己Ctrl键+鼠标滚轮放大看咯~]
主要是这几天做好了一个小游戏项目吧~~HOHO~~瞬间感觉我也能做起一个能玩的东西了,以前玩过的一些小游戏是不是也非常简单呢?~~
嗯,人生里用代码(java)敲出的第一个小游戏哈哈
是主要的东东~

对了,根据设计原则の单一职责原则,不同类要不同分工.所以建的主窗体类要分开,地图类分开,场景角色类分开,场景元素类分开,既然是弹幕游戏,当然敌人和子弹类建得也比较多,也必须分开,然后还有个专门的工具包的类.最后还有资源文件dao类.
所以上周三那天写在一个类的大体的东西,看着各种烦又乱还找不清,分类存放后看起来方便多了.

设计原则の迪米特原则:软件实体应尽可能少地与其他实体发生相互作用(不要与陌生人说话,嗯大概是这样子~),各方法最好分工分开

设计原则の接口隔离原则:使用专门的接口比用统一的接口要好,便于分工,在实现接口时,不应看到自己不用关心的方法.如给所有角色元素中的敌人实现一个产生道具的接口,即他们必须产生道具(当然概率要设好),把敌人子弹类实现个会伤害主角接口,然后在判定是否碰撞时就可以限定实现某接口的元素才能与主角产生交互(增加状态\道具\死亡等),这样很方便

设计原则の开闭原则:对扩展开放,对修改关闭,其他原则都是它的表现和补充.实现开闭原则的方法是抽象.  如把能动的元素建个父类。他们都有 
对象x坐标 */
Y坐标 */
对象宽度 */
对象高度 */
对象碰撞区域 */
当前对象需要绘制的图片 */
当前对象的速度 */         
这几个属性。并且有
* 画笔绘制自身图片
* 设置配置碰撞区域和本身重合  
* 移动出屏幕就移除自身     方法.
开闭原则の开的* 抽象移动方法,由子类对象特点分别实现
所以这个父类就建成抽象类.

设计原则の组合/聚合复用原则(ARP) 
例子是 如果人要实现飞这个方法,当然不能继承飞机,只要调用飞机的飞的方法即可[就是成员变量那new一个飞机即可]

设计原则の依赖倒转原则(DIP)
我们是面对抽象编程,不是面向具体的编程.  如主窗体加个所有角色的父类即可,而不是具体的人\怪物\子弹等

设计原则の李氏替换原则(LSP)
父类出现的地方,子类一定可以替换,若父类方法在子类中发生了畸变,就要断开父子关系.采用依赖,复合,组合原则即可
能以此检测两个类是否是父子关系

哦对,是因为讲了一点点线程,才能实现咱的游戏运行吧呵呵~

项目思想其一:设final表示的多个状态值,人物的一个阶段就用一个状态值.分好阶段,清晰表示

在eclipse里设置增大虚拟内存:窗口->首选项  java 已安装jre  选中  编辑  -Xmx128m   (128m或更多自己设)

判断俩区域是否相交   intersects()关键字


好了,来谈谈次项目始末点滴吧~(5天来脑子里全想着这game,今天过了就过了该收心了,有想添新东西闲了再来完善吧)

 

上周三项目经理开始讲个横版弹幕游戏,然后我就想到了目前不是大多是竖版的么.飞机啊雷电啊东方啊等等,就是竖版才有意思嘛.于是周五晚回来就开始着手重新开始做了,自己跟着做的半成品丢一边,以之为参考吧(毕竟还是刚开始做好多东西都不懂的).
自己能想到的可以新添的点子肯定是比较多的,但是具体能实现哪些就不好说了,也只能自己想办法根据已有经验去实现.没思路的就丢一变不去管了,有思路的单单要去实现起都要花不少时间呢~\

开始有想在窗体弄个不动的背景图片,也就是在窗体直接加入的图片等,弄了画布加其他元素后,这个图片就不见了.所以只得也扔进画布里.
 // 创建媒体跟踪器
 private MediaTracker track = new MediaTracker(this);

 /** 双缓冲画布 */
 private Image memoryImage;
 /** 双缓冲画笔 */
 private Graphics memoryGraphics;

周四周五跟着经理做什么就做什么,具体就不说了,开始说自己怎么做这个新的过程的吧~

在主窗体里://Runnable 实现多接口
public class MainFrame extends JFrame implements Runnable

关键代码:
  // 另外开辟内存空间用来存放叠加后的 图片
  this.memoryImage = this.createImage(700, 700);
  // 从双缓冲画布中得到双缓冲画笔。这样通过画笔绘制的图片就会叠加在双缓冲画布中
  this.memoryGraphics = this.memoryImage.getGraphics();

  // 注册键盘事件
  this.addKeyListener(new FrameKeyListener());

  // 初始化图片
  InitImage.init(track);
  try {
   // 将组号1的所有图,等待一起显示。避免某些图先加载先显示了
   track.waitForID(1);
  } catch (InterruptedException e) {
   e.printStackTrace();
  }
  
                //这个位置添加比较大型的元素进来的,如主角和boss等
  roleList.add(i);
  roleList.add(boss);
  roleList.add(boss2);
  roleList.add(boss3);
  Thread th = new Thread(this);// Thread是线程。 注意this
  th.start();

然后在实现的run()里写个while真循环:
this.draw(this.getGraphics());
并且 try 里
Thread.sleep(20);

然后另写draw方法绘制图片
小的直接在这里添加进来.多的(如各人物怪物子弹等)就专门写个初始化图片的类,这里调用即可.
(就这不知道纠结过多少eclipse不能识别gif,png,jpg以外的图片,中心那的图片软件和画图转不了格式~)

让地图动设自动的,纵坐标不断自加就行.初始地图坐标为负的长度

地图好了添加人物,有父类所有角色,继承之.设好人物的各个阶段状态(初始无敌,大招无敌,普通图片,左右分别移动的不同图片等),设好键盘事件.

这里让很多人纠结的是(包括我),项目经理跟大家讲课的时候设定了几个static final 状态的常量,是否能被打,是否作弊的boolean.他的isByHit设定是true就是无敌,但是平常思维是"会被打吗?会"不是表示不无敌吗?然后大家开始那会都这样跟着写,又在各个地方不断的设定和改变,思维慢的会被搞成晕乎乎的.所以这里我就全部以前写的关系,删了自己重新写,慢慢理清了不知道多久哦~出的问题多多:如图像被空指针,要么是某状态调不到,要么写错啥的...人物一出来没有无敌时间,按了无敌键无反应,设定的boolean错了呗...开始状态能按无敌键有效,正常状态后就按着无效了...画布里动态要变要存在的图片等东西不能放构造方法里,不然在进城里就是昙花一现...因为要设定的判断的地方很多,在碰撞设置里,地图里有少量敌人和子弹元素.若我   "||" 或个实现是子弹这个接口,人物一出来就瞬死..当时太无语了找了两天不知怎么回事就先搁着,然后群里问了下别人发了下代码,才被找出原来仅仅是三个boolean用与或链接,A||B&&C,前俩必须加括号,不然这可不是顺序运算...

项目经理给的cut图片方法有写了单行和多行的切割并变成动态显示,他没讲多行的显示出来要多么的难,又没示范,结果我只能单独自己想算法给实现出来..还有就是不能缩放以及不好随即选择这组被切割图片的某几张显示...揪心的我就只找点单张的gif图或者静态的图而来可以缩放的...

人物若吃到加生命或者火力或者炸弹的道具.要分别添加到各个属性里去,其中改子弹属性最难,还是观望了同僚的思路才把它实现出来.(自己设想的是像大多数弹幕游戏一样子弹应该变多和变大或者范围什么的啊,感觉实现出来好纠结),就直接跟他的思路把子弹的大小和去敌人血的多少设为静态变量,能在人物吃到这个道具的时候判定并让子弹变大和威力变大...然后几分钟做出来了..真的是非常感谢他大几个小时的想法并实现了呢~(嗯,亲爱的中秋~)

按发发招无敌时若是左右移动状态(此状态有不同的图片显示),则是左右图片的显示(这样不好看),没像大家那样无敌时弄另外个图片显示,想想懒得找其他图了就这样吧

子弹变大后发射点和人物不协调...于是又去具体算子弹宽度和人物宽度的数据,并动态被获取成中心位置发射..而不是大家的获取人物图片坐标再加上具体的大概个x,y值...

触弹死亡后,若人物掉出屏幕外过程中(此时人物还没被移除集合),若碰到另外的伤害单位(敌人子弹或者敌人身体),生命会继续被扣掉,若穿过敌人整个身体,生命会无限扣..此大bug我也想了很久...结果就是把人物死亡时也设定成无敌了事的一句代码...汗呐...(当然包括死亡状态的某些状态,也要设定能不能发子弹或者大招的,不然人物死亡还没掉出屏幕的过程中,能发大招,岂不是很搞笑呢?~)

没有做他们的那种遇到大boss时画面静止或者打败后跳转通关,应该很简单,就是设个这个时候地图的滚动为isfalse.通关的话我就设定个"是男人就XXX"系列吧,越后面越难以及达到多少分数就算通关吧。不过因为有排行榜系统,就做个无限玩下去系列得了。。无非就是添加敌人计数类那里再多设记个阶段调整出敌人数量,在boss里设发弹幕频率和移动增加罢了(我目前仅仅设的当主角子弹威力大于多少时增加出怪数量,就够玩很久了,然后若人物死亡子弹威力被初始化自然又开始出怪是慢慢的了~)

若所得分数超过排行榜第五名则弹窗让你输名字并计入资源文件,主菜单里能跳排行榜看具体排名,今晚回来我又动态的在游戏主窗里显示的最高分。嗯嗯~~

对了我新实现的有这几个方面:在窗体里动态用图片数量的方法显示生命和炸弹数量;发射的子弹击中敌人动态在击中位置显示击中的数值(子弹威力我也设了分阶段的随即数值,而不像大家的都是定数吧),伤害能看到的感觉有没有?爆击了感觉也很爽啊呵呵【当然也可以把大boss的血量随窗体显示出来具体数值并用长条状的图片显示,我这没弄,不过原理一样的】

哦我设了三中敌人的子弹,大小和图片和运动方式不同。如小的子弹被数量多的敌人来发射,并且速度快些;大的子弹被数量少的敌人发射,并且速度慢些(看大家好多都设定成大的敌人子弹速度很快,太揪心了,反应杂来得及?)。。当初美好的设想“发射出的一波子弹是圈形的或者散射的”,以及“发射的子弹会跟踪主角位置若超过身位则不跟踪”。。发现完全没实现思路啊,以经理说法是要用三角函数了,我看他写的代码都是分别自己写了当横坐标为x时,几种分别的y坐标值(也就是只设定了有限个方向并且是固定角度和固定数量的),我看着觉得繁琐呢,子弹速度恒定,随机个横坐标出来在用函数算出纵坐标不就得了?或者也写固定几个角度用函数算出横纵坐标不就可以了?。。。这个感觉算法写着也烦,所以就先没写了。...我就写了
y+=2*speed;
count++;
if(count>200||count<0){ n=Math.random()*2-1;count=0;}
x+=n*speed;
感觉简简单单,并且敌人发射的每个子弹方向都不一样,还是有可玩性了(若不设个count计数,则落下的子弹是左右的鬼畜抖动的)
[大家大多数的敌人只单独往一个方向走,子弹也是],这样的固定方向怎么会有意思呢[额毕竟大家都第一次做嘛,嗯嗯]

预想的把主角设双层碰撞区域,在外围大的区域但是没到内围小的区域,碰到敌人子弹能加分但是不会死.被碰到内层区域才会死..因为太忙了就没去专门想以及实现(东方游戏就是有这个擦弹加分系统)
对了我获取的静态8张boss图片,每次重新开游戏会是不一样的3种怪物显示,但是不能随即成同一场战斗中同一个怪随机到不同的图片,较揪心,,,还没想到解决方法..

嗯有哥们说是这csdn网站本身就很卡的问题,,,额,.我是不是该回去转战我的QQ空间呢...

哦对了还今天才被老师解决的应该是目前知道的最后个小bug,有时候我打着打着人物变成双重影子了,若发大招人物被移动或者被触死会只死亡一个,然后就会新出个人物和另外个没死的个人物同时存在得最为明显...经老师调试,原来是死亡状态我为了严密性给调用了俩次,还不是线程的一直循环性嘛.最后删掉其中以个果断OK了..万岁~~`

nnd这才只是打字而已.写这些到现在都0点了,靠!我还不是去专门翻代码的呢....说好的预习明天要讲的三层架构呢?~~~

没玩头..暂时还不晓得怎么导出成可以直接玩的东东...

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值