关于战棋对战化的设想和实现

想写写博客了,但是却发现自己最近什么东西都没弄,只忙着工作了

 

于是,把之前发过的帖子,拿来这里填一下了

 

关于曹操传对战化,或者说是战棋游戏的网络化,我在很早之前就有过很多的设想,只是没有精力和能力去把它变成现实

说一说我对战棋网络化的设想吧,
1,和现在其他网游一样,每个玩家可以选择自己喜欢的人物角色进行游戏,这些人物有着不同的属性,比如说曹操传里的骑兵,步兵,弓兵,军师,跑车等等
2,玩家一开始的属性,根据玩家选择的人物兵种的不同而不同,但是数据总合相等
3,玩家根据做任务或者升级等方式提升自己的等级,然后获得相应的属性点数,自己来分配到相应的属性,得到相应的能力成长,但是属性点数分配的时候,不同的兵种,各个属性的成长不一样,比如说,骑兵攻击分配一点,成长+4,步兵攻击分配一点,成长+2等等,就是取消了根据武力智力等来成长的方式
4,装备,药品等,和其他网络游戏一样,没什么特殊设想
5,关于战斗
       1)任务战斗:就是人机对战,可以多个玩家一起参战,共同和电脑对战,来完成一些比较难打的任务等
       2)玩家对战:就是PK
6,战场上,因为每个玩家只有一个角色,所以每个人只能控制一个人物,且加入时间限制,每人有10秒钟左右的控制时间,超过这个时间则不做任何动作或者进入由电脑自动控制人物行动
7,为了避免玩家一个人孤军进入对方阵地后被群P,每个人加入速度属性,战场上根据每个人物的行动先后顺序根据速度的大小来决定,这样即使一个人挨打,其他人可以跟上去补血
8,防止避战,战棋游戏和其他游戏不同,谁也不想先进入对方的攻击范围去挨打,解决的方法我想到下面几个
    1)随即分配玩家在战场的位置,这样玩家一开始就处于攻击或被攻击状态了,但是对于防御弱的人来说,这个方法恐怕太不合理
    2)在战斗开始时,加入攻击方和防守方,攻击方在规定回合内没有做任何攻击动作的时候,就要受到相应的惩罚,这个攻守方的设定,可以是随机的,也可以是玩家开战之前就已经决定好的
总的来说,设想就先说这么多吧

我是一个很喜欢去尝试的人,有了想法就会尝试着去做,但是本人也是一个比较懒的人,真正去完成这样一个游戏,恐怕现在的我还没有这个时间和精力
那么,我在这里,就简单的实现一下战场上的一部分功能,顺便练习一下网络游戏的初步制作
希望我有毅力去完成尽可能多的完善它......

客户端实现方式,我还是选择Flash,因为用Flash可以不下载就可以玩,
服务端的实现,可以用C,C++或java,这里,我选择java
至于flash和java之间,采用socket

好了,下面开始制作
为了偷懒,我直接在我之前的游戏基础上来制作,具体看我的其他关于SLG游戏制作的帖子

代码主要开始要看源码,这次我只做简单说明

 

首先,用户需要连接和登陆服务器
那么,先来研究一下,flash和java服务器的连接
如果有兴趣跟我一起研究的话,你需要Flash CS3以上版本和eclipse

 

客户端:

//先来建立连接IP地址和端口,这里服务器暂时采用本地 private var hostIp:String = '127.0.0.1'; private var port:int = 8210; //进行连接服务器 public function start():void { //连接socket socket=new Socket(hostIp,port); //注册连接完成侦听函数 socket.addEventListener(Event.CONNECT,onConnect, false, 0, true); //监听连接关闭 socket.addEventListener(Event.CLOSE,funClose); //注册数据通讯函数 socket.addEventListener( ProgressEvent.SOCKET_DATA, onSocketData ); //注册相应错误函数 socket.addEventListener( IOErrorEvent.IO_ERROR , failConnect , false, 0, true); socket.addEventListener(SecurityErrorEvent.SECURITY_ERROR, onSecurityError, false, 0, true); } //向服务器发送数据 public function writeMsg(msg:String):void{ socket.writeUTFBytes(msg + "/n"); socket.flush( ); } 

 

