Search Unity

Player Movement Rotation help

Discussion in 'Scripting' started by OberZine, Oct 22, 2019.

  1. OberZine

    OberZine

    Joined:
    Aug 6, 2018
    Posts:
    17
    Code (CSharp):
    1.  
    2. using System.Collections;
    3. using System.Collections.Generic;
    4. using UnityEngine;
    5.  
    6. public class PlayerMovementPC : MonoBehaviour
    7. {
    8.     public float moveSpeed = 2f;
    9.     //public float turnSpeed = 2f;
    10.  
    11.     public Rigidbody2D player;
    12.  
    13.     Vector2 movement;
    14.  
    15.     // Update is called once per frame
    16.     void Update()
    17.     {
    18.         //input
    19.         movement.x = Input.GetAxisRaw("Horizontal");
    20.         movement.y = Input.GetAxisRaw("Vertical");
    21.  
    22.  
    23.     }
    24.  
    25.     private void FixedUpdate()
    26.     {
    27.         //movement
    28.         player.MovePosition(player.position + movement * moveSpeed * Time.fixedDeltaTime);      
    29.  
    30.         //rotation
    31.         //transform.Rotate(0, movement.x * turnSpeed, 0);
    32.         //transform.eulerAngles = new Vector3(0, transform.eulerAngles.z, 0);
    33.        
    34.  
    35.     }
    36. }
    37.  
    38.  
    So I can move my top down view character, but would like it to rotate to the direction that it is gonna be travelling in.

    The character is a snail. So naturally it won't move fast and won't turn fast. Any solution to that?
     
  2. StarManta

    StarManta

    Joined:
    Oct 23, 2006
    Posts:
    8,775
    You can use this to rotate slowly towards your direction:
    Code (csharp):
    1. transform.rotation = Quaternion.RotateTowards(transform.rotation, targetedRotation, Time.deltaTime * someSpeedInDegrees));
    In 3D, determining the "targetedRotation" is easy (just Quaternion.LookRotation), but in 2D it needs a little more math. Assuming your sprite's "up" is its "forward", you can use this:
    Code (csharp):
    1. Quaternion targetedRotation = Quaternion.AngleAxis(Mathf.Atan2(movement.y, movement.x) * Mathf.Rad2Deg,Vector3.forward);
    (note: you probably want to cache this value and only change it when movement != Vector2.zero)

    From here you basically have two possible approaches:
    1) The snail always moves absolutely in the direction you press to move, and rotating towards it is purely visual. For this, you should be able to just insert the line above and leave it as is.
    2) The snail always moves in its own forward vector, and just turns towards the player's desired movement vector. This will look more correct but players might find it annoying to control, and there's a possibility of getting stuck in corners. For this, you'll want to change your movement line to something more like:
    Code (csharp):
    1. float moveSpeed = movement.magnitude;
    2. player.MovePosition(player.position + player.transform.rotation * Vector3.up * moveSpeed * Time.fixedDeltaTime);[code]
     
  3. OberZine

    OberZine

    Joined:
    Aug 6, 2018
    Posts:
    17
    So I kind of understand what you're saying, I've only ever dealt with 3D, 2D seems way more complicated haha.
    I'm not entirely sure where to put the lines of code you're suggesting?
     
  4. OberZine

    OberZine

    Joined:
    Aug 6, 2018
    Posts:
    17

    Code (CSharp):
    1. public class PlayerMovementPC : MonoBehaviour
    2. {
    3.     public float moveSpeed = 2f;
    4.     //public float turnSpeed = 2f;
    5.  
    6.     public Rigidbody2D player;
    7.  
    8.     Vector2 movement;
    9.  
    10.     // Update is called once per frame
    11.     void Update()
    12.     {
    13.         //input
    14.         movement.x = Input.GetAxisRaw("Horizontal");
    15.         movement.y = Input.GetAxisRaw("Vertical");
    16.  
    17.  
    18.     }
    19.  
    20.     private void FixedUpdate()
    21.     {    
    22.         //movement
    23.         player.MovePosition(player.position + movement * moveSpeed * Time.fixedDeltaTime);
    24.  
    25.         //rotation
    26.  
    27.     }
    28. }
    Based on what I have where do I add rotation? to update? fixedupdate?
     
  5. OberZine

    OberZine

    Joined:
    Aug 6, 2018
    Posts:
    17
    Code (CSharp):
    1. using System.Collections;
    2. using System.Collections.Generic;
    3. using UnityEngine;
    4.  
    5. public class PlayerMovementPC : MonoBehaviour
    6. {
    7.     public float moveSpeed = 2f;  
    8.  
    9.     //public float turnSpeed = 2f;
    10.  
    11.     public Rigidbody2D player;
    12.  
    13.     Vector2 movement;
    14.  
    15.     // Update is called once per frame
    16.     void Update()
    17.     {
    18.         //input
    19.         movement.x = Input.GetAxisRaw("Horizontal");
    20.         movement.y = Input.GetAxisRaw("Vertical");
    21.     }
    22.  
    23.     private void FixedUpdate()
    24.     {
    25.         float moveSpeed = movement.magnitude;
    26.  
    27.         //movement
    28.         player.MovePosition(player.position + movement * moveSpeed * Time.fixedDeltaTime);
    29.         //player.MovePosition(player.position + player.transform.rotation * Vector3.up * moveSpeed * Time.fixedDeltaTime);
    30.  
    31.         //rotation
    32.         if (movement != Vector2.zero)
    33.         {
    34.             Quaternion targetedRotation = Quaternion.AngleAxis(Mathf.Atan2(movement.y, movement.x) * Mathf.Rad2Deg, Vector3.forward);
    35.         }
    36.  
    37.     }
    38. }
    39.  
    I did this just to test if it rotates at all? but it doesn't. it still moves.
     
  6. StarManta

    StarManta

    Joined:
    Oct 23, 2006
    Posts:
    8,775
    You haven't done anything with "targetedRotation" - you still need to apply it to the transform. Use the code from the first code tag in my previous comment.
     
  7. OberZine

    OberZine

    Joined:
    Aug 6, 2018
    Posts:
    17
    Code (CSharp):
    1. {
    2.     public float moveSpeed = 2f;
    3.  
    4.     public float turnSpeed = 2f;
    5.  
    6.     public Quaternion targetedRotation;
    7.  
    8.     public Rigidbody2D player;
    9.  
    10.     Vector2 movement;
    11.  
    12.     // Update is called once per frame
    13.     void Update()
    14.     {
    15.         //input
    16.         movement.x = Input.GetAxisRaw("Horizontal");
    17.         movement.y = Input.GetAxisRaw("Vertical");      
    18.     }
    19.  
    20.     private void FixedUpdate()
    21.     {
    22.         float moveSpeed = movement.magnitude;
    23.  
    24.         //transform.rotation = Quaternion.RotateTowards(transform.rotation, targetedRotation, Time.deltaTime * turnSpeed));
    25.  
    26.         //movement
    27.         //player.MovePosition(player.position + movement * moveSpeed * Time.fixedDeltaTime);
    28.  
    29.         player.MovePosition(player.position + player.transform.rotation * Vector3.up * moveSpeed * Time.fixedDeltaTime);
    30.  
    31.         //rotation
    32.         if (movement != Vector2.zero)
    33.         {
    34.             Quaternion targetedRotation = Quaternion.AngleAxis(Mathf.Atan2(movement.y, movement.x) * Mathf.Rad2Deg, Vector3.forward);
    35.         }
    36.     }
    So I did this but now I'm getting and error on line: player.MovePosition(player.position + player.transform.rotation * Vector3.up * moveSpeed * Time.fixedDeltaTime);

    am I on the right tracks?
     
  8. StarManta

    StarManta

    Joined:
    Oct 23, 2006
    Posts:
    8,775
    You should be doing that after you set the value of targetedRotation. Also, in line 34 you're creating a local "targetedRotation" and the class variable that you're using on line 29 is never getting changed - remove the "Quaternion" from the start of line 34 to make that use the class variable.

    Also, always paste the actual error message - it contains important information for knowing what's going wrong.
     
  9. OberZine

    OberZine

    Joined:
    Aug 6, 2018
    Posts:
    17
    Thanks for your help, I've not got it working. Woo. I'll be sure to reference this thread and you. Thanks again.