FixedUpdate para física
Parte de la sección Física y jugabilidad del Journey de Unity de Coddy. Lección 4 de 71.
Unity mueve los cuerpos en pasos de física fijos de 0.02 segundos (Time.fixedDeltaTime), 50 por segundo, independientemente de la frecuencia de fotogramas. FixedUpdate() se ejecuta justo antes de cada paso. Update() se ejecuta una vez por cada fotograma dibujado, y eso puede ser 30, 60 o 144 veces por segundo: a 144, la mayoría de los fotogramas no tienen ningún paso de física, y en un ordenador lento un fotograma puede contener dos.
De aquí se desprenden dos reglas. Una fuerza añadida en Update() se añade una vez por fotograma, así que un ordenador más rápido empuja con más fuerza: las fuerzas que actúan a lo largo del tiempo van en FixedUpdate(). Además, GetKeyDown es verdadero durante un solo fotograma; si ese fotograma no tiene ningún paso de física, FixedUpdate() nunca lo detecta y se pierde la pulsación. Por eso, lee las pulsaciones en Update(), guárdalas en un bool y actúa en consecuencia en FixedUpdate(). Esta barca recibe el empuje constante del viento y se desplaza lateralmente con un clic:
private bool dashQueued;
void Update()
{
if (Input.GetMouseButtonDown(0))
{
dashQueued = true; // recuerda el clic
}
}
void FixedUpdate()
{
rb.AddForce(Vector3.forward * wind); // un empuje constante en cada paso
if (dashQueued)
{
rb.AddForce(Vector3.right * 4f, ForceMode.Impulse);
dashQueued = false; // un clic, un impulso
}
}Es importante borrar el valor booleano después de usarlo: si se dejara en true, se desplazaría en cada paso. También se podría añadir un único impulso directamente desde Update(), como se hacía con el salto de la rana; el valor booleano mantiene todos los empujes en un solo lugar, junto a las fuerzas con las que interactúa. Las teclas mantenidas (GetKey, GetAxis) describen un estado, no un instante, así que FixedUpdate() puede leerlas directamente. Dentro de FixedUpdate(), Time.deltaTime devuelve el valor de 0.02 del paso.
Desafío
FácilColoca las dos tareas del trineo en los métodos correctos.
- Mueve los dos bloques
ifde las flechas deUpdate()aFixedUpdate(). - Añade
private bool hopPressed;. EnUpdate(), asígnaletruecuando se pulseInput.GetKeyDown(KeyCode.Space). - En
FixedUpdate(), cuandohopPressedesté establecido, añade el impulso y luego asígnalefalse.
Pulsa «Jugar»: las flechas impulsan de manera uniforme y cada pulsación de la barra espaciadora hace que el trineo salte. Después, pulsa «Comprobar».
Pruébalo tú mismo
using UnityEngine;
public class Sled : MonoBehaviour
{
public float push = 6f;
public float hop = 5f;
private Rigidbody rb;
void Start()
{
rb = GetComponent<Rigidbody>();
}
void Update()
{
if (Input.GetKey(KeyCode.RightArrow))
{
rb.AddForce(Vector3.right * push);
}
if (Input.GetKey(KeyCode.LeftArrow))
{
rb.AddForce(Vector3.left * push);
}
}
void FixedUpdate()
{
if (Input.GetKeyDown(KeyCode.Space))
{
rb.AddForce(Vector3.up * hop, ForceMode.Impulse);
}
}
}
Todas las lecciones de Física y jugabilidad
1Cuerpo rígido
Gravedad y masaEmpujar con AddForceSaltar con un impulsoFixedUpdate para físicaVelocidadCuerpos cinemáticosRepaso: plataforma de lanzamiento4Corrutinas
InvocarInvokeRepeating y CancelInvokeTu primera corrutinaBucles en corrutinasDetener corrutinasRepaso: cuenta regresiva10Proyecto: Escape de la arena
La arenaCazadores2Colisiones
OnCollisionEnter¿Qué golpeé?Romper al impactarDe pie sobre el sueloRebote y fricciónFormas de los collidersRepaso: muro destructible5Proyecto: Carrera de Monedas
La pelota rodanteMonedas para recoger3Disparadores
Colisionadores de tipo triggerOnTriggerEnterObjetos coleccionablesLas cajas guardan el restoZonas letalesEntrada y salidaRepaso: llave y puertaPractica por tu cuenta: Playground de Unity