这就是客户端一个简单的连接服务器的代码了

在看服务端:
简单来说需要,建立socket和连接socket
private ServerSocket server;
server = new ServerSocket(8210);

但是用这些简单代码进行连接的时候,会遇到一个安全问题,就是flash的安全沙箱问题,
解决办法就是当flash进行访问的时候,返回一个<cross-domain-policy><allow-access-from domain=/"*/" to-ports=/"8210/"/></cross-domain-policy>/0的字符串,来允许访问
当然真正实现起来,代码需要很多,最后我会把代码放上来

在客户端建立一个登陆界面,来连接和登录服务器
效果,

关于战棋对战化的设想和实现_第1张图片

服务器没有启动或者连接服务器失败的时候,显示相应的错误信息
为了简便,我暂时把登录验证信息的密码设定为123,用户名随意
输入登陆信息,然后发送给服务器进行验证
Sav.socket.writeMsg("type=login&name=" +txtName.text +"&pass="+txtPass.text);
这里的type代表验证信息的种类,这里的意思是:登陆验证,用户名,密码
登录成功后,服务器返回
bMan.sendToSocket(this.socket,"type=in");
表示:登录成功,用户名,输出信息
当然这些规则都是自己规定的,在于服务器互通信息的过程中,为了简便,我假设所有信息都是合法的,不需要做任何处理,因为真正做网络游戏的时候,为了防止不法用户,必须对所有信息进行验证处理,这次,咱们把这些东东都省略掉
客户端接收到服务器验证成功的信息后,页面跳转
if(resultHash.getValue("type") == "in"){
        Sav.Game.loginSuc();
        return;
}
登录成功后,效果,

关于战棋对战化的设想和实现_第2张图片

 

再来加一个简单的聊天功能
客户端把输入的信息发送给服务器
Sav.socket.writeMsg( "type=talk&msg=" + _txtInput.text);
服务端把这个信息发送给所有用户
if ("talk".equals(result.get("type"))) {
        bMan.sendToAll("type=talk&name=" + user.getName() + "&msg=" + result.get("msg"));
}
最后客户端接收到信息后,显示出来
if(resultHash.getValue("type")  == "talk"){
        addText(resultHash.getValue("name") + ":" + resultHash.getValue("msg"));
        return;
}
效果,

关于战棋对战化的设想和实现_第3张图片

 

现在大家知道flash的魅力了吧,做一个聊天工具原来如此简单

进入战斗之前,玩家得有自己的角色,这个应该是在刚开始进入游戏的时候设定的,
因为我这次只研究战场,所以就在战斗之前选择人物了
时间有限,我只说明我做的原理,代码我只挑重点的地方写,完整代码等游戏差不多成形的时候会提供下载
在登录成功后,建立一个界面,
用来做战前准备,
先来建立四个可选人物
private var _arr_select:Array = [new CharacterMC(1),new CharacterMC(98),new CharacterMC(100),new CharacterMC(103)];
然后把它们依次放到界面上面,并且添加点击事件,当用户点击人物的时候,表示选择了该人物进行游戏
(_arr_select[0] as Sprite).addEventListener(MouseEvent.MOUSE_DOWN,onSelect01);
(_arr_select[1] as Sprite).addEventListener(MouseEvent.MOUSE_DOWN,onSelect02);
(_arr_select[2] as Sprite).addEventListener(MouseEvent.MOUSE_DOWN,onSelect03);
(_arr_select[3] as Sprite).addEventListener(MouseEvent.MOUSE_DOWN,onSelect04);
下面是其中一个点击事件,当用户点击这个人物的时候,在左上方显示选定角色
private function onSelect01(e:MouseEvent):void{
        if(Sav.INDEX >= 0){
                return;
        }
        _arr_select[0].alpha = 1;
        _arr_select[1].alpha = 1;
        _arr_select[2].alpha = 1;
        _arr_select[3].alpha = 1;
        Sav.ID = 1;
        _arr_select[0].alpha = 0.5;
        //Sav.SHOW_USER是已经创建好地用来显示选定角色的Sprite
        Sav.SHOW_USER.removeChildAt(1);
        var showChara:CharacterMC = new CharacterMC(Sav.ID);
        showChara.y = 25;
        Sav.SHOW_USER.addChild(showChara);
}
然后,再画四个可选框,两个甲方,两个乙方
如下图

