[原创]雷电小游戏app设计
相信雷电是很多人的童年回忆,本文就尝试用android studio做一个简单的雷电小游戏。
游戏界面如下:
项目结构如下:
设计思路:
游戏机制设计
游戏目前的场景比较简单,为我军飞机对战敌军Boss飞机。我军飞机目前只有普通子弹攻击一种方式,我军飞机的移动方式为手指在屏幕上移动控制。为了增加游戏难度,为敌军飞机设计了三种攻击模式:
1)Boss飞机满血量为1000.当Boss飞机血量大于600时,Boss飞机会左右移动,对我军飞机进行规律地激光攻击;
2)Boss飞机血量在[300,600]之间时,Boss飞机移动会加速,会左右移动,追踪我军飞机并进行向无规律地激光攻击;
3)Boss飞机血量小于300时,会启动死亡撞击模式,一边攻击,一边试图撞击我军飞机。死亡撞击演示gif如下:
敌军飞机被击毁后,会掉落物品,游戏中设计了小水晶作为掉落物品,我军飞机获取后处于无敌状态,被光罩笼罩。为后续的设计做铺垫。
总结发现,在上述场景中,出现了飞机、掉落物品、子弹、爆炸效果等概念,将其抽象为类。
工程部分UML图如下:
飞机和敌机相撞,会导致我军飞机被击毁,另外飞机获取物品时也要做碰撞检测、子弹击中飞机时,还是要做碰撞检测。这些逻辑有共通之处,可以抽出一个公共的类,具有检测碰撞的公共方法。这样就避免了在代码到处去写和修改碰撞的逻辑。该公共类如下:
package com.example.demonstar.common;
import android.content.Context;
import android.graphics.Bitmap;
public class CommonObject {
protected int positionX;
protected int positionY;
protected Bitmap skin;
protected Context context;
public CommonObject(Context context) {
this.context = context;
}
public CommonObject(Context context, int positionX, int positionY) {
this.context = context;
this.positionX = positionX;
this.positionY = positionY;
}
public boolean isCollided(CommonObject object) {
return this.detectCollision(object) || object.detectCollision(this);
}
protected boolean detectCollision(CommonObject object) {
if (object == null) {
return false;
}
if (isVertexInArea(this.positionX, this.positionY, object)) {
return true;
}
if (isVertexInArea(this.positionX + this.skin.getWidth(), this.positionY, object)) {
return true;
}
if (isVertexInArea(this.positionX, this.positionY + this.skin.getHeight(), object)) {
return true;
}
if (isVertexInArea(this.positionX + this.skin.getWidth(), this.positionY + this.skin.getHeight(), object)) {
return true;
}
return false;
}
protected boolean isVertexInArea(int abscissa, int ordinate, CommonObject object) {
return this.isAbscissaInRange(abscissa, object) && this.isOrdinateInRange(ordinate, object);
}
protected boolean isAbscissaInRange(int abscissa, CommonObject object) {
return abscissa < object.getPositionX() + object.getSkin().getWidth() &&
abscissa > object.getPositionX();
}
protected boolean isOrdinateInRange(int ordinate, CommonObject object) {
return ordinate > object.getPositionY() &&
ordinate < object.getPositionY() + object.getSkin().getHeight();
}
public int getPositionX() {
return positionX;
}
public void setPositionX(int positionX) {
this.positionX = positionX;
}
public int getPositionY() {
return positionY;
}
public void setPositionY(int positionY) {
this.positionY = positionY;
}
public Bitmap getSkin() {
return skin;
}
public void setSkin(Bitmap skin) {
this.skin = skin;
}
public Context getContext() {
return context;
}
public void setContext(Context context) {
this.context = context;
}
}
isCollided(CommonObject object)就是检测碰撞的公共方法。
以上图来说明一下碰撞检测的逻辑:
飞机总是需要一个原始图片去绘制到画布上的,碰撞检测实际上是在检测图片之间有无重叠。考虑我军飞机图片进入敌机图片区域的情形:当我军飞机位图的任意一个顶点位于ABCD的范围时,即可认为检测到碰撞的发生。敌机进入我军飞机HIJK区域时,同样也会发生碰撞。
时间所限,有空再写完。