Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. We have updated the language to the Editor Terms based on feedback from our employees and community. Learn more.
    Dismiss Notice

Movement issue with conditional statements

Discussion in 'Scripting' started by Wallywee95, Dec 12, 2019.

  1. Wallywee95

    Wallywee95

    Joined:
    Jun 21, 2019
    Posts:
    4
    Hi everyone, please bear with me as I am still getting up to speed with scripting.

    I am currently making a small endless runner style game and currently creating an "intro/upgrade" scene, where the player can move between three pillars. I have stored the X values of the first and last pillar, set those as minimum and maximum width values - and then created an incremental value to keep the player within the right positions. For example, the first pillar is positioned at an x value of 3, the second at 9 and the third at 15. So the minWidth = 3; maxWidth = 15; and the incrementalX = 6.

    upload_2019-12-12_10-21-37.png

    I then take these values and create these conditional statements (which did seem to work fine at first).

    {
    transform.position = Vector2.MoveTowards(transform.position, targetPos, speed * Time.deltaTime);

    if (Input.GetKeyDown(KeyCode.LeftArrow) && transform.position.x > minWidth)
    {
    if (facingRight)
    {
    facingRight = false;
    Flip();
    }
    targetPos = new Vector2(transform.position.x - xIncrement, transform.position.y);
    }

    else if (Input.GetKeyDown(KeyCode.RightArrow) && transform.position.x < maxWidth)
    {
    if (!facingRight)
    {
    facingRight = true;
    Flip();
    }
    targetPos = new Vector2(transform.position.x + xIncrement, transform.position.y );


    The issue I have is that if the player presses one of the arrow keys before the character has finished the journey to one of the pillars - the increment is applied halfway through the movement, meaning that the target position becomes the wrong value.

    I just need a pointer into the direction of how to solve this, I'm having a real mindblank and could use some help!
     

    Attached Files:

  2. Yoreki

    Yoreki

    Joined:
    Apr 10, 2019
    Posts:
    2,590
    Hi and welcome.
    First and foremost, please take a look at the first sticky post on this subforum, which explains how you can use code tags. Code tags make code much more readable by adding proper format and syntax highlighting to it. Other than that, this is a nice looking first post with a good description and images added :)

    So let me summarize, just so i understand you correctly. You have these 3 pillars and you want your player to move between them (from one to the next), but dont want the player to be able to stop inbetween two pillars?
    And your code basically works, but if the player hits some arrow key while the character is still running, it created a problem where the target position is set to the wrong position (somewhere before reaching the target pillar)?
    If all the above is correct, then this is probably because of how you determine targetPos, and that you allow the player to always do it. There are different ways to fix this, but you could just add a 'currentlyMoving' bool, which you set true when either of the conditions is met to make your character move, and false when you detect that he reached his target. You now simply disable the user from making any inputs while 'currentlyMoving' is true, for example by putting all the input-related code in another if statement.

    A more elegant way to solve this problem (imho) would be to have an array of the 3 target positions and a 'targetIndex'. The targetIndex is "moved" by player inputs and the character simply always walks to the position you saved at targets[targetIndex], which should be easily calculatable animation wise. This should get rid of all these problems more elegantly. I'm really short on time right now, if i understood your problem correctly and you need a better explanation of this i can add it later.

    Hope this helps :)
     
    Wallywee95 likes this.
  3. AlexN2805

    AlexN2805

    Joined:
    Nov 27, 2019
    Posts:
    33
    If you don't want your targetPos to exceed either the minWidth or maxWidth, you could use the System.Math.Min() or System.Math.Max() functions when you set targetPos, this causes the position to be minWidth if the position accidentaly becomes lower than minWidth.. or maxWidth when it accidentally becomes bigger than maxWidth:
    Code (CSharp):
    1. targetPos = new Vector2(System.Math.Min(transform.position.x - xIncrement, minWidth), transform.position.y)
    2.  
    3. ... or ...
    4.  
    5. targetPos = new Vector2(System.Math.Max(transform.position.x + xIncrement, minWidth), transform.position.y)
    Keep in mind that this only solves the effect and not so much the cause. It would be better to solve the cause so that this scenario doesn't exist ofcourse.
     
    Wallywee95 likes this.
  4. Wallywee95

    Wallywee95

    Joined:
    Jun 21, 2019
    Posts:
    4
    Hi Yoreki,

    Thanks for such a great reply! The solution seems so simple now - you understood my problem perfectly and your solutions are ideal.

    I will be sure to read the sticky post, I had been worried that the code was difficult to read in this current format, so it will be good to give that a read.

    Thanks again for your response, I have no idea why I didn't think about creating an array for target positions, let alone a simple bool!

    Appreciate the help.