盘旋DPAD有时会使角色在一个方向无限移动 [英] Hovering off DPAD sometimes makes character move infinitely in one direction

查看:239
本文介绍了盘旋DPAD有时会使角色在一个方向无限移动的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在游戏中有一个DPAD,当玩家按下时,让我们说左侧的DPAD,如果他将他的触摸移动到Up DPAD,我们走,玩家继续向左走。



如果你持有一个方向,也可以继续工作,可以说Up继续持有,但是移动Up DPAD,有时候你可以继续朝这个方向前进。
$ b $ 你的动态,或
已经走向不同的方向

  • 设置冲突,迫使这些变量成为错误; aka,
    你碰到了什么,inMotion = false等等。



  • 这就是我所能想到的关于如何解决这个问题的。

    另外,我为我的检查使用了很多变量,更改我的函数返回布尔值,还是这样好?只是好奇。



    游戏类

     
    {
    import flash.display.MovieClip;
    import flash.utils.Timer;
    import flash.events.TimerEvent;

    公共类游戏扩展MovieClip
    {
    public var area1:Boolean = true;
    public var area2:Boolean = false;
    public var area3:Boolean = false;

    public var player1:Boolean = true;
    public var player2:Boolean = false;

    public var upWalkspeed:Number = -5;
    public var downWalkspeed:Number = 5;
    public var leftWalkspeed:Number = -5;
    public var rightWalkspeed:Number = 5;

    public var inMotion:Boolean = false;
    public var goingUp:Boolean = false;
    public var goingDown:Boolean = false;
    public var goingLeft:Boolean = false;
    public var goingRight:Boolean = false;

    public var playerPosKeeper_mc:MovieClip = new mc_PlayerPosKeeper();

    public var up_dpad:MovieClip = new dpad_Up();
    public var down_dpad:MovieClip = new dpad_Down();
    public var left_dpad:MovieClip = new dpad_Left();
    public var right_dpad:MovieClip = new dpad_Right();
    public var menu_dpad:MovieClip = new dpad_Menu();
    public var run_dpad:MovieClip = new dpad_Menu();

    public var barrierRoof1_game:MovieClip = new game_BarrierRoof();
    public var barrierRoof2_game:MovieClip = new game_BarrierRoof();
    public var barrierSide1_game:MovieClip = new game_BarrierSide();
    public var barrierSide2_game:MovieClip = new game_BarrierSide();

    public var StageCollisions:Array = new Array(barrierRoof1_game,barrierRoof2_game,barrierSide1_game,barrierSide2_game);
    //修复MC不在|||之前public var player1States:Array = new Array(mc_P1D1,mc_P1D2,mc_P1L1,mc_P1L2,mc_P1R1,mc_P1R2,mc_P1U1,mc_P1U2);

    public function Game()
    {
    trace(SUCCESS | Constructed Game Class);

    var aMove:Movement = new Movement(this);
    addChild(aMove);



    $ b $ c

    $ p $强> Movement Class

     
    {
    import flash.display.Stage;
    import flash.display.MovieClip;
    import flash.events.Event;
    导入flash.events.TouchEvent;
    import flash.net.dns.AAAARecord;
    导入flash.ui.Multitouch;
    import flash.ui.MultitouchInputMode;


    公共类运动延伸MovieClip
    {
    公共功能运动(main:游戏)
    {
    trace(SUCCESS |构造运动类);

    addChild(main.playerPosKeeper_mc);
    main.playerPosKeeper_mc.x = 384;
    main.playerPosKeeper_mc.y = 46;

    addChild(main.up_dpad);
    main.up_dpad.x = 55;
    main.up_dpad.y = 336;

    addChild(main.down_dpad);
    main.down_dpad.x = 57;
    main.down_dpad.y = 432;

    addChild(main.left_dpad);
    main.left_dpad.x = 19;
    main.left_dpad.y = 372;

    addChild(main.right_dpad);
    main.right_dpad.x = 118;
    main.right_dpad.y = 372;

    addChild(main.menu_dpad);
    main.menu_dpad.x = 61;
    main.menu_dpad.y = 377;

    addChild(main.run_dpad);
    main.run_dpad.x = 684;
    main.run_dpad.y = 369;

    addChild(main.barrierRoof1_game);
    main.barrierRoof1_game.x = 0;
    main.barrierRoof1_game.y = 0;

    addChild(main.barrierRoof2_game);
    main.barrierRoof2_game.x = 0;
    main.barrierRoof2_game.y = 470;

    addChild(main.barrierSide1_game);
    main.barrierSide1_game.x = 0;
    main.barrierSide1_game.y = 0;

    addChild(main.barrierSide2_game);
    main.barrierSide2_game.x = 790;
    main.barrierSide2_game.y = 0;

    Multitouch.inputMode = MultitouchInputMode.TOUCH_POINT;

    main.up_dpad.addEventListener(TouchEvent.TOUCH_BEGIN,upBeginInput);
    main.down_dpad.addEventListener(TouchEvent.TOUCH_BEGIN,downBeginInput);
    main.left_dpad.addEventListener(TouchEvent.TOUCH_BEGIN,leftBeginInput);
    main.right_dpad.addEventListener(TouchEvent.TOUCH_BEGIN,rightBeginInput);

    //将来可能会添加诊断方向按钮?


    // !!注意 !!
    //使用某种值,可能是返回值或变量来同步动画
    //如果玩家正在移动,将来

    //移动方向

    //开始移动
    函数upBeginInput(e:TouchEvent):void
    {
    main.inMotion = true;
    main.goingUp = true;
    main.goingDown = false;
    main.goingLeft = false;
    main.goingRight = false;
    main.up_dpad.addEventListener(TouchEvent.TOUCH_END,upEndInput);
    addEventListener(Event.ENTER_FRAME,sendUpMovement);

    函数upEndInput(e:TouchEvent):void
    {
    main.inMotion = false;
    main.goingUp = false;
    main.up_dpad.removeEventListener(TouchEvent.TOUCH_END,upEndInput);
    removeEventListener(Event.ENTER_FRAME,sendUpMovement);
    }
    function sendUpMovement():void
    {
    if(main.inMotion == true&& main.goingUp == true&& main.goingDown = = false& main.goingLeft == false& main.goingRight == false)
    {
    movePlayer(0,main.upWalkspeed);
    }
    else
    {
    }
    }
    //结束上移



    //开始向下运动
    函数downBeginInput(e:TouchEvent):void
    {
    main.inMotion = true;
    main.goingUp = false;
    main.goingDown = true;
    main.goingLeft = false;
    main.goingRight = false;
    main.down_dpad.addEventListener(TouchEvent.TOUCH_END,downEndInput);
    addEventListener(Event.ENTER_FRAME,sendDownMovement);

    function downEndInput(e:TouchEvent):void
    {
    main.inMotion = false;
    main.goingDown = false;
    main.down_dpad.removeEventListener(TouchEvent.TOUCH_END,downEndInput);
    removeEventListener(Event.ENTER_FRAME,sendDownMovement);

    函数sendDownMovement():void
    {
    if(main.inMotion == true&& main.goingUp == false&& main.goingDown = = true&& main.goingLeft == false& main.goingRight == false)
    {
    movePlayer(0,main.downWalkspeed);
    }
    else
    {
    }
    }
    //结束向下运动



    // LEFT移动开始
    函数leftBeginInput(e:TouchEvent):void
    {
    main.inMotion = true;
    main.goingUp = false;
    main.goingDown = false;
    main.goingLeft = true;
    main.goingRight = false;
    main.left_dpad.addEventListener(TouchEvent.TOUCH_END,leftEndInput);
    addEventListener(Event.ENTER_FRAME,sendLeftMovement);

    function leftEndInput(e:TouchEvent):void
    {
    main.inMotion = false;
    main.goingLeft = false;
    main.left_dpad.removeEventListener(TouchEvent.TOUCH_END,leftEndInput);
    removeEventListener(Event.ENTER_FRAME,sendLeftMovement);

    function sendLeftMovement():void
    {
    if(main.inMotion == true&& main.goingUp == false&& main.goingDown = = false& main.goingLeft == true&& main.goingRight == false)
    {
    movePlayer(main.leftWalkspeed,0);
    }
    else
    {
    }
    }
    // LEFT移动结束



    //开始右移动
    函数rightBeginInput(e:TouchEvent):void
    {
    main.inMotion = true;
    main.goingUp = false;
    main.goingDown = false;
    main.goingLeft = false;
    main.goingRight = true;
    main.right_dpad.addEventListener(TouchEvent.TOUCH_END,rightEndInput);
    addEventListener(Event.ENTER_FRAME,sendRightMovement);

    function rightEndInput(e:TouchEvent):void
    {
    main.inMotion = false;
    main.goingRight = false;
    main.right_dpad.removeEventListener(TouchEvent.TOUCH_END,rightEndInput);
    removeEventListener(Event.ENTER_FRAME,sendRightMovement);

    函数sendRightMovement():void
    {
    if(main.inMotion == true&& main.goingUp == false&& main.goingDown = = false& main.goingLeft == false& main.goingRight == true)
    {
    movePlayer(main.rightWalkspeed,0);
    }
    else
    {
    }
    }
    // RIGHT结束符


    函数movePlayer( movementX:Number,movementY:Number):void
    {
    var originalX:Number = main.playerPosKeeper_mc.x;
    var originalY:Number = main.playerPosKeeper_mc.y;
    main.playerPosKeeper_mc.x + = movementX;
    if(checkCollision())
    {
    main.playerPosKeeper_mc.x = originalX;
    }
    main.playerPosKeeper_mc.y + = movementY;
    if(checkCollision())
    {
    main.playerPosKeeper_mc.y = originalY;



    函数checkCollision():Boolean
    {
    for each(var StageCollisions:MovieClip in main.StageCollisions)
    {
    if(main.playerPosKeeper_mc.hitTestObject(StageCollisions))
    {
    return true;
    main.inMotion = false;
    main.goingUp = false;
    main.goingDown = false;
    main.goingLeft = false;
    main.goingRight = false;
    }
    }
    return false;



    $ b $ / code $ / pre

    解决方案

    在开始调试行为之前,您需要了解什么是算法。你有4个类似的代码,它们在细节上有所不同,使你的整个脚本太长,难以理解,难以管理。以下是指导原则:

      var isMoving:Boolean; 
    var方向:Point = new Point;
    var Buttons:Array = [Up,Down,Left,Right];

    //订阅相同处理程序和行为的所有按钮。
    for each(var aButton:Buttons中的InteractiveObject)
    {
    aButton.addEventListener(MouseEvent.MOUSE_DOWN,onDown);
    aButton.addEventListener(MouseEvent.MOUSE_OUT,onUp);
    aButton.addEventListener(MouseEvent.MOUSE_UP,onUp);


    函数onDown(e:MouseEvent):void
    {
    //图按下哪个按钮。
    switch(e.currentTarget)
    {
    case up:
    Direction.x = 0;
    Direction.y = -1;
    break;

    情况下:
    Direction.x = 0;
    Direction.y = 1;
    break;

    左:
    Direction.x = -1;
    Direction.y = 0;
    break;

    案例上:
    Direction.x = 1;
    Direction.y = 0;
    break;
    }

    //现在开始移动英雄进入方向。
    if(!isMoving)
    {
    isMoving = true;
    addEventListener(Event.ENTER_FRAME,onFrame);



    函数onFrame(e:Event):void
    {
    Hero.x + = Direction.x;
    Hero.y + = Direction.y;


    函数onUp(e:MouseEvent):void
    {
    //如果有任何按钮被释放或鼠标移出,请停止移动Hero。
    removeEventListener(Event.ENTER_FRAME,onFrame);

    Direction.x = 0;
    Direction.y = 0;

    isMoving = false;





    $ b

    正如你所看到的,算法的优点在于你需要处理在不同的情况下,需要的处理方式不同,在这个例子中(与您想要创建的非常相似),它是设置移动方向的块。其余的代码对于所有的按钮是相同的,这就是为什么整个脚本简短易读,易于理解和管理。

    I have a DPAD in my game when the player holds down let's say the Left DPAD, if he moves his touch to the Up DPAD and let's go, the player continues going in the left direction.

    It also works if you hold the a direction, lets say Up continue holding but move off the Up DPAD, sometimes you may continue going in that direction.

    What I've tried to prevent this:

    • On direction clicks, trigger checks on whether your in motion, or already going a different direction
    • Setting collisions to force these variables to become false; aka, you hit something, inMotion = false, etc

    That's about all I can think of on how to fix this.

    Also, I use a lot of variables for my checks, is it better to change my functions to return booleans, or is this way fine? Just curious.

    Game Class

    package 
    {
        import flash.display.MovieClip;
        import flash.utils.Timer;
        import flash.events.TimerEvent;
    
        public class Game extends MovieClip
        {
            public var area1:Boolean = true;
            public var area2:Boolean = false;
            public var area3:Boolean = false;
    
            public var player1:Boolean = true;
            public var player2:Boolean = false;
    
            public var upWalkspeed:Number = -5;
            public var downWalkspeed:Number = 5;
            public var leftWalkspeed:Number = -5;
            public var rightWalkspeed:Number = 5;
    
            public var inMotion:Boolean = false;
            public var goingUp:Boolean = false;
            public var goingDown:Boolean = false;
            public var goingLeft:Boolean = false;
            public var goingRight:Boolean = false;
    
            public var playerPosKeeper_mc:MovieClip = new mc_PlayerPosKeeper();
    
            public var up_dpad:MovieClip = new dpad_Up();
            public var down_dpad:MovieClip = new dpad_Down();
            public var left_dpad:MovieClip = new dpad_Left();
            public var right_dpad:MovieClip = new dpad_Right();
            public var menu_dpad:MovieClip = new dpad_Menu();
            public var run_dpad:MovieClip = new dpad_Menu();
    
            public var barrierRoof1_game:MovieClip = new game_BarrierRoof();
            public var barrierRoof2_game:MovieClip = new game_BarrierRoof();
            public var barrierSide1_game:MovieClip = new game_BarrierSide();
            public var barrierSide2_game:MovieClip = new game_BarrierSide();
    
            public var StageCollisions:Array = new Array(barrierRoof1_game, barrierRoof2_game, barrierSide1_game, barrierSide2_game);
            // fix MC goes after not before ||| public var player1States:Array = new Array(mc_P1D1,mc_P1D2,"mc_P1L1","mc_P1L2","mc_P1R1","mc_P1R2","mc_P1U1","mc_P1U2");
    
            public function Game()
            {
                trace("SUCCESS | Constructed Game Class");
    
                var aMove:Movement = new Movement(this);
                addChild(aMove);
    
            }
        }
    }
    

    Movement Class

    package 
    {
        import flash.display.Stage;
        import flash.display.MovieClip;
        import flash.events.Event;
        import flash.events.TouchEvent;
        import flash.net.dns.AAAARecord;
        import flash.ui.Multitouch;
        import flash.ui.MultitouchInputMode;
    
    
        public class Movement extends MovieClip
        {
            public function Movement(main:Game)
            {
                trace("SUCCESS | Constructed Movement Class");
    
                addChild(main.playerPosKeeper_mc);
                main.playerPosKeeper_mc.x = 384;
                main.playerPosKeeper_mc.y = 46;
    
                addChild(main.up_dpad);
                main.up_dpad.x = 55;
                main.up_dpad.y = 336;
    
                addChild(main.down_dpad);
                main.down_dpad.x = 57;
                main.down_dpad.y = 432;
    
                addChild(main.left_dpad);
                main.left_dpad.x = 19;
                main.left_dpad.y = 372;
    
                addChild(main.right_dpad);
                main.right_dpad.x = 118;
                main.right_dpad.y = 372;
    
                addChild(main.menu_dpad);
                main.menu_dpad.x = 61;
                main.menu_dpad.y = 377;
    
                addChild(main.run_dpad);
                main.run_dpad.x = 684;
                main.run_dpad.y = 369;
    
                addChild(main.barrierRoof1_game);
                main.barrierRoof1_game.x = 0;
                main.barrierRoof1_game.y = 0;
    
                addChild(main.barrierRoof2_game);
                main.barrierRoof2_game.x = 0;
                main.barrierRoof2_game.y = 470;
    
                addChild(main.barrierSide1_game);
                main.barrierSide1_game.x = 0;
                main.barrierSide1_game.y = 0;
    
                addChild(main.barrierSide2_game);
                main.barrierSide2_game.x = 790;
                main.barrierSide2_game.y = 0;
    
                Multitouch.inputMode = MultitouchInputMode.TOUCH_POINT;
    
                main.up_dpad.addEventListener(TouchEvent.TOUCH_BEGIN, upBeginInput);
                main.down_dpad.addEventListener(TouchEvent.TOUCH_BEGIN, downBeginInput);
                main.left_dpad.addEventListener(TouchEvent.TOUCH_BEGIN, leftBeginInput);
                main.right_dpad.addEventListener(TouchEvent.TOUCH_BEGIN, rightBeginInput);
    
                // Maybe add diagnol direction buttons in the future?;
    
    
                //  !!  NOTE  !!
                //  Use some sort of value, maybe a return or a variable to sync up animations
                // to if the player is moving, in the future
    
                // Movement Directions
    
                // Start of UP Movement
                function upBeginInput(e:TouchEvent):void
                {
                    main.inMotion = true;
                    main.goingUp = true;
                    main.goingDown = false;
                    main.goingLeft = false;
                    main.goingRight = false;
                    main.up_dpad.addEventListener(TouchEvent.TOUCH_END, upEndInput);
                    addEventListener(Event.ENTER_FRAME,sendUpMovement);
                }
                function upEndInput(e:TouchEvent):void
                {
                    main.inMotion = false;
                    main.goingUp = false;
                    main.up_dpad.removeEventListener(TouchEvent.TOUCH_END, upEndInput);
                    removeEventListener(Event.ENTER_FRAME,sendUpMovement);
                }
                function sendUpMovement():void
                {
                    if (main.inMotion == true && main.goingUp == true && main.goingDown == false && main.goingLeft == false && main.goingRight == false)
                    {
                        movePlayer(0, main.upWalkspeed);
                    }
                    else
                    {
                    }
                }
                // End of UP Movement
    
    
    
                // Start of DOWN Movement
                function downBeginInput(e:TouchEvent):void
                {
                    main.inMotion = true;
                    main.goingUp = false;
                    main.goingDown = true;
                    main.goingLeft = false;
                    main.goingRight = false;
                    main.down_dpad.addEventListener(TouchEvent.TOUCH_END, downEndInput);
                    addEventListener(Event.ENTER_FRAME,sendDownMovement);
                }
                function downEndInput(e:TouchEvent):void
                {
                    main.inMotion = false;
                    main.goingDown = false;
                    main.down_dpad.removeEventListener(TouchEvent.TOUCH_END, downEndInput);
                    removeEventListener(Event.ENTER_FRAME,sendDownMovement);
                }
                function sendDownMovement():void
                {
                    if (main.inMotion == true && main.goingUp == false && main.goingDown == true && main.goingLeft == false && main.goingRight == false)
                    {
                        movePlayer(0, main.downWalkspeed);
                    }
                    else
                    {
                    }
                }
                // End of DOWN Movement
    
    
    
                // Start of LEFT Movement
                function leftBeginInput(e:TouchEvent):void
                {
                    main.inMotion = true;
                    main.goingUp = false;
                    main.goingDown = false;
                    main.goingLeft = true;
                    main.goingRight = false;
                    main.left_dpad.addEventListener(TouchEvent.TOUCH_END, leftEndInput);
                    addEventListener(Event.ENTER_FRAME,sendLeftMovement);
                }
                function leftEndInput(e:TouchEvent):void
                {
                    main.inMotion = false;
                    main.goingLeft = false;
                    main.left_dpad.removeEventListener(TouchEvent.TOUCH_END, leftEndInput);
                    removeEventListener(Event.ENTER_FRAME,sendLeftMovement);
                }
                function sendLeftMovement():void
                {
                    if (main.inMotion == true && main.goingUp == false && main.goingDown == false && main.goingLeft == true && main.goingRight == false)
                    {
                        movePlayer(main.leftWalkspeed, 0);
                    }
                    else
                    {
                    }
                }
                // End of LEFT Movement
    
    
    
                // Start of RIGHT Movement
                function rightBeginInput(e:TouchEvent):void
                {
                    main.inMotion = true;
                    main.goingUp = false;
                    main.goingDown = false;
                    main.goingLeft = false;
                    main.goingRight = true;
                    main.right_dpad.addEventListener(TouchEvent.TOUCH_END, rightEndInput);
                    addEventListener(Event.ENTER_FRAME,sendRightMovement);
                }
                function rightEndInput(e:TouchEvent):void
                {
                    main.inMotion = false;
                    main.goingRight = false;
                    main.right_dpad.removeEventListener(TouchEvent.TOUCH_END, rightEndInput);
                    removeEventListener(Event.ENTER_FRAME,sendRightMovement);
                }
                function sendRightMovement():void
                {
                    if (main.inMotion == true && main.goingUp == false && main.goingDown == false && main.goingLeft == false && main.goingRight == true)
                    {
                        movePlayer(main.rightWalkspeed, 0);
                    }
                    else
                    {
                    }
                }
                // End of RIGHT Movement
    
    
                function movePlayer(movementX:Number, movementY:Number):void
                {
                    var originalX:Number = main.playerPosKeeper_mc.x;
                    var originalY:Number = main.playerPosKeeper_mc.y;
                    main.playerPosKeeper_mc.x +=  movementX;
                    if (checkCollision())
                    {
                        main.playerPosKeeper_mc.x = originalX;
                    }
                    main.playerPosKeeper_mc.y +=  movementY;
                    if (checkCollision())
                    {
                        main.playerPosKeeper_mc.y = originalY;
                    }
                }
    
                function checkCollision():Boolean
                {
                    for each (var StageCollisions:MovieClip in main.StageCollisions)
                    {
                        if (main.playerPosKeeper_mc.hitTestObject(StageCollisions))
                        {
                            return true;
                            main.inMotion = false;
                            main.goingUp = false;
                            main.goingDown = false;
                            main.goingLeft = false;
                            main.goingRight = false;
                        }
                    }
                    return false;
                }
            }
        }
    }
    

    解决方案

    Before you even start to debug behaviors, you need to understand what algorithmic approach is. You have 4 similar pieces of code which differ in minor details and make your whole script too long and unreadable and hard to manage. Here's the guideline:

    var isMoving:Boolean;
    var Direction:Point = new Point;
    var Buttons:Array = [Up, Down, Left, Right];
    
    // Subscribe all buttons for the same handlers and behaviors.
    for each (var aButton:InteractiveObject in Buttons)
    {
        aButton.addEventListener(MouseEvent.MOUSE_DOWN, onDown);
        aButton.addEventListener(MouseEvent.MOUSE_OUT, onUp);
        aButton.addEventListener(MouseEvent.MOUSE_UP, onUp);
    }
    
    function onDown(e:MouseEvent):void
    {
        // Figure which button was pressed.
        switch (e.currentTarget)
        {
            case Up:
                Direction.x = 0;
                Direction.y = -1;
                break;
    
            case Down:
                Direction.x = 0;
                Direction.y = 1;
                break;
    
            case Left:
                Direction.x = -1;
                Direction.y = 0;
                break;
    
            case Up:
                Direction.x = 1;
                Direction.y = 0;
                break;
        }
    
        // Now start moving Hero into the Direction.
        if (!isMoving)
        {
            isMoving = true;
            addEventListener(Event.ENTER_FRAME, onFrame);
        }
    }
    
    function onFrame(e:Event):void
    {
        Hero.x += Direction.x;
        Hero.y += Direction.y;
    }
    
    function onUp(e:MouseEvent):void
    {
        // If any of buttons is released or mouse out, stop moving Hero.
        removeEventListener(Event.ENTER_FRAME, onFrame);
    
        Direction.x = 0;
        Direction.y = 0;
    
        isMoving = false;
    }
    

    As you can see, the beauty of algorithmic approach is that you need to handle differently only things that need to be handled differently, in the example case (which is pretty similar to what you want to create) it is the block to set the movement direction. The rest of the code is identical for all the buttons and that's why the whole script is short and readable, easy to understand and manageable.

    这篇关于盘旋DPAD有时会使角色在一个方向无限移动的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

    查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