关于战棋对战化的设想和实现_第4张图片

 

点击相应位置的时候,应该把自己所选的角色人物添加到这个位置
但是只是在自己的游戏界面上添加当然不行,应该让所有人都看到,所以当选择位置的时候,应该先通知服务器
Sav.socket.writeMsg("type=startin&index=0&id=" + Sav.ID);
这句话表示,告诉服务器自己选择了Sav.ID角色,并把这个角色放到0的位置上
然后服务器通知其他所有人,
bMan.sendToAll("type=select&name=" + user.getName() + "&index=" + user.getRoomIndex() + "&id=" + user.getId());
这句话表示,服务器通知所有用户,user.getName()用户,选择了user.getId()角色,并选择了user.getRoomIndex()位置
然后,所有用户在接受到服务器的通知后,在页面上显示该用户
看下图中,我用了四个用户登录,他们选择了人物角色和位置后,所有人都可以看得到

下次该研究让这些家伙们同时进入战场了

关于战棋对战化的设想和实现_第5张图片

 

关于战棋对战化的设想和实现_第6张图片

 

关于战棋对战化的设想和实现_第7张图片

 

关于战棋对战化的设想和实现_第8张图片

 

 

当四个玩家都选择好了人物和位置后,服务器就通知各个玩家进入战场,
告诉玩家进入哪个战场,以及出现的位置等等
至于地图的数据等,可以直接在本地加载,我图个省事,直接从服务器一起发给玩家了
                                                        String startXml = "<data>" + 
                                                    "<Map>1</Map>" + 
                                                    "<DataMap>" + 
                                                        "<list>1,1,1,1,1,0,0,0,0,1,1,1,1,1,1,1,1,1,1,1</list>" + 
                                                        "<list>3,1,1,1,1,1,0,0,0,1,1,1,1,1,1,1,1,1,1,1</list>" + 
                                                        "<list>3,3,1,1,1,1,0,0,0,0,1,1,1,1,1,1,1,1,1,1</list>" + 
                                                        "<list>3,3,3,1,1,1,1,0,0,0,1,1,1,1,1,1,1,1,3,3</list>" + 
                                                        "<list>3,3,3,3,1,1,1,0,0,0,0,1,1,1,1,1,1,3,3,3</list>" + 
                                                        "<list>3,3,3,3,3,1,1,0,0,0,0,0,1,1,1,1,1,3,3,3</list>" + 
                                                        "<list>3,3,3,3,3,4,4,4,4,0,0,4,4,4,4,1,1,3,3,3</list>" + 
                                                        "<list>3,3,3,3,3,4,6,0,0,0,0,0,0,6,4,1,3,3,3,3</list>" + 
                                                        "<list>3,3,3,3,3,4,6,0,0,0,0,0,0,6,4,1,3,3,3,3</list>" + 
                                                        "<list>3,3,3,3,0,4,6,0,0,0,0,0,0,0,4,1,3,3,3,3</list>" + 
                                                        "<list>3,3,3,0,0,0,0,0,0,4,4,0,0,0,4,3,3,3,3,3</list>" + 
                                                        "<list>3,3,0,0,0,0,0,0,0,5,7,0,0,0,4,3,3,3,3,3</list>" + 
                                                        "<list>3,0,0,0,0,4,0,0,0,0,0,0,0,0,4,3,3,3,3,3</list>" + 
                                                        "<list>0,0,0,0,0,4,6,6,0,0,0,0,0,7,4,0,3,3,3,3</list>" + 
                                                        "<list>0,0,0,0,0,4,4,4,4,0,0,4,4,4,4,0,1,1,3,3</list>" + 
                                                        "<list>0,0,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1,3</list>" + 
                                                        "<list>1,1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1</list>" + 
                                                        "<list>1,1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,1,1,1</list>" + 
                                                        "<list>1,1,1,1,1,1,1,0,0,0,0,0,0,0,0,0,1,1,1,1</list>" + 
                                                        "<list>1,1,1,1,1,1,1,1,1,0,0,0,0,0,0,1,1,1,1,1</list>" + 
                                                    "</DataMap>" + 
                                                    "<Our>" + 
                                                        "<List x@/"9/" y@/"12/" speed@/"" + ourlist.get(0).getSpeed() + "/" username@/"" + ourlist.get(0).getName() + "/">" + ourlist.get(0).getId() + "</List>" + 
                                                        "<List x@/"10/" y@/"13/" speed@/"" + ourlist.get(1).getSpeed() + "/" username@/"" + ourlist.get(1).getName() + "/">" + ourlist.get(1).getId() + "</List>" + 
                                                    "</Our>" + 
                                                    "<Enemy>" + 
                                                        "<List x@/"8/" y@/"13/" speed@/"" + enemylist.get(0).getSpeed() + "/" username@/"" + enemylist.get(0).getName() + "/">" + enemylist.get(0).getId() + "</List>" + 
                                                        "<List x@/"11/" y@/"13/" speed@/"" + enemylist.get(1).getSpeed() + "/" username@/"" + enemylist.get(1).getName() + "/">" + enemylist.get(1).getId() + "</List>" + 
                                                    "</Enemy>" + 
                                                "</data>";
                                                        bMan.sendToAll("type=start&xml=" + startXml);
