Laya1.8.4 UI长按选择对应位置释放技能

时间:2024-03-30 13:28:32

需求:

需要实现拖拽摇杆选择技能释放位置,释放技能。

原理:首先拆分需求,分为两部分,UI部分和场景部分,UI部分需要实现长按效果,长按后又要有拖动效果,将官方文档的示例代码改了改就实现了UI部分,然后就是场景部分,有时候是拖动圆的位置,有时候是旋转扇形的方向,前一种就是以人物自身为圆心,用技能的范围长度为半径,配合着UI部分给出的弧度转换为方向坐标,再加上人物位置即可,同时还要注意UI摇杆按钮有个极限拖拽的长度,因此对应场景中的也需有个范围长度,直接上代码吧!

    _proto.Init = function(){
 
        this.skill2.on(Laya.Event.MOUSE_DOWN,this,this.onPreSkill2);
        Laya.stage.on(Laya.Event.MOUSE_UP,this,this.onRelaseSkill2);
        this.knob.visible = false;

        this.curTouchId = 0;
        /***手指(鼠标)是否按下****/
        this.isDown = false;
        /***摇杆的角度****/
        this.angle = -1;        
        /***摇杆的弧度****/
        this.radians = -1;
        /***是否左手遥控****/
        this.isleftControl = true;   
        //控制器中心点位置初始化
        this.originPiont = new Laya.Point(this.skill2.x,this.skill2.y);
        this.scale = 1;
    }

    _proto.onPreSkill2 = function(e){
        Laya.timer.once(500,this,this.onHold,[e]);
    }

    _proto.onHold = function(e){
        this.isHold = true;
        this.knob.visible = true;
        this.curTouchId = e.touchId;
        //已按下
        this.isDown = true;
        //初始化摇杆控制点位置
        this.knob.pos(this.skill2.x,this.skill2.y);
        //摇杆移动控制事件监听
        Laya.stage.on(Laya.Event.MOUSE_MOVE,this,this.onMove);
    }
    
    _proto.onRelaseSkill2 = function(e){
	// 鼠标放开时,如果正在hold,则播放放开的效果
    if (this.isHold)
    {
        this.isHold = false;
        this.knob.visible = false;
        Laya.stage.off(Laya.Event.MOUSE_MOVE,this,this.onMove);
        //修改摇杆角度与弧度为-1(代表无角度)
        this.radians = this.angle = -1;
    }
    Laya.timer.clear(this, this.onHold);
    }

    _proto.onMove = function(e){
        //如果不是上次的点击id,返回(避免多点抬起,以第一次按下id为准)
        if(e.touchId != this.curTouchId)return;
        //将移动时的鼠标屏幕坐标转化为摇杆局部坐标
        var locationPos = this.globalToLocal(new Laya.Point(Laya.stage.mouseX,Laya.stage.mouseY),false);
        //更新摇杆控制点位置
        this.knob.pos(locationPos.x,locationPos.y);
        //更新控制点与摇杆中心点位置距离
        this.deltaX = locationPos.x - this.originPiont.x;
        this.deltaY = locationPos.y - this.originPiont.y;
        //console.log(this.deltaX,this.deltaY);
        //计算控制点在摇杆中的角度
        var dx = this.deltaX * this.deltaX;
        var dy = this.deltaY * this.deltaY;
        //console.log(dx,dy);
        this.angle = Math.atan2(this.deltaX,this.deltaY) * 180 / Math.PI; 
        if(this.angle < 0) this.angle += 360;
        //对角度取整
        this.angle = Math.round(this.angle);
        //计算控制点在摇杆中的弧度
        this.radians = Math.PI / 180 * this.angle;
        //强制控制点与中心距离不超过80像素
        if(dx+dy >= 80*80){
            //控制点在半径为80像素的位置(根据弧度变化)
            var x = Math.floor(Math.sin(this.radians) * 80 +this.originPiont.x);
            var y = Math.floor(Math.cos(this.radians) * 80 + this.originPiont.y);
            this.knob.pos(x,y);
            this.scale = 1;
        }
        else{
            //不超过80像素取原坐标
            this.knob.pos(locationPos.x,locationPos.y);
            this.scale = (dx + dy)/(80*80);
        }
    }
//场景部分
   if(this.mMainUI.angle != -1)
        {
            var scale = this.mMainUI.scale;
            var speedX = Math.sin(this.mMainUI.radians) * 3 * scale;
            var speedZ = Math.cos(this.mMainUI.radians) * 3 * scale;
            var pos = new Vector3();
            Vector3.add(this._owner.transform.position,new Vector3(speedX,0,speedZ),pos);
            this.range.transform.position = pos;
        }
        else{
//range就是那个白色的圈
            this.range.transform.position = this._owner.transform.position;
        }

参考链接:3D角色脚本控制与碰撞检测__LAYABOX技术文档

鼠标交互--Hold (layabox.com)