Empresas
Empregos
  • Sobre nós
  • Soluções
    • Publicação de vagas
      Publique sua vaga e receba candidatos qualificados em 48h.
    • Avaliações de candidatos
      Mais de 500 testes técnicos e psicológicos, mais anti-fraude.
    • Headhunting
      Busca executiva personalizada do início ao fim.
    • Folha de Pagamento + EOR
      Dispersão de folha e EOR em mais de 15 países da LATAM.
  • Preços
  • Empregos

0

848
Visualizações
Unity - How to jump using a NavMeshAgent and click to move logic

I am building a game where the player can be controlled using the mouse input, using a click to move logic via a navmesh agent.

In order to let the player jump, I started using a CharacterController as well which should help managing the player. My issue is that I can't figure out where to put the jump logic. All references I found are related using the character controller without the navmesh agent.

I can get rid of the CharacterController if needed, but the NavMeshAgent has to stay.

Here it is a working code which allows to walk. Can you please help me with the jumping logic?

  private NavMeshAgent _agent;
  private CharacterController _characterController;
  private Vector3 _desVelocity;

  private void Update()
  {
     if (Input.GetMouseButtonDown(0))
     {
         Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
         if (Physics.Raycast(ray.origin, ray.direction, out RaycastHit hitInfo))
         {
             _agent.destination = hitInfo.point;
         }
     }
     var currMovementDirection = _desVelocity.normalized * currentSpeed;
     if (_agent.remainingDistance > _agent.stoppingDistance)
     {
         _desVelocity = _agent.desiredVelocity;
         _characterController.Move(currMovementDirection * Time.deltaTime);
     }
 }
over 4 years ago · Santiago Trujillo
2 Respostas
Responde à pergunta

0

You can achieve this using a Rigidbody instead of a CharacterController. The trick is that you need to disable the NavMeshAgent in order to jump.

Optionally, you set the destination to where you are at the time of the jump, so that the agent doesn't continue the simulation while the jump is happening.

Using collision detection, you turn the NavMeshAgent back on again once you land.

public class PlayerMovement : MonoBehaviour
{

    private Camera cam;
    private NavMeshAgent agent;
    private Rigidbody rigidbody;
    public bool grounded = true;

    void Start()
    {
        cam = Camera.main;
        agent = GetComponent<NavMeshAgent>();
        rigidbody = GetComponent<Rigidbody>();
    }

    void Update()
    {
        // clicking on the nav mesh, sets the destination of the agent and off he goes
        if (Input.GetMouseButtonDown(0) && (!agent.isStopped))
        {
            Ray ray = cam.ScreenPointToRay(Input.mousePosition);
            if (Physics.Raycast(ray, out RaycastHit hit))
            {
                agent.SetDestination(hit.point);
            }
        }

        // when you want to jump
        if (Input.GetKeyDown(KeyCode.Space) && grounded)
        {
            grounded = false;
            if (agent.enabled)
            {
                // set the agents target to where you are before the jump
                // this stops her before she jumps. Alternatively, you could
                // cache this value, and set it again once the jump is complete
                // to continue the original move
                agent.SetDestination(transform.position);
                // disable the agent
                agent.updatePosition = false;
                agent.updateRotation = false;
                agent.isStopped = true;
            }
            // make the jump
            rigidbody.isKinematic = false;
            rigidbody.useGravity = true;
            rigidbody.AddRelativeForce(new Vector3(0, 5f, 0), ForceMode.Impulse);
        }
    }

    /// <summary>
    /// Check for collision back to the ground, and re-enable the NavMeshAgent
    /// </summary>
    private void OnCollisionEnter(Collision collision)
    {
        if (collision.collider != null && collision.collider.tag == "Ground")
        {
            if (!grounded)
            {
                if (agent.enabled)
                {
                    agent.updatePosition = true;
                    agent.updateRotation = true;
                    agent.isStopped = false;
                }
                rigidbody.isKinematic = true;
                rigidbody.useGravity = false;
                grounded = true;
            }
        }
    }
}
over 4 years ago · Santiago Trujillo Relatório

0

The jump logic should be inside the Update() method since we want the height to be calculated every frame.

void Update()
{
    if (Input.GetMouseButtonDown(0))
    {
        Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);
        if (Physics.Raycast(ray.origin, ray.direction, out RaycastHit hitInfo))
        {
            _agent.destination = hitInfo.point;
        }
    }
    var currMovementDirection = _desVelocity.normalized * currentSpeed;

    groundedPlayer = _characterController.isGrounded;
    if (groundedPlayer && currMovementDirection.y < 0)
    {
        currMovementDirection.y = 0f;
    }



    // Changes the height position of the player..
    if (Input.GetButtonDown("Jump") && groundedPlayer)
    {
        currMovementDirection.y += Mathf.Sqrt(jumpHeight * -3.0f * gravityValue);
    }

    currMovementDirection.y += gravityValue * Time.deltaTime;
    if (_agent.remainingDistance > _agent.stoppingDistance)
    {
        _desVelocity = _agent.desiredVelocity;
        _characterController.Move(currMovementDirection * Time.deltaTime);
    }
}

Please see the official docs here

over 4 years ago · Santiago Trujillo Relatório
Responde à pergunta
Encontrar trabalhos remotos

Descubra a nova forma de encontrar um emprego!

melhores empregos
Principais categorias de trabalho
Empresas
Postar vaga Preços Comercial
Jurídico
Termos e Condições Política de privacidade
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomende algumas ofertas para mim
Preciso de ajuda