因为和服务器通信的时候,字符串中有等号,所以xml数据中的等号先换成了@,到了客户端再换回来
每个用户在接受到start指令后,进入战场
之前的游戏中,一开始就进入战场了,这次只是在进入战场之前,加一些东西而已
画面如下,战场上每个人物上面显示用户名,画面的左上方,显示自己的信息
关于战棋对战化的设想和实现_第9张图片
关于战棋对战化的设想和实现_第10张图片

 

 

到这里,这个简陋版虽然已经完成,
但是因为只是想学习一下如何做网络游戏,简单实现下功能而已,而且是在原来代码上改的,可以说代码写的乱七八糟,
如果想看一看,AS和JAVA如何通信的话,可以参照一下,如果想学习的话,就不要看代码了
关于测试,打开目录
slg/as3.0/bin
先运行服务器文件CaocaoServer.jar,双击就可以了,但是打开了也没有什么提示,只是在任务管理器里多了一个javaw.exe进程
关闭的方法有两个,一个是用任务管理器里直接关闭,一个就是在游戏的对话框里发送stop
服务器启动后,启动游戏CaoCao.exe文件,
本来想弄成网页版的,但是因为Flash10.1出来后,嵌在网页里的falsh,当页面不是当前页的时候,flash的自动动态帧频会自动降到每秒2帧,定时器也只会每秒触发2次,游戏基本上等于停止状态,所以没办法,只能发布成exe文件了

进入游戏后添入用户名和密码,用户名任意,密码是123
然后,先从下面的四个角色中选择一个,然后点击甲方或者乙方对应的位置

然后,再点击CaoCao.exe文件,填写另外一个用户名
如此,一共打开四个游戏文件,相当于四个人在玩游戏
四个人都选择好相应的角色和位置后,就会进入游戏的战场界面,看看左上角的人物,黑白表示当前不可操作,彩色表示当前可以操作,还有游戏右下角也会有文字提示

结论,AS3.0做网络游戏,还是比较轻松的

 

关于源代码的下载:

http://download.csdn.net/source/2892360

 

你可能感兴趣的:(游戏,list,socket,服务器,Flash,网络游戏)