0
\$\begingroup\$

So I've been trying to make a top down game with the new input system. Been trying to make the character rotate and look at the mouse's position. The player moves on the x and z axis, with the camera looking down from the y axis.

Been following this guide https://youtu.be/bXNFxQpp2qk?t=1280 for Character Controller. This got me getting basic movement working and at time 21:20 he creates a way to rotate the player. The end result I'm trying to get working is something like this https://youtu.be/rQG9aUWarwE with it's field of view as well.

My current result looks like this: https://gfycat.com/equaldefiantblackbear

I got it rotating, but its not working right, the player is stuck looking on the right its not actually looking at the mouse correctly. I've been stuck on this for weeks, and I couldn't figure out why.

Here is my player inputs and I'm taking mouse mouse position as a Vector2.

Player Inputs

Rotation is handled within this method in my code: where mousePosition can get he mouse position correctly, and then mouseViewportPosition converts it to a vector3 for the player to use.

Still can't figure out how to get the player to look at the mouse position as rotation. I assume it's because of something with the conversion of vector2 to vector3 that's causing, but I am relatively new to unity. I only know that I need to make the character rotate on the x and z axis only, and this rotation need to be based on mouse position.

Been trying guides such as https://youtu.be/b0AQg5ZTpac and https://youtu.be/H2RLv0aWUB0 but got no progress at all.

If anyone wants the full code on the player, then its posted below the method.

Here's the full method code, this method is called within Update():

void handleRotation()
    {
        // We're getting a Vector2, whereas we will need a Vector3
        // Get a z value based on camera, and include it in a Vector3
        Vector2 mousePosition = playerInput.CharacterControls.MousePosition.ReadValue<Vector2>();

        var mousePositionZ = _camera.farClipPlane * .5f;

        Vector3 mouseViewportPosition = _camera.ViewportToWorldPoint(new Vector3(mousePosition.x, mousePosition.y, _camera.transform.position.y));


        Debug.Log("MousePos: " + mouseViewportPosition);

        Vector3 positionToLookAt;
        positionToLookAt.x = mouseViewportPosition.x;
        positionToLookAt.y = 0.0f;
        //positionToLookAt.z = currentMovement.z;
        positionToLookAt.z = mouseViewportPosition.z;

        Quaternion currentRotation = transform.rotation;
        
        Quaternion targetRotation = Quaternion.LookRotation(positionToLookAt - transform.position);
        transform.rotation = Quaternion.Slerp(currentRotation, targetRotation, rotationFactorPerFrame * Time.deltaTime);
        
    }

Full code if anyone is interested:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.InputSystem;

public class AnimationAndMovementController : MonoBehaviour
{

    PlayerInput playerInput;
    CharacterController characterController;


    Animator animator;

    int isWalkingHash;
    int isRunningHash;

    Camera _camera;

    Vector2 currentMovementInput;
    Vector3 currentMovement;
    Vector3 currentRunMovement;

    bool isMovementPressed;
    bool isRunPressed;

    float rotationFactorPerFrame = 15.0f;
    float runMultiplier = 3.0f;



    // Start is called before the first frame update
    void Start()
    {
        _camera = Camera.main;
    }

    void Awake()
    {
        playerInput = new PlayerInput();
        characterController = GetComponent<CharacterController>();
        animator = GetComponent<Animator>();

        isWalkingHash = Animator.StringToHash("isWalking");
        isRunningHash = Animator.StringToHash("isRunning");


        playerInput.CharacterControls.Move.started += onMovementInput;
        playerInput.CharacterControls.Move.canceled += onMovementInput;
        playerInput.CharacterControls.Move.performed += onMovementInput;

        playerInput.CharacterControls.Run.started += onRun;
        playerInput.CharacterControls.Run.canceled += onRun;

    }


    void onRun(InputAction.CallbackContext context)
    {
        isRunPressed = context.ReadValueAsButton();
    }


    void onMovementInput(InputAction.CallbackContext context)
    {

        currentMovementInput = context.ReadValue<Vector2>();
        currentMovement.x = currentMovementInput.x;
        currentMovement.z = currentMovementInput.y;

        currentRunMovement.x = currentMovementInput.x * runMultiplier;
        currentRunMovement.z = currentMovementInput.y * runMultiplier;

        isMovementPressed = currentMovementInput.x != 0 || currentMovementInput.y != 0;

    }



    void handleAnimation()
    {
        bool isWalking = animator.GetBool(isWalkingHash);
        bool isRunning = animator.GetBool(isRunningHash);

        if (isMovementPressed && !isWalking)
        {
            animator.SetBool(isWalkingHash, true);
        }
        else if (!isMovementPressed && isWalking)
        {
            animator.SetBool(isWalkingHash, false);
        }

        if ((isMovementPressed && isRunPressed) && !isRunning)
        {
            animator.SetBool(isRunningHash, true);
        }
        else if ((!isMovementPressed && !isRunPressed) && isRunning)
        {
            animator.SetBool(isRunningHash, false);
        }
        else if ((isMovementPressed && !isRunPressed) && isRunning)
        {
            animator.SetBool(isRunningHash, false);
        }

    }


    void handleGravity()
    {
        if (characterController.isGrounded)
        {
            float groundedGravity = -0.05f;
            currentMovement.y = groundedGravity;
            currentRunMovement.y = groundedGravity;
        }
        else
        {
            float gravity = -9.8f;
            currentMovement.y = gravity;
            currentRunMovement.y = gravity;
        }
    }

    void handle_isRunPressed()
    {
        if (isRunPressed)
        {
            characterController.Move(currentRunMovement * Time.deltaTime);
        }
        else
        {
            characterController.Move(currentMovement * Time.deltaTime);
        }
    }

    void handleRotation()
    {
        // We're getting a Vector2, whereas we will need a Vector3
        // Get a z value based on camera, and include it in a Vector3
        Vector2 mousePosition = playerInput.CharacterControls.MousePosition.ReadValue<Vector2>();

        var mousePositionZ = _camera.farClipPlane * .5f;

        Vector3 mouseViewportPosition = _camera.ViewportToWorldPoint(new Vector3(mousePosition.x, mousePosition.y, _camera.transform.position.y));


        Debug.Log("MousePos: " + mouseViewportPosition);

        Vector3 positionToLookAt;
        positionToLookAt.x = mouseViewportPosition.x;
        positionToLookAt.y = 0.0f;
        //positionToLookAt.z = currentMovement.z;
        positionToLookAt.z = mouseViewportPosition.z;


        


        Quaternion currentRotation = transform.rotation;
        
        Quaternion targetRotation = Quaternion.LookRotation(positionToLookAt - transform.position);
        transform.rotation = Quaternion.Slerp(currentRotation, targetRotation, rotationFactorPerFrame * Time.deltaTime);
        
    }


    float AngleBetweenTwoPoints(Vector3 a, Vector3 b)
    {
        return Mathf.Atan2(b.y - a.y, b.x - a.x) * Mathf.Rad2Deg;
    }



    // Update is called once per frame
    void Update()
    {
        handleRotation();
        handleAnimation();
        handleGravity();

        handle_isRunPressed();
    }


    void OnEnable()
    {
        playerInput.CharacterControls.Enable();
    }

    void OnDisable()
    {
        playerInput.CharacterControls.Disable();
    }


}
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.