JS做的横版三国游戏,如何让键盘判断可以得到格斗游戏那样的摇杆判定

【Cocos2d-Js实战教学(1)横版摇杆八方向移动】 - 入梦凡尘 - 博客园
本教程主要通过搭建一个横版摇杆八方向移动的实例,让大家如何用Cocos2dx-Js来做一款游戏,从基础了解Cocos2dx-Js的基本实现原理,从创建工程,到各个知识点的梳理。
教程分为上下两讲:
上讲有2个小节:
1,工程的创建;
2,Cocos2dx-Js目录及Cocos2dx运行原理;
下讲有2个小节:
1,Cocos2dx-Js的事件处理机制;
2,摇杆的、八方向、精灵移动的实现;
Js环境搭载传送门:
轻松搭建完后,开始用JS写一个横版摇杆动作游戏的Demo,听起来貌似很高大上~~。
首先要做好几个准备:
1,角色精灵,我准备了一个骨骼动画精灵1个,cocosstiduo2.0.6制作的;
2,地图,也是用cocosstiduo2.0.6制作,生成出MainScene.csb 文件;
3,摇杆的PNG素材;
下面开始创建一个新的工程GoFighting,创建主场景MainLayer.js文件;
MainLayer继承BaseLayer.js,BaseLayer中处理这个层基本的页面处理,包括弹出的新层的遮罩处理;
BaseLayer.js:
1 var BaseLayer=cc.Layer.extend({
_bgFrame:null,
_notShowAnimation:null,
_directorSteps:null,
_showAnied:false,
init:function(notShowAnimation){
var bret=false;
if(this._super()){
//不可删除
var bgFrame = cc.LayerColor(cc.color(0,0,0,200));
this.addChild(bgFrame);
this._bgFrame=bgF
this._notShowAnimation=notShowA
this.setAnchorPoint(cc.p(0.5,0.5));
this.ignoreAnchorPointForPosition(false);
if(!this._notShowAnimation){
this.setScale(0.8);
this.setContentSize(winSize);
this.setPosition(cc.p(winSize.width/2,winSize.height/2));
cc.eventManager.addListener({
event: cc.EventListener.TOUCH_ONE_BY_ONE,
swallowTouches: true,
//onTouchMoved: this.onTouchMoved,
onTouchBegan: function(){return true;}
bret=true;
setBgColor:function(color){
this._bgFrame.setColor(color);
onEnter:function(){
this._super();
if(!this._notShowAnimation&&!this._showAnied){
var sl=cc.EaseIn.create(cc.ScaleTo.create(0.15,1.1),2);
var sl2=cc.ScaleTo.create(0.15,1);
var seq=cc.Sequence.create(sl,sl2);
this.runAction(seq);
this._showAnied=true;
onExit:function(){
this._super();
MemoryManager.getInstance().releaseMeoryFromOther();
54 BaseLayer.OpenActionFs=function(obj){
obj.setScale(0.8);
if(obj!=null){
var sl=cc.EaseIn.create(cc.ScaleTo.create(0.15,1.1),2);
var sl2=cc.ScaleTo.create(0.15,1);
var seq=cc.Sequence.create(sl,sl2);
obj.runAction(seq);
首先我们加载主场景必须得背景图片,而主场景背景图片由cocosstiduo2.0.6制作,如何绑定呢?
在3.2引擎终目前还不支持直接使用widgetFromBinaryFile方法加载CSB,那么换成另外一种加载创建Node的方式:
ccs.csLoader.createNode(res.MainScene_CSB);
使用该方法需要自己去添加全路径
cocostidio制作的CSB文件加载,注:
在3.2引擎终目前还不支持直接使用widgetFromBinaryFile方法加载CSB
var baseroot = ccs.csLoader.createNode(res.MainScene_CSB);
baseroot.setAnchorPoint(cc.p(0.5,0.5));
baseroot.setPosition(this.getContentSize().width/2,this.getContentSize().height/2);
this.baseroot=
this.addChild(baseroot,1,9001);
BaseLayer.OpenActionFs(baseroot);
然后Run看一下效果:
然后继续加载角色的骨骼动画
//角色骨骼动画加载
var charname = "Char_014_1";
var nowcharurl = resRole+charname+".ExportJson";
if(jsb.fileUtils.isFileExist(nowcharurl)==true) {
cc.log("nowcharurl =" + nowcharurl);
ccs.ArmatureDataManager.getInstance().addArmatureFileInfo(nowcharurl);
var hero = ccs.Armature.create(charname);
this._hero_donghua =
hero.setPosition(cc.p(330, 260));
hero.getAnimation().play("stand");
hero.getAnimation().setMovementEventCallFunc(this.overStand, this);
baseroot.addChild(hero, 3,99999);
角色hero有回调,如跑动后停下来的回调:
//移动完后回调
overStand:function() {
if(this._hero_donghua.getAnimation().getCurrentMovementID()=="")
this._hero_donghua.getAnimation().play("stand");
单单一个角色植入场景是否显得逻辑太单调,我们可以拖动这个精灵岂不更好,加一个简单的事件,让精灵活一点吧!!
//主角监听
var listener_Role = cc.EventListener.create({
event: cc.EventListener.TOUCH_ONE_BY_ONE,
swallowTouches: true,
onTouchBegan: function (touch, event) {
var target = event.getCurrentTarget();
var locationInNode = target.convertToNodeSpace(touch.getLocation());
var s = target.getContentSize();
var rect = cc.rect(0, 0, s.width, s.height);
if (cc.rectContainsPoint(rect, locationInNode)) {
cc.log("sprite began... x = " + locationInNode.x + ", y = " + locationInNode.y);
target.setOpacity(180);
target.getAnimation().play("move");
return true;
return false;
onTouchMoved: function (touch, event) {
var target = event.getCurrentTarget();
var delta = touch.getDelta();
target.x += delta.x;
target.y += delta.y;
onTouchEnded: function (touch, event) {
var target = event.getCurrentTarget();
cc.log("sprite onTouchesEnded.. ");
target.setOpacity(255);
target.getAnimation().play("stand");
在ctor构造中添加角色事件的注册方法:
cc.eventManager.addListener(listener_Role, this._hero_donghua);
OK,我们再Run起来看看效果:
还可以拖动的呢!
然后,我们继续实现摇杆模式:
摇杆与事件有关,JS中摇杆须继承cc.EventListener去创建事件,事件类型cc.EventListener.TOUCH_ONE_BY_ONE(单点触摸方式);
//摇杆监听
var listener_YaoGan = cc.EventListener.create({
event: cc.EventListener.TOUCH_ONE_BY_ONE,
swallowTouches: true,
onTouchBegan: function (touch, event) {
var target = event.getCurrentTarget();
var locationInNode = target.convertToNodeSpace(touch.getLocation());
//创建摇杆
this.sprite_yaogan = new cc.Sprite(res.YaoGan_png);
this.sprite_yaogan.attr({
x: locationInNode.x,
y: locationInNode.y
target.addChild(this.sprite_yaogan, 4,90099);
//创建摇杆点
this.sprite_yaogan_dian = new cc.Sprite(res.YaoGan_Dian_png);
this.sprite_yaogan_dian.attr({
x: locationInNode.x,
y: locationInNode.y
target.addChild(this.sprite_yaogan_dian, 4,90999);
return true;
onTouchMoved: function (touch, event) {
var target = event.getCurrentTarget();
var sp_dian = target.getChildByTag(90999);
var sp_yaoganbd = target.getChildByTag(90099);
var sp_hero = target.getChildByTag(99999);
if(sp_dian!=null&&sp_yaoganbd!=null)
var p_dian =
sp_yaoganbd.getPosition();
var bd_width =sp_yaoganbd.getContentSize().width*0.5;
cc.log("bd_width&&=="+bd_width);
var point = touch.getLocation();
var p_rad = this.getRad(p_dian,point);
cc.log("p_rad&&=="+p_rad);
//计算两个圆心之间距离
var juli =Math.sqrt(Math.pow((p_dian.x - point.x),2) + Math.pow((p_dian.y - point.y),2));
//距离不超过半径
if(juli&=bd_width)
cc.log("go111&&&");
sp_dian.setPosition(cc.pAdd(this.getAngelePosition(bd_width,p_rad),cc.p(p_dian.x,p_dian.y)));
cc.log("go2222&&&");
var delta = touch.getDelta();
sp_dian.x += delta.x;
sp_dian.y += delta.y;
//判断方向---四方向
if(p_rad&=-PI/4&&p_rad&PI/4)
R_Direction="right";
else if(p_rad&=PI/4&&p_rad&3*PI/4)
R_Direction="up";
else if((p_rad&=3*PI/4&&p_rad&=PI)||(p_rad&=-PI&&p_rad&-3*PI/4))
R_Direction="left";
else if(p_rad&=-3*PI/4&&p_rad&-PI/4)
R_Direction="down";
//判断方向---八方向
var move_x =
parseInt(p_dian.x -point.x);
var move_y =
parseInt(p_dian.y -point.y);
if(move_x&=10&&move_y&=-10)
R_Direction = "left_up";
else if(move_x&=10&&move_y&=10)
R_Direction = "left_down";
else if(move_x&=-10&&move_y&=-10)
R_Direction = "rigth_up";
else if(move_x&=-10&&move_y&=10)
R_Direction = "rigth_down";
else if(move_x&-10&&move_x&10&&move_y&0)
R_Direction = "down";
else if(move_x&-10&&move_x&10&&move_y&0)
R_Direction = "up";
else if(move_x&0&&move_y&-10&&move_y&10)
R_Direction = "left";
else if(move_x&0&&move_y&-10&&move_y&10)
R_Direction = "right";
R_Action="move";
cc.log("R_Direction&&&"+R_Direction);
//获取半径坐标
getAngelePosition:function(r,angle){
return cc.p(r*Math.cos(angle),r*Math.sin(angle));
//判断两点之间夹角
getRad:function(pos1,pos2)
var px1 = pos1.x;
var py1 = pos1.y;
var px2 = pos2.x;
var py2 = pos2.y;
//得到两点x的距离
var x = px2 - px1;
//得到两点y的距离
var y = py1 - py2;
//算出斜边长度
var xie = Math.sqrt(Math.pow(x,2) + Math.pow(y,2));
//得到这个角度的余弦值(通过三角函数中的店里:角度余弦值=斜边/斜边)
var cosAngle = x /
//通过反余弦定理获取到期角度的弧度
var rad = Math.acos(cosAngle);
//注意:当触屏的位置Y坐标&摇杆的Y坐标,我们要去反值-0~-180
if (py2 & py1)
onTouchEnded: function (touch, event) {
var target = event.getCurrentTarget();
if(target.getChildByTag(90099)!=null)
target.removeChildByTag(90099);
if(target.getChildByTag(90999)!=null)
target.removeChildByTag(90999);
R_Action="stand";
var sp_hero = target.getChildByTag(99999);
sp_hero.getAnimation().play("stand");
在上面这个Js类中,包含了几个方法如,两点之间夹角的计算公式和最大半径坐标的计算公式;
因为我们需要在摇杆和摇杆点上面去做坐标处理,计算出夹角来对角色进行坐标位移操作,达到我们所需要的效果
跑起来的摇杆效果如下:
摇杆可以活动了,并且不能超过底下的背景半径,达到了我们需要的效果,下面就继续实现摇杆操控精灵移动的功能
可以继续在onTouchMoved: function (touch, event)事件终写方法获取一些判定参数:
var R_Direction = "";
var R_Action = "stand";
//移动速度
var R_speed = 4;
继续看listener_YaoGan类中的方向判断,我写了2种角色移动方法:
1,根据PI=3.1415 来计算 ,做了4方向的标识判断
2,根据坐标差值来计算,做了8方向的标识判断
OK,两种方法都可以行,可以自己拓展。
有了标识我们需要启动一个定时器来执行人物的操作
下面是定时器部分的代码:
//更新状态
runGame:function(){
if(R_Action=="move")
if(this._hero_donghua!=null)
if(this._hero_donghua.getAnimation().getCurrentMovementID()!="move")
this._hero_donghua.getAnimation().play("move");
var p_hero_old = this._hero_donghua.getPosition();
if(R_Direction=="right")
this._hero_donghua.setScaleX(-1);
this._hero_donghua.setPosition(cc.p(p_hero_old.x+R_speed,p_hero_old.y));
else if(R_Direction=="up")
this._hero_donghua.setPosition(cc.p(p_hero_old.x,p_hero_old.y+R_speed));
else if(R_Direction=="left")
this._hero_donghua.setScaleX(1);
this._hero_donghua.setPosition(cc.p(p_hero_old.x-R_speed,p_hero_old.y));
else if(R_Direction=="down")
this._hero_donghua.setPosition(cc.p(p_hero_old.x,p_hero_old.y-R_speed));
else if(R_Direction=="left_up")
this._hero_donghua.setScaleX(1);
this._hero_donghua.setPosition(cc.p(p_hero_old.x-R_speed,p_hero_old.y+R_speed));
else if(R_Direction=="left_down")
this._hero_donghua.setScaleX(1);
this._hero_donghua.setPosition(cc.p(p_hero_old.x-R_speed,p_hero_old.y-R_speed));
else if(R_Direction=="rigth_up")
this._hero_donghua.setScaleX(-1);
this._hero_donghua.setPosition(cc.p(p_hero_old.x+R_speed,p_hero_old.y+R_speed));
else if(R_Direction=="rigth_down")
this._hero_donghua.setScaleX(-1);
this._hero_donghua.setPosition(cc.p(p_hero_old.x+R_speed,p_hero_old.y-R_speed));
OK,人物可以根据摇杆八方向的跑动起来了,我们Run起来看看效果,应该很赞!
嗯,该Demo就开发完毕了,下面是整个DEMO的下载地址,希望能大家对大家起到帮助;
自己创建一个新的工程,将ZIP解压文件拷贝到工程根目录就可以Run起来,替换main.js和project.json;

我要回帖

更多关于 ios11 横版键盘 的文章

 

随机推荐