El objetivo#
Un personaje que puede saltar desde el suelo y una vez más en el aire (doble salto), y que recupera los saltos al tocar el suelo.
Requisitos#
En tu personaje: un Rigidbody2D (Gravity Scale ≈ 3 para un salto ágil) y un Collider2D. Un objeto vacío hijo colocado en los pies (para detectar el suelo) y una capa "Suelo" asignada a las plataformas.
La receta#
using UnityEngine;
[RequireComponent(typeof(Rigidbody2D))]
public class SaltoDoble : MonoBehaviour
{
[SerializeField] private float fuerzaSalto = 12f;
[SerializeField] private int saltosMaximos = 2; // 2 = doble salto
[SerializeField] private Transform pies;
[SerializeField] private float radioSuelo = 0.2f;
[SerializeField] private LayerMask capaSuelo;
private Rigidbody2D rb;
private int saltosRestantes;
void Awake() => rb = GetComponent<Rigidbody2D>();
void Update()
{
if (EnSuelo() && rb.linearVelocity.y <= 0.01f)
saltosRestantes = saltosMaximos; // recarga al aterrizar
if (Input.GetKeyDown(KeyCode.Space) && saltosRestantes > 0)
{
// Reinicia la velocidad vertical para que el 2.º salto sea consistente
rb.linearVelocity = new Vector2(rb.linearVelocity.x, fuerzaSalto);
saltosRestantes--;
}
}
bool EnSuelo() => Physics2D.OverlapCircle(pies.position, radioSuelo, capaSuelo);
void OnDrawGizmosSelected()
{
if (pies == null) return;
Gizmos.color = Color.red;
Gizmos.DrawWireSphere(pies.position, radioSuelo);
}
}Por qué funciona#
saltosRestantescuenta cuántos saltos quedan; se recarga asaltosMaximosal tocar suelo.- Al reiniciar la velocidad vertical antes de aplicar el impulso, el segundo salto siempre tiene la misma altura, aunque el personaje estuviera cayendo.
saltosMaximoste da salto sencillo (1), doble (2) o triple (3) cambiando un número.
Para que el salto se sienta profesional, añade coyote time (permitir saltar unos milisegundos después de dejar el borde) y jump buffering (recordar la pulsación si se hizo justo antes de aterrizar). Son dos temporizadores pequeños que marcan una diferencia enorme en la sensación de control.
Errores frecuentes#
- No detectar bien el suelo: si el círculo de
piesse solapa con el propio collider del jugador, siempre dará "en suelo". Usa unaLayerMaskque solo incluya el suelo. - Sumar fuerza en vez de fijar velocidad: usar
AddForcepara saltar da alturas inconsistentes según la velocidad previa. FijarlinearVelocity.yes más predecible para plataformas. - Leer el salto en
FixedUpdate:GetKeyDownpuede perderse ahí; léelo enUpdate.
Resumen#
Un contador de saltos + detección de suelo + fijar la velocidad vertical. Cambiando saltosMaximos tienes salto simple, doble o triple. Para entender por qué el input va en Update y la física en FixedUpdate, mira el ciclo de vida.