围住神经猫-Java源码Word下载.doc
《围住神经猫-Java源码Word下载.doc》由会员分享,可在线阅读,更多相关《围住神经猫-Java源码Word下载.doc(10页珍藏版)》请在冰点文库上搜索。
publicintgetX(){
returnx;
publicvoidsetX(intx){
publicintgetY(){
returny;
publicvoidsetY(inty){
publicintgetStatus(){
returnstatus;
publicvoidsetStatus(intstatus){
this.status=status;
//同时设置X,Y坐标的方法
publicvoidsetXY(intx,inty){
/*每一个点都是一个抽象的对象,需要把每一个点抽象为一个类,然后让每一个圆圈继承于这个类,
或者直接把它实现为这个类的实例。
每个点有三个状态:
灰色-猫可走的路径;
红色-路障且状态
无法改变;
黄色-猫当前的位置。
*/
Playground
importjava.util.HashMap;
importjava.util.HashSet;
importjava.util.Map;
importjava.util.Vector;
importandroid.R.integer;
importandroid.content.Context;
importandroid.graphics.Canvas;
importandroid.graphics.Color;
importandroid.graphics.Paint;
importandroid.graphics.RectF;
importandroid.view.MotionEvent;
importandroid.view.SurfaceHolder;
importandroid.view.SurfaceHolder.Callback;
importandroid.view.SurfaceView;
importandroid.view.View;
importandroid.view.View.OnTouchListener;
importandroid.widget.Toast;
publicclassPlaygroundextendsSurfaceViewimplementsOnTouchListener{
//界面的响应和界面的绘制在SurfaceView完成,触摸事件的响应通过OnTouchListener接口实现
privatestaticintWIDTH=40;
//元素的
privatestaticfinalintROW=10;
//行高:
每行储存10个元素
privatestaticfinalintCOL=10;
//列宽:
每列储存10个元素
privatestaticfinalintBLOCKS=15;
//默认添加的路障数量
privateDotmatrix[][];
//声明二维数组来存放点元素
privateDotcat;
//声明猫这个点
publicPlayground(Contextcontext){
super(context);
//使用Context创建当前类构造函数
getHolder().addCallback(callback);
//将Callback对象指定给getholder
matrix=newDot[ROW][COL];
//将行高,列宽传递进去,指定数组大小
for(inti=0;
i<
ROW;
i++){//循环添加数据
for(intj=0;
j<
COL;
j++){
matrix[i][j]=newDot(j,i);
/*X,Y坐标值和行列值是相反的。
即通过查找列值获得X坐标,查找行值获得Y坐标*/
}
}
setOnTouchListener(this);
//设定为自己的触摸监听器
initGame();
//调用游戏初始化
//坐标反转:
封装一个getDot函数实现X,Y坐标反过来传递,所有的操作通过X,Y调用
privateDotgetDot(intx,inty){
returnmatrix[y][x];
//判断猫是否处于边界
privatebooleanisAtEdge(Dotd){
if(d.getX()*d.getY()==0||d.getX()+1==COL||d.getY()+1==ROW){
returntrue;
//当前点的坐标无论是x或y为0,或x或y值是定义的游戏场景最大值时都处于边界
returnfalse;
//为每个点实现获取相邻点的方法
privateDotgetNeighbour(Dotone,intdir){//每个点都有6个相邻点
switch(dir){
case1:
returngetDot(one.getX()-1,one.getY());
//获得中心点左边相邻点
case2:
if(one.getY()%2==0){
returngetDot(one.getX()-1,one.getY()-1);
//奇数行获得中心点左上相邻点:
x-1,y-1
}else{
returngetDot(one.getX(),one.getY()-1);
//偶数行获得中心点左上相邻点:
y-1
case3:
//奇数行获得中心点右上相邻点:
returngetDot(one.getX()+1,one.getY()-1);
//偶数行获得中心点右上相邻点:
x+1,y-1
case4:
returngetDot(one.getX()+1,one.getY());
//获得中心点右边相邻点
case5:
returngetDot(one.getX(),one.getY()+1);
//奇数行获得中心点右下相邻点:
y+1
returngetDot(one.getX()+1,one.getY()+1);
//偶数行获得中心点右下相邻点:
x+1,y+1
case6:
returngetDot(one.getX()-1,one.getY()+1);
//奇数行获得中心点左下相邻点:
x-1,y+1
//偶数行获得中心点左下相邻点:
default:
break;
returnnull;
//中心点6个方向距离的判断与获取。
路径结束点为路障用负数表示,为场景边缘用正数表示
privateintgetDistance(Dotone,intdir){
// System.out.println("
X:
"
+one.getX()+"
Y:
+one.getY()+"
Dir:
+dir);
intdistance=0;
if(isAtEdge(one)){
return1;
//如果下一个点已在屏幕边缘,无需再判断
Dotori=one,next;
//定义ori和next,ori指定为当前函数传入的one
while(true){
next=getNeighbour(ori,dir);
if(next.getStatus()==Dot.STATUS_ON){
returndistance*-1;
//下一个点为路障的话,直接返回距离0
if(isAtEdge(next)){
distance++;
returndistance;
//下一个点为场景边缘时,距离+1并返回
distance++;
ori=next;
//下一个点既不是路障也不是场景边缘,距离自加并把当前的下一个点赋值成参考点ori
//实现猫移动到下一个点
privatevoidMoveTo(Dotone){
one.setStatus(Dot.STATUS_IN);
//one的状态设置为猫所处的点
getDot(cat.getX(),cat.getY()).setStatus(Dot.STATUS_OFF);
;
//将猫当前点的状态复位
cat.setXY(one.getX(),one.getY());
//将猫移动到新的点
}
//猫的移动
privatevoidmove(){
if(isAtEdge(cat)){
lose();
return;
//猫处于游戏边缘,失败
Vector<
Dot>
avaliable=newVector<
>
();
//avaliable容器记录可用点
positive=newVector<
//positive容器记录这个方向上可以直接到达屏幕边缘的路径
HashMap<
Dot,Integer>
al=newHashMap<
//pl容器记录方向
for(inti=1;
7;
i++){//如果当前猫被6个邻点围住
Dotn=getNeighbour(cat,i);
if(n.getStatus()==Dot.STATUS_OFF){
avaliable.add(n);
//如果相邻点可用,把它添加到avaliable记录器中
al.put(n,i);
//为pl传入方向i
if(getDistance(n,i)>
0){
positive.add(n);
//当它有一个路径可以直接到达屏幕边缘,把n传递进positive中
}
//移动算法的优化
if(avaliable.size()==0){
win();
//周围的6个点都不可走,没有可用点,成功围住猫
}elseif(avaliable.size()==1){
MoveTo(avaliable.get(0));
//只有一个方向可走,可用点有一个,移动到这个可用点上
}else{//有多个方向可走
Dotbest=null;
if(positive.size()!
=0){//存在可以直接到达屏幕边缘的走向
System.out.println("
向前进"
);
intmin=999;
//999远大于场景中的所有可用步长,其他数也可
for(inti=0;
positive.size();
i++){
inta=getDistance(positive.get(i),al.get(positive.get(i)));
if(a<
min){
min=a;
//把最短路径长度传给min
best=positive.get(i);
//选出拥有最短路径的点
}
}else{//所有方向都存在路障
躲路障"
intmax=0;
avaliable.size();
intk=getDistance(avaliable.get(i),al.get(avaliable.get(i)));
if(k<
=max){//所有方向都存在路障,距离k为负数
max=k;
best=avaliable.get(i);
MoveTo(best);
//移动到最短路径的下一点
privatevoidlose(){
Toast.makeText(getContext(),"
Lose"
Toast.LENGTH_SHORT).show();
//失败提示
privatevoidwin(){
YouWin!
//成功提示
//实现界面绘制,在redraw方法中将所有元素以图形化显示出来,也就是将它绘制在Canvas对象上
privatevoidredraw(){
Canvasc=getHolder().lockCanvas();
//锁定画布
c.drawColor(Color.LTGRAY);
//设置颜色为浅灰色
Paintpaint=newPaint();
//创建Paint对象
paint.setFlags(Paint.ANTI_ALIAS_FLAG);
//开启抗锯齿,优化视频质量
//用两个For循环嵌套将所有的点显示到界面中来
for(inti=0;
intoffset=0;
//引入偏移量
if(i%2!
=0){
offset=WIDTH/2;
//对偶数行进行缩进
Dotone=getDot(j,i);
//将坐标赋值给内部变量one
//由于每个点对应的三种状态颜色不一样,要用一个switch语句
switch(one.getStatus()){
caseDot.STATUS_OFF:
paint.setColor(0xFFEEEEEE);
//STATUS_OFF状态时设置颜色为浅灰色
break;
caseDot.STATUS_ON:
paint.setColor(0xFFFFAA00);
//STATUS_ON状态时设置颜色为橙色
caseDot.STATUS_IN:
paint.setColor(0xFFFF0000);
//STATUS_IN状态时设置颜色为红色
default:
c.drawOval(newRectF(one.getX()*WIDTH+offset,one.getY()*WIDTH,
(one.getX()+1)*WIDTH+offset,(one.getY()+1)*WIDTH),paint);
/*在Canvas画布上画椭圆并界定它的上下左右边界宽度且有错位*/
getHolder().unlockCanvasAndPost(c);
//取消Canvas的锁定,吧绘图内容更新到界面上
//为Surfaceview添加Callback
Callbackcallback=newCallback(){//声明并实例化一个Callback接口
@Override
publicvoidsurfaceDestroyed(SurfaceHolderarg0){
//TODOAuto-generatedmethodstub
publicvoidsurfaceCreated(SurfaceHolderarg0){
redraw();
//执行redraw函数,在界面第一次显示时将指定的内容显示到界面上
//使用surfaceChanged方法来适配不同的屏幕尺寸
publicvoidsurfaceChanged(SurfaceHolderarg0,intarg1,intarg2,intarg3){
//surfacechanged方法包含四个参数:
SurfaceHolderholder,intformat,intwidth,intheight
WIDTH=arg2/(COL+1);
//需要修改width,即arg2。
//重绘界面
};
//游戏初始化:
分别对可走路径位置,猫的位置和路障位置进行初始化
privatevoidinitGame(){
//用for循环将所有点设置为STATUS_OFF,即可用状态
matrix[i][j].setStatus(Dot.STATUS_OFF);
cat=newDot(4,5);
//设置猫的起始点
getDot(4,5).setStatus(Dot.STATUS_IN);
//把猫的起始点的状态设置为STATUS_IN,才能记录猫的位置
//用for循环随机的指定10个点的坐标作为路障
BLOCKS;
){
intx=(int)((Math.random()*1000)%COL);
inty=(int)((Math.random()*1000)%ROW);
//随机获取1对坐标点
if(getDot(x,y).getStatus()==Dot.STATUS_OFF){//对当前可用路径点进行选择
getDot(x,y).setStatus(Dot.STATUS_ON);
//并把这个点设置为路障
i++;
//循环内自加避免当前路障被重复添加
//System.out.println("
Block:
+i);
//触摸事件的处理
publicbooleanonTouch(Viewarg0,MotionEvente){
if(e.getAction()==MotionEvent.ACTION_UP){
//当用户触摸之后手离开屏幕释放的瞬间才对事件进行响应
// Toast.makeText(getContext(),e.getX()+"
:
+e.getY(),Toast.LENGTH_SHORT).show();
//将屏幕的坐标转换为游戏的坐标
intx,y;
y=(int)(e.getY()/WIDTH);
//横向状态下,奇、偶数行有坐标偏移,而纵向的Y值是不变的,将y进行转换
if(y%2==0){
x=(int)(e.getX()/WIDTH);
//奇数行直接将屏幕的X坐标转换成游戏的X坐标
x=(int)((e.getX()-WIDTH/2)/WIDTH);
//偶数行偏移